alpha release
This commit is contained in:
264
bolt.py
Normal file
264
bolt.py
Normal file
@@ -0,0 +1,264 @@
|
||||
import argparse
|
||||
import concurrent.futures
|
||||
import json
|
||||
import random
|
||||
import re
|
||||
import statistics
|
||||
|
||||
from collections import Counter
|
||||
from fuzzywuzzy import fuzz, process
|
||||
|
||||
import core.config
|
||||
from core.config import token
|
||||
from core.datanize import datanize
|
||||
from core.prompt import prompt
|
||||
from core.photon import photon
|
||||
from core.tweaker import tweaker
|
||||
from core.evaluate import evaluate
|
||||
from core.ranger import ranger
|
||||
from core.zetanize import zetanize
|
||||
from core.requester import requester
|
||||
from core.utils import extractHeaders, entropy, isProtected
|
||||
from core.colors import green, yellow, end, run, good, info, bad, white
|
||||
|
||||
parser = argparse.ArgumentParser()
|
||||
parser.add_argument('-u', help='target url', dest='target')
|
||||
parser.add_argument('-t', help='number of threads', dest='threads', type=int)
|
||||
parser.add_argument('-l', help='levels to crawl', dest='level', type=int)
|
||||
parser.add_argument('--delay', help='delay between requests', dest='delay', type=int)
|
||||
parser.add_argument('--timeout', help='http request timeout', dest='timeout', type=int)
|
||||
parser.add_argument('--headers', help='http headers', dest='headers', action='store_true')
|
||||
args = parser.parse_args()
|
||||
|
||||
def banner():
|
||||
print ('''%s
|
||||
⚡ %sBOLT%s ⚡
|
||||
%s''' % (yellow, white, yellow, end))
|
||||
|
||||
if not args.target:
|
||||
banner()
|
||||
print('\n' + parser.format_help().lower())
|
||||
quit()
|
||||
|
||||
if args.headers:
|
||||
headers = extractHeaders(prompt())
|
||||
else:
|
||||
headers = core.config.headers
|
||||
|
||||
banner()
|
||||
|
||||
target = args.target
|
||||
delay = args.delay or 0
|
||||
level = args.level or 2
|
||||
timeout = args.timeout or 20
|
||||
threadCount = args.threads or 2
|
||||
|
||||
allTokens = []
|
||||
weakTokens = []
|
||||
tokenDatabase = []
|
||||
insecureForms = []
|
||||
|
||||
print ('%s Phase: Crawling %s[%s1/5%s]%s' % (run, green, end, green, end))
|
||||
dataset = photon(target, headers, level, threadCount)
|
||||
allForms = dataset[0]
|
||||
print ('\r%s Crawled %i URL(s) and found %i form(s).%-10s' % (info, dataset[1], len(allForms), ' '))
|
||||
print ('%s Phase: Evaluating %s[%s2/5%s]%s' % (run, green, end, green, end))
|
||||
|
||||
evaluate(allForms, weakTokens, tokenDatabase, allTokens, insecureForms)
|
||||
|
||||
if weakTokens:
|
||||
print ('%s Weak token(s) found' % good)
|
||||
for weakToken in weakTokens:
|
||||
url = list(weakToken.keys())[0]
|
||||
token = list(weakToken.values())[0]
|
||||
print ('%s %s %s' % (info, url, token))
|
||||
|
||||
if insecureForms:
|
||||
print ('%s Insecure form(s) found' % good)
|
||||
for insecureForm in insecureForms:
|
||||
url = list(insecureForm.keys())[0]
|
||||
action = list(insecureForm.values())[0]['action']
|
||||
form = action.replace(target, '')
|
||||
if form:
|
||||
print ('%s %s %s[%s%s%s]%s' % (bad, url, green, end, form, green, end))
|
||||
|
||||
with open('./db/hashes.json') as f:
|
||||
hashPatterns = json.load(f)
|
||||
|
||||
aToken = allTokens[0]
|
||||
matches = []
|
||||
for element in hashPatterns:
|
||||
pattern = element['regex']
|
||||
if re.match(pattern, aToken):
|
||||
for name in element['matches']:
|
||||
matches.append(name)
|
||||
if matches:
|
||||
print ('%s Token matches the pattern of following hash type(s):' % info)
|
||||
for name in matches:
|
||||
print (' %s>%s %s' % (yellow, end, name))
|
||||
|
||||
print ('%s Phase: Comparing %s[%s3/5%s]%s' % (run, green, end, green, end))
|
||||
uniqueTokens = set(allTokens)
|
||||
if len(uniqueTokens) < len(allTokens):
|
||||
print ('%s Potential Replay Attack condition found' % good)
|
||||
print ('%s Verifying and looking for the cause' % run)
|
||||
replay = False
|
||||
for url, token in tokenDatabase:
|
||||
for url2, token2 in tokenDatabase:
|
||||
if token == token2 and url != url2:
|
||||
print ('%s The same token was used on %s%s%s and %s%s%s' % (good, green, url, end, green, url2, end))
|
||||
replay = True
|
||||
if not replay:
|
||||
print ('%s Further investigation shows that it was a false positive.')
|
||||
|
||||
def fuzzy(tokens):
|
||||
averages = []
|
||||
for token in tokens:
|
||||
sameTokenRemoved = False
|
||||
result = process.extract(token, tokens, scorer=fuzz.partial_ratio)
|
||||
scores = []
|
||||
for each in result:
|
||||
score = each[1]
|
||||
if score == 100 and not sameTokenRemoved:
|
||||
sameTokenRemoved = True
|
||||
continue
|
||||
scores.append(score)
|
||||
average = statistics.mean(scores)
|
||||
averages.append(average)
|
||||
return statistics.mean(averages)
|
||||
|
||||
try:
|
||||
similarity = fuzzy(allTokens)
|
||||
print ('%s Tokens are %s%i%%%s similar to each other on an average' % (info, green, similarity, end))
|
||||
except statistics.StatisticsError:
|
||||
print ('%s No CSRF protection to test' % bad)
|
||||
quit()
|
||||
|
||||
simTokens = []
|
||||
|
||||
print ('%s Phase: Observing %s[%s4/5%s]%s' % (run, green, end, green, end))
|
||||
print ('%s 100 simultaneous requests are being made, please wait.' % info)
|
||||
|
||||
def extractForms(url):
|
||||
response = requester(url, {}, headers, True, 0).text
|
||||
forms = zetanize(url, response)
|
||||
for each in forms.values():
|
||||
localTokens = set()
|
||||
inputs = each['inputs']
|
||||
for inp in inputs:
|
||||
value = inp['value']
|
||||
if value and match(r'^[\w\-_]+$', value):
|
||||
if entropy(value) > 10:
|
||||
simTokens.append(value)
|
||||
|
||||
while True:
|
||||
sample = random.choice(tokenDatabase)
|
||||
goodToken = list(sample.values())[0]
|
||||
if len(goodToken) > 0:
|
||||
goodCandidate = list(sample.keys())[0]
|
||||
break
|
||||
|
||||
threadpool = concurrent.futures.ThreadPoolExecutor(max_workers=30)
|
||||
futures = (threadpool.submit(extractForms, goodCandidate) for goodCandidate in [goodCandidate] * 30)
|
||||
for i in concurrent.futures.as_completed(futures):
|
||||
pass
|
||||
|
||||
if simTokens:
|
||||
if len(set(simTokens)) < len(simTokens):
|
||||
print ('%s Same tokens were issued for simultaneous requests.' % good)
|
||||
else:
|
||||
print (simTokens)
|
||||
else:
|
||||
print ('%s Different tokens were issued for simultaneous requests.' % info)
|
||||
|
||||
print ('%s Phase: Testing %s[%s5/5%s]%s' % (good, green, end, green, end))
|
||||
|
||||
parsed = ''
|
||||
print ('%s Finding a suitable form for further testing. It may take a while.' % run)
|
||||
for url, forms in allForms[0].items():
|
||||
found = False
|
||||
parsed = datanize(forms, tolerate=True)
|
||||
if parsed:
|
||||
found = True
|
||||
break
|
||||
if found:
|
||||
break
|
||||
|
||||
if not parsed:
|
||||
candidate = list(random.choice(tokenDatabase).keys())[0]
|
||||
parsed = datanize(candidate, headers, tolerate=True)
|
||||
print (parsed)
|
||||
|
||||
origGET = parsed[0]
|
||||
origUrl = parsed[1]
|
||||
origData = parsed[2]
|
||||
|
||||
print ('%s Making a request with CSRF token for comparison.' % run)
|
||||
response = requester(origUrl, origData, headers, origGET, 0)
|
||||
originalCode = response.status_code
|
||||
originalLength = len(response.text)
|
||||
print ('%s Status Code: %s' % (info, originalCode))
|
||||
print ('%s Content Length: %i' % (info, originalLength))
|
||||
print ('%s Checking if the resonse is dynamic.' % run)
|
||||
response = requester(origUrl, origData, headers, origGET, 0)
|
||||
secondLength = len(response.text)
|
||||
if originalLength != secondLength:
|
||||
print ('%s Response is dynamic.' % info)
|
||||
tolerableDifference = abs(originalLength - secondLength)
|
||||
else:
|
||||
print ('%s Response isn\'t dynamic.' % info)
|
||||
tolerableDifference = 0
|
||||
|
||||
print ('%s Emulating a mobile browser' % run)
|
||||
print ('%s Making a request with mobile browser' % run)
|
||||
headers['User-Agent'] = 'Mozilla/4.0 (compatible; MSIE 5.5; Windows CE; PPC; 240x320)'
|
||||
response = requester(origUrl, {}, headers, True, 0).text
|
||||
parsed = zetanize(origUrl, response)
|
||||
if isProtected(parsed):
|
||||
print ('%s CSRF protection is enabled for mobile browsers as well.' % bad)
|
||||
else:
|
||||
print ('%s CSRF protection isn\'t enabled for mobile browsers.' % good)
|
||||
|
||||
print ('%s Making a request without CSRF token parameter.' % run)
|
||||
data = tweaker(origData, 'remove')
|
||||
response = requester(origUrl, data, headers, origGET, 0)
|
||||
if response.status_code == originalCode:
|
||||
if str(originalCode)[0] in ['4', '5']:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
else:
|
||||
difference = abs(originalLength - len(response.text))
|
||||
if difference <= tolerableDifference:
|
||||
print ('%s It worked!' % good)
|
||||
else:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
print ('%s Making a request without CSRF token parameter value.' % run)
|
||||
data = tweaker(origData, 'clear')
|
||||
response = requester(origUrl, data, headers, origGET, 0)
|
||||
if response.status_code == originalCode:
|
||||
if str(originalCode)[0] in ['4', '5']:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
else:
|
||||
difference = abs(originalLength - len(response.text))
|
||||
if difference <= tolerableDifference:
|
||||
print ('%s It worked!' % good)
|
||||
else:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
seeds = ranger(allTokens)
|
||||
print ('%s Generating a fake token.' % run)
|
||||
data = tweaker(origData, 'generate', seeds=seeds)
|
||||
print ('%s Making a request with the self generated token.' % run)
|
||||
response = requester(origUrl, data, headers, origGET, 0)
|
||||
if response.status_code == originalCode:
|
||||
if str(originalCode)[0] in ['4', '5']:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
else:
|
||||
difference = abs(originalLength - len(response.text))
|
||||
if difference <= tolerableDifference:
|
||||
print ('%s It worked!' % good)
|
||||
else:
|
||||
print ('%s It didn\'t work' % bad)
|
||||
|
||||
print ('%s Making requests with various tweaks to the token. It may take a while.' % run)
|
||||
# data = datanize(goodCandidate, headers)[1]
|
||||
# data = tweaker(data, 'remove')
|
||||
# response = requester(origUrl, data, headers, origGET, 0)
|
||||
20
core/colors.py
Normal file
20
core/colors.py
Normal file
@@ -0,0 +1,20 @@
|
||||
import sys
|
||||
|
||||
colors = True # Output should be colored
|
||||
machine = sys.platform # Detecting the os of current system
|
||||
if machine.lower().startswith(('os', 'win', 'darwin', 'ios')):
|
||||
colors = False # Colors shouldn't be displayed in mac & windows
|
||||
if not colors:
|
||||
end = red = white = green = yellow = run = bad = good = info = que = ''
|
||||
else:
|
||||
white = '\033[97m'
|
||||
green = '\033[92m'
|
||||
red = '\033[91m'
|
||||
yellow = '\033[93m'
|
||||
end = '\033[0m'
|
||||
back = '\033[7;91m'
|
||||
info = '\033[93m[!]\033[0m'
|
||||
que = '\033[94m[?]\033[0m'
|
||||
bad = '\033[91m[-]\033[0m'
|
||||
good = '\033[92m[+]\033[0m'
|
||||
run = '\033[97m[~]\033[0m'
|
||||
14
core/config.py
Normal file
14
core/config.py
Normal file
@@ -0,0 +1,14 @@
|
||||
password = 'xXx!69!xXx'
|
||||
email = 'testing@gmail.com'
|
||||
strings = ['red', 'bob', 'admin', 'alex', 'testing', 'test', 'lol', 'yes', 'dragon', 'bad']
|
||||
commonNames = ['csrf', 'auth', 'token', 'verify', 'hash']
|
||||
token = r'^[\w\-_+=/]{14,256}$'
|
||||
|
||||
headers = { # default headers
|
||||
'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
|
||||
'Accept-Language': 'en-US,en;q=0.5',
|
||||
'Accept-Encoding': 'gzip,deflate',
|
||||
'Connection': 'close',
|
||||
'DNT': '1',
|
||||
'Upgrade-Insecure-Requests': '1',
|
||||
}
|
||||
39
core/datanize.py
Normal file
39
core/datanize.py
Normal file
@@ -0,0 +1,39 @@
|
||||
import random
|
||||
import re
|
||||
|
||||
from core.config import password, email, token, strings
|
||||
from core.requester import requester
|
||||
from core.zetanize import zetanize
|
||||
|
||||
def datanize(forms, tolerate=False):
|
||||
parsedForms = list(forms.values())
|
||||
for oneForm in parsedForms:
|
||||
data = {}
|
||||
login = False
|
||||
protected = False
|
||||
action = oneForm['action']
|
||||
method = oneForm['method']
|
||||
inputs = oneForm['inputs']
|
||||
for inp in inputs:
|
||||
name = inp['name']
|
||||
kind = inp['type']
|
||||
value = inp['value']
|
||||
if re.match(token, value):
|
||||
protected = True
|
||||
if kind == 'password':
|
||||
data[name] = password
|
||||
login = True
|
||||
if kind == 'email':
|
||||
data[name] = email
|
||||
if kind == 'text':
|
||||
data[name] = random.choice(strings)
|
||||
else:
|
||||
data[name] = value
|
||||
if method == 'GET':
|
||||
GET = True
|
||||
else:
|
||||
GET = False
|
||||
if protected:
|
||||
if not login or tolerate:
|
||||
return [GET, action, data]
|
||||
return None
|
||||
30
core/evaluate.py
Normal file
30
core/evaluate.py
Normal file
@@ -0,0 +1,30 @@
|
||||
from re import match
|
||||
from core.utils import entropy
|
||||
from core.config import commonNames
|
||||
|
||||
def evaluate(dataset, weakTokens, tokenDatabase, allTokens, insecureForms):
|
||||
done = []
|
||||
for i in dataset:
|
||||
for url, page in i.items():
|
||||
localTokens = set()
|
||||
for each in page.values():
|
||||
protected = False
|
||||
action = each['action']
|
||||
method = each['method']
|
||||
inputs = each['inputs']
|
||||
for inp in inputs:
|
||||
name = inp['name']
|
||||
value = inp['value']
|
||||
if value and match(r'^[\w\-_]+$', value):
|
||||
if entropy(value) > 10:
|
||||
localTokens.add(value)
|
||||
protected = True
|
||||
break
|
||||
elif name.lower() in commonNames:
|
||||
weakTokens.append({url : {name : value}})
|
||||
if not protected and action not in done:
|
||||
done.append(done)
|
||||
insecureForms.append({url : each})
|
||||
for token in localTokens:
|
||||
allTokens.append(token)
|
||||
tokenDatabase.append({url : localTokens})
|
||||
54
core/photon.py
Normal file
54
core/photon.py
Normal file
@@ -0,0 +1,54 @@
|
||||
# Let's import what we need
|
||||
import tld
|
||||
import sys
|
||||
import json
|
||||
from re import findall
|
||||
import concurrent.futures
|
||||
from urllib.parse import urlparse # for python3
|
||||
|
||||
from core.colors import run
|
||||
from core.zetanize import zetanize
|
||||
from core.requester import requester
|
||||
from core.utils import getUrl, getParams
|
||||
|
||||
def photon(seedUrl, headers, depth, threadCount):
|
||||
forms = [] # web forms
|
||||
processed = set() # urls that have been crawled
|
||||
storage = set() # urls that belong to the target i.e. in-scope
|
||||
scheme = urlparse(seedUrl).scheme
|
||||
host = urlparse(seedUrl).netloc
|
||||
main_url = scheme + '://' + host
|
||||
storage.add(seedUrl)
|
||||
def rec(url):
|
||||
processed.add(url)
|
||||
urlPrint = (url + (' ' * 60))[:60]
|
||||
print ('%s Parsing %-40s' % (run, urlPrint), end='\r')
|
||||
url = getUrl(url, '', True)
|
||||
params = getParams(url, '', True)
|
||||
if '=' in url:
|
||||
inps = []
|
||||
for name, value in params.items():
|
||||
inps.append({'name': name, 'value': value})
|
||||
forms.append({url : {0: {'action': url, 'method': 'get', 'inputs': inps}}})
|
||||
response = requester(url, params, headers, True, 0).text
|
||||
forms.append({url : zetanize(url, response)})
|
||||
matches = findall(r'<[aA].*href=["\']{0,1}(.*?)["\']', response)
|
||||
for link in matches: # iterate over the matches
|
||||
link = link.split('#')[0].lstrip(' ') # remove everything after a "#" to deal with in-page anchors
|
||||
if link[:4] == 'http':
|
||||
if link.startswith(main_url):
|
||||
storage.add(link)
|
||||
elif link[:2] == '//':
|
||||
if link.split('/')[2].startswith(host):
|
||||
storage.add(schema + link)
|
||||
elif link[:1] == '/':
|
||||
storage.add(main_url + link)
|
||||
else:
|
||||
storage.add(main_url + '/' + link)
|
||||
for x in range(depth):
|
||||
urls = storage - processed
|
||||
threadpool = concurrent.futures.ThreadPoolExecutor(max_workers=10)
|
||||
futures = (threadpool.submit(rec, url) for url in urls)
|
||||
for i in concurrent.futures.as_completed(futures):
|
||||
pass
|
||||
return [forms, len(processed)]
|
||||
19
core/prompt.py
Normal file
19
core/prompt.py
Normal file
@@ -0,0 +1,19 @@
|
||||
import os
|
||||
import tempfile
|
||||
|
||||
def prompt(default=None):
|
||||
editor = 'nano'
|
||||
with tempfile.NamedTemporaryFile(mode='r+') as tmpfile:
|
||||
if default:
|
||||
tmpfile.write(default)
|
||||
tmpfile.flush()
|
||||
|
||||
child_pid = os.fork()
|
||||
is_child = child_pid == 0
|
||||
|
||||
if is_child:
|
||||
os.execvp(editor, [editor, tmpfile.name])
|
||||
else:
|
||||
os.waitpid(child_pid, 0)
|
||||
tmpfile.seek(0)
|
||||
return tmpfile.read().strip()
|
||||
10
core/ranger.py
Normal file
10
core/ranger.py
Normal file
@@ -0,0 +1,10 @@
|
||||
def ranger(tokens):
|
||||
digits = set()
|
||||
alphabets = set()
|
||||
for token in tokens:
|
||||
for char in token:
|
||||
if char in '0123456789':
|
||||
digits.add(char)
|
||||
elif char in 'abcdefghijklmnopqrstuvwxyz':
|
||||
alphabets.add(char)
|
||||
return [list(digits), list(alphabets)]
|
||||
20
core/requester.py
Normal file
20
core/requester.py
Normal file
@@ -0,0 +1,20 @@
|
||||
import time
|
||||
import random
|
||||
import warnings
|
||||
import requests
|
||||
|
||||
warnings.filterwarnings('ignore') # Disable SSL related warnings
|
||||
|
||||
def requester(url, data, headers, GET, delay):
|
||||
time.sleep(delay)
|
||||
user_agents = ['Mozilla/5.0 (X11; Linux i686; rv:60.0) Gecko/20100101 Firefox/60.0',
|
||||
'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.113 Safari/537.36'
|
||||
'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Safari/537.36 OPR/43.0.2442.991']
|
||||
if headers:
|
||||
if 'User-Agent' not in headers:
|
||||
headers['User-Agent'] = random.choice(user_agents)
|
||||
if GET:
|
||||
response = requests.get(url, params=data, headers=headers, verify=False)
|
||||
else:
|
||||
response = requests.post(url, data=data, headers=headers, verify=False)
|
||||
return response
|
||||
38
core/tweaker.py
Normal file
38
core/tweaker.py
Normal file
@@ -0,0 +1,38 @@
|
||||
from core.config import token
|
||||
import random
|
||||
import re
|
||||
|
||||
def tweaker(data, strategy, index=0, seeds=[None, None]):
|
||||
newData = {}
|
||||
if strategy == 'clear':
|
||||
for name, value in data.items():
|
||||
if re.match(token, value):
|
||||
value = ''
|
||||
newData[name] = value
|
||||
return newData
|
||||
elif strategy == 'remove':
|
||||
for name, value in data.items():
|
||||
if not re.match(token, value):
|
||||
newData[name] = value
|
||||
elif strategy == 'break':
|
||||
for name, value in data.items():
|
||||
if re.match(token, value):
|
||||
value = value[:-index]
|
||||
newData[name] = value
|
||||
elif strategy == 'generate':
|
||||
digits = seeds[0]
|
||||
alphabets = seeds[1]
|
||||
for name, value in data.items():
|
||||
if re.match(token, value):
|
||||
newToken = ''
|
||||
for char in list(value):
|
||||
if char in digits:
|
||||
newToken += random.choice(digits)
|
||||
elif char in alphabets:
|
||||
newToken += random.choice(alphabets)
|
||||
else:
|
||||
newToken += char
|
||||
newData[name] = newToken
|
||||
else:
|
||||
newData[name] = value
|
||||
return newData
|
||||
62
core/utils.py
Normal file
62
core/utils.py
Normal file
@@ -0,0 +1,62 @@
|
||||
import re
|
||||
from core.config import token
|
||||
|
||||
def entropy(string):
|
||||
digits = re.findall(r'\d', string)
|
||||
lowerAlphas = re.findall(r'[a-z]', string)
|
||||
upperAlphas = re.findall(r'[A-Z]', string)
|
||||
entropy = len(set(digits + lowerAlphas + upperAlphas))
|
||||
if not digits:
|
||||
entropy = entropy/2
|
||||
return entropy
|
||||
|
||||
def isProtected(parsed):
|
||||
protected = False
|
||||
parsedForms = list(parsed.values())
|
||||
for oneForm in parsedForms:
|
||||
inputs = oneForm['inputs']
|
||||
for inp in inputs:
|
||||
name = inp['name']
|
||||
kind = inp['type']
|
||||
value = inp['value']
|
||||
if re.match(token, value):
|
||||
protected = True
|
||||
return protected
|
||||
|
||||
def extractHeaders(headers):
|
||||
sorted_headers = {}
|
||||
matches = re.findall(r'(.*):\s(.*)', headers)
|
||||
for match in matches:
|
||||
header = match[0]
|
||||
value = match[1]
|
||||
try:
|
||||
if value[-1] == ',':
|
||||
value = value[:-1]
|
||||
sorted_headers[header] = value
|
||||
except IndexError:
|
||||
pass
|
||||
return sorted_headers
|
||||
|
||||
def getUrl(url, data, GET):
|
||||
if GET:
|
||||
return url.split('?')[0]
|
||||
else:
|
||||
return url
|
||||
|
||||
def getParams(url, data, GET):
|
||||
params = {}
|
||||
if GET:
|
||||
if '=' in url:
|
||||
data = url.split('?')[1]
|
||||
if data[:1] == '?':
|
||||
data = data[1:]
|
||||
else:
|
||||
data = ''
|
||||
parts = data.split('&')
|
||||
for part in parts:
|
||||
each = part.split('=')
|
||||
try:
|
||||
params[each[0]] = each[1]
|
||||
except IndexError:
|
||||
params = None
|
||||
return params
|
||||
48
core/zetanize.py
Normal file
48
core/zetanize.py
Normal file
@@ -0,0 +1,48 @@
|
||||
import re
|
||||
from urllib.parse import urlparse
|
||||
|
||||
def zetanize(url, response):
|
||||
parsedUrl = urlparse(url)
|
||||
mainUrl = parsedUrl.scheme + '://' + parsedUrl.netloc
|
||||
def e(string):
|
||||
return string.encode('utf-8')
|
||||
|
||||
def d(string):
|
||||
return string.decode('utf-8')
|
||||
|
||||
response = re.sub(r'(?s)<!--.*?-->', '', response)
|
||||
forms = {}
|
||||
matches = re.findall(r'(?i)(?s)<form.*?</form.*?>', response)
|
||||
num = 0
|
||||
for match in matches:
|
||||
page = re.search(r'(?i)action=[\'"](.*?)[\'"]', match)
|
||||
method = re.search(r'(?i)method=[\'"](.*?)[\'"]', match)
|
||||
forms[num] = {}
|
||||
action = d(e(page.group(1)))
|
||||
if not action.startswith('http'):
|
||||
if action.startswith('/'):
|
||||
action = mainUrl + action
|
||||
else:
|
||||
action = mainUrl + '/' + action
|
||||
forms[num]['action'] = action.replace('&', '&') if page else ''
|
||||
forms[num]['method'] = d(e(method.group(1)).lower()) if method else 'get'
|
||||
forms[num]['inputs'] = []
|
||||
inputs = re.findall(r'(?i)(?s)<input.*?>', response)
|
||||
for inp in inputs:
|
||||
inpName = re.search(r'(?i)name=[\'"](.*?)[\'"]', inp)
|
||||
if inpName:
|
||||
inpType = re.search(r'(?i)type=[\'"](.*?)[\'"]', inp)
|
||||
inpValue = re.search(r'(?i)value=[\'"](.*?)[\'"]', inp)
|
||||
inpName = d(e(inpName.group(1)))
|
||||
inpType = d(e(inpType.group(1)) )if inpType else ''
|
||||
inpValue = d(e(inpValue.group(1))) if inpValue else ''
|
||||
if inpType.lower() == 'submit' and inpValue == '':
|
||||
inpValue = 'Submit Query'
|
||||
inpDict = {
|
||||
'name' : inpName,
|
||||
'type' : inpType,
|
||||
'value' : inpValue
|
||||
}
|
||||
forms[num]['inputs'].append(inpDict)
|
||||
num += 1
|
||||
return forms
|
||||
999
db/hashes.json
Normal file
999
db/hashes.json
Normal file
@@ -0,0 +1,999 @@
|
||||
[
|
||||
{
|
||||
"regex": "^[a-f0-9]{4}$",
|
||||
"matches": [
|
||||
"CRC-16",
|
||||
"CRC-16-CCITT",
|
||||
"FCS-16"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{8}$",
|
||||
"matches": [
|
||||
"Adler-32",
|
||||
"CRC-32B",
|
||||
"FCS-32",
|
||||
"GHash-32-3",
|
||||
"GHash-32-5",
|
||||
"FNV-132",
|
||||
"Fletcher-32",
|
||||
"Joaat",
|
||||
"ELF-32",
|
||||
"XOR-32"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{6}$",
|
||||
"matches": [
|
||||
"CRC-24"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$crc32\\$[a-f0-9]{8}.)?[a-f0-9]{8}$",
|
||||
"matches": [
|
||||
"CRC-32"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\+[a-z0-9\\/.]{12}$",
|
||||
"matches": [
|
||||
"Eggdrop IRC Bot"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/.]{13}$",
|
||||
"matches": [
|
||||
"DES(Unix)",
|
||||
"Traditional DES",
|
||||
"DEScrypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{16}$",
|
||||
"matches": [
|
||||
"MySQL323",
|
||||
"DES(Oracle)",
|
||||
"Half MD5",
|
||||
"Oracle 7-10g",
|
||||
"FNV-164",
|
||||
"CRC-64"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/.]{16}$",
|
||||
"matches": [
|
||||
"Cisco-PIX(MD5)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\([a-z0-9\\/+]{20}\\)$",
|
||||
"matches": [
|
||||
"Lotus Notes/Domino 6"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^_[a-z0-9\\/.]{19}$",
|
||||
"matches": [
|
||||
"BSDi Crypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{24}$",
|
||||
"matches": [
|
||||
"CRC-96(ZIP)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/.]{24}$",
|
||||
"matches": [
|
||||
"Crypt16"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$md2\\$)?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"MD2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}(:.+)?$",
|
||||
"matches": [
|
||||
"MD5",
|
||||
"MD4",
|
||||
"Double MD5",
|
||||
"LM",
|
||||
"RIPEMD-128",
|
||||
"Haval-128",
|
||||
"Tiger-128",
|
||||
"Skein-256(128)",
|
||||
"Skein-512(128)",
|
||||
"Lotus Notes/Domino 5",
|
||||
"Skype",
|
||||
"ZipMonster",
|
||||
"PrestaShop",
|
||||
"md5(md5(md5($pass)))",
|
||||
"md5(strtoupper(md5($pass)))",
|
||||
"md5(sha1($pass))",
|
||||
"md5($pass.$salt)",
|
||||
"md5($salt.$pass)",
|
||||
"md5(unicode($pass).$salt)",
|
||||
"md5($salt.unicode($pass))",
|
||||
"HMAC-MD5 (key = $pass)",
|
||||
"HMAC-MD5 (key = $salt)",
|
||||
"md5(md5($salt).$pass)",
|
||||
"md5($salt.md5($pass))",
|
||||
"md5($pass.md5($salt))",
|
||||
"md5($salt.$pass.$salt)",
|
||||
"md5(md5($pass).md5($salt))",
|
||||
"md5($salt.md5($salt.$pass))",
|
||||
"md5($salt.md5($pass.$salt))",
|
||||
"md5($username.0.$pass)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$snefru\\$)?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"Snefru-128"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$NT\\$)?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"NTLM"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^([^\\\\\\/:*?\"<>|]{1,20}:)?[a-f0-9]{32}(:[^\\\\\\/:*?\"<>|]{1,20})?$",
|
||||
"matches": [
|
||||
"Domain Cached Credentials"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^([^\\\\\\/:*?\"<>|]{1,20}:)?(\\$DCC2\\$10240#[^\\\\\\/:*?\"<>|]{1,20}#)?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"Domain Cached Credentials 2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{SHA}[a-z0-9\\/+]{27}=$",
|
||||
"matches": [
|
||||
"SHA-1(Base64)",
|
||||
"Netscape LDAP SHA"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$1\\$[a-z0-9\\/.]{0,8}\\$[a-z0-9\\/.]{22}(:.*)?$",
|
||||
"matches": [
|
||||
"MD5 Crypt",
|
||||
"Cisco-IOS(MD5)",
|
||||
"FreeBSD MD5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"Lineage II C4"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$H\\$[a-z0-9\\/.]{31}$",
|
||||
"matches": [
|
||||
"phpBB v3.x",
|
||||
"Wordpress v2.6.0/2.6.1",
|
||||
"PHPass' Portable Hash"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$P\\$[a-z0-9\\/.]{31}$",
|
||||
"matches": [
|
||||
"Wordpress \u2265 v2.6.2",
|
||||
"Joomla \u2265 v2.5.18",
|
||||
"PHPass' Portable Hash"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:[a-z0-9]{2}$",
|
||||
"matches": [
|
||||
"osCommerce",
|
||||
"xt:Commerce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$apr1\\$[a-z0-9\\/.]{0,8}\\$[a-z0-9\\/.]{22}$",
|
||||
"matches": [
|
||||
"MD5(APR)",
|
||||
"Apache MD5",
|
||||
"md5apr1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{smd5}[a-z0-9$\\/.]{31}$",
|
||||
"matches": [
|
||||
"AIX(smd5)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"WebEdition CMS"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:.{5}$",
|
||||
"matches": [
|
||||
"IP.Board \u2265 v2+"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:.{8}$",
|
||||
"matches": [
|
||||
"MyBB \u2265 v1.2+"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9]{34}$",
|
||||
"matches": [
|
||||
"CryptoCurrency(Adress)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{40}(:.+)?$",
|
||||
"matches": [
|
||||
"SHA-1",
|
||||
"Double SHA-1",
|
||||
"RIPEMD-160",
|
||||
"Haval-160",
|
||||
"Tiger-160",
|
||||
"HAS-160",
|
||||
"LinkedIn",
|
||||
"Skein-256(160)",
|
||||
"Skein-512(160)",
|
||||
"MangosWeb Enhanced CMS",
|
||||
"sha1(sha1(sha1($pass)))",
|
||||
"sha1(md5($pass))",
|
||||
"sha1($pass.$salt)",
|
||||
"sha1($salt.$pass)",
|
||||
"sha1(unicode($pass).$salt)",
|
||||
"sha1($salt.unicode($pass))",
|
||||
"HMAC-SHA1 (key = $pass)",
|
||||
"HMAC-SHA1 (key = $salt)",
|
||||
"sha1($salt.$pass.$salt)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\*[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"MySQL5.x",
|
||||
"MySQL4.1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9]{43}$",
|
||||
"matches": [
|
||||
"Cisco-IOS(SHA-256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{SSHA}[a-z0-9\\/+]{38}==$",
|
||||
"matches": [
|
||||
"SSHA-1(Base64)",
|
||||
"Netscape LDAP SSHA",
|
||||
"nsldaps"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9=]{47}$",
|
||||
"matches": [
|
||||
"Fortigate(FortiOS)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{48}$",
|
||||
"matches": [
|
||||
"Haval-192",
|
||||
"Tiger-192",
|
||||
"SHA-1(Oracle)",
|
||||
"OSX v10.4",
|
||||
"OSX v10.5",
|
||||
"OSX v10.6"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{51}$",
|
||||
"matches": [
|
||||
"Palshop CMS"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9]{51}$",
|
||||
"matches": [
|
||||
"CryptoCurrency(PrivateKey)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{ssha1}[0-9]{2}\\$[a-z0-9$\\/.]{44}$",
|
||||
"matches": [
|
||||
"AIX(ssha1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x0100[a-f0-9]{48}$",
|
||||
"matches": [
|
||||
"MSSQL(2005)",
|
||||
"MSSQL(2008)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$md5,rounds=[0-9]+\\$|\\$md5\\$rounds=[0-9]+\\$|\\$md5\\$)[a-z0-9\\/.]{0,16}(\\$|\\$\\$)[a-z0-9\\/.]{22}$",
|
||||
"matches": [
|
||||
"Sun MD5 Crypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{56}$",
|
||||
"matches": [
|
||||
"SHA-224",
|
||||
"Haval-224",
|
||||
"SHA3-224",
|
||||
"Skein-256(224)",
|
||||
"Skein-512(224)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$2[axy]|\\$2)\\$[0-9]{2}\\$[a-z0-9\\/.]{53}$",
|
||||
"matches": [
|
||||
"Blowfish(OpenBSD)",
|
||||
"Woltlab Burning Board 4.x",
|
||||
"bcrypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{40}:[a-f0-9]{16}$",
|
||||
"matches": [
|
||||
"Android PIN"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(S:)?[a-f0-9]{40}(:)?[a-f0-9]{20}$",
|
||||
"matches": [
|
||||
"Oracle 11g/12c"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$bcrypt-sha256\\$(2[axy]|2)\\,[0-9]+\\$[a-z0-9\\/.]{22}\\$[a-z0-9\\/.]{31}$",
|
||||
"matches": [
|
||||
"bcrypt(SHA-256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:.{3}$",
|
||||
"matches": [
|
||||
"vBulletin < v3.8.5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:.{30}$",
|
||||
"matches": [
|
||||
"vBulletin \u2265 v3.8.5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$snefru\\$)?[a-f0-9]{64}$",
|
||||
"matches": [
|
||||
"Snefru-256"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{64}(:.+)?$",
|
||||
"matches": [
|
||||
"SHA-256",
|
||||
"RIPEMD-256",
|
||||
"Haval-256",
|
||||
"GOST R 34.11-94",
|
||||
"GOST CryptoPro S-Box",
|
||||
"SHA3-256",
|
||||
"Skein-256",
|
||||
"Skein-512(256)",
|
||||
"Ventrilo",
|
||||
"sha256($pass.$salt)",
|
||||
"sha256($salt.$pass)",
|
||||
"sha256(unicode($pass).$salt)",
|
||||
"sha256($salt.unicode($pass))",
|
||||
"HMAC-SHA256 (key = $pass)",
|
||||
"HMAC-SHA256 (key = $salt)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:[a-z0-9]{32}$",
|
||||
"matches": [
|
||||
"Joomla < v2.5.18"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f-0-9]{32}:[a-f-0-9]{32}$",
|
||||
"matches": [
|
||||
"SAM(LM_Hash:NT_Hash)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$chap\\$0\\*)?[a-f0-9]{32}[\\*:][a-f0-9]{32}(:[0-9]{2})?$",
|
||||
"matches": [
|
||||
"MD5(Chap)",
|
||||
"iSCSI CHAP Authentication"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$episerver\\$\\*0\\*[a-z0-9\\/=+]+\\*[a-z0-9\\/=+]{27,28}$",
|
||||
"matches": [
|
||||
"EPiServer 6.x < v4"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{ssha256}[0-9]{2}\\$[a-z0-9$\\/.]{60}$",
|
||||
"matches": [
|
||||
"AIX(ssha256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{80}$",
|
||||
"matches": [
|
||||
"RIPEMD-320"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$episerver\\$\\*1\\*[a-z0-9\\/=+]+\\*[a-z0-9\\/=+]{42,43}$",
|
||||
"matches": [
|
||||
"EPiServer 6.x \u2265 v4"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x0100[a-f0-9]{88}$",
|
||||
"matches": [
|
||||
"MSSQL(2000)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{96}$",
|
||||
"matches": [
|
||||
"SHA-384",
|
||||
"SHA3-384",
|
||||
"Skein-512(384)",
|
||||
"Skein-1024(384)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{SSHA512}[a-z0-9\\/+]{96}$",
|
||||
"matches": [
|
||||
"SSHA-512(Base64)",
|
||||
"LDAP(SSHA-512)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{ssha512}[0-9]{2}\\$[a-z0-9\\/.]{16,48}\\$[a-z0-9\\/.]{86}$",
|
||||
"matches": [
|
||||
"AIX(ssha512)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{128}(:.+)?$",
|
||||
"matches": [
|
||||
"SHA-512",
|
||||
"Whirlpool",
|
||||
"Salsa10",
|
||||
"Salsa20",
|
||||
"SHA3-512",
|
||||
"Skein-512",
|
||||
"Skein-1024(512)",
|
||||
"sha512($pass.$salt)",
|
||||
"sha512($salt.$pass)",
|
||||
"sha512(unicode($pass).$salt)",
|
||||
"sha512($salt.unicode($pass))",
|
||||
"HMAC-SHA512 (key = $pass)",
|
||||
"HMAC-SHA512 (key = $salt)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{136}$",
|
||||
"matches": [
|
||||
"OSX v10.7"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x0200[a-f0-9]{136}$",
|
||||
"matches": [
|
||||
"MSSQL(2012)",
|
||||
"MSSQL(2014)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$ml\\$[0-9]+\\$[a-f0-9]{64}\\$[a-f0-9]{128}$",
|
||||
"matches": [
|
||||
"OSX v10.8",
|
||||
"OSX v10.9"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{256}$",
|
||||
"matches": [
|
||||
"Skein-1024"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^grub\\.pbkdf2\\.sha512\\.[0-9]+\\.([a-f0-9]{128,2048}\\.|[0-9]+\\.)?[a-f0-9]{128}$",
|
||||
"matches": [
|
||||
"GRUB 2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^sha1\\$[a-z0-9]+\\$[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"Django(SHA-1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{49}$",
|
||||
"matches": [
|
||||
"Citrix Netscaler"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$S\\$[a-z0-9\\/.]{52}$",
|
||||
"matches": [
|
||||
"Drupal > v7.x"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$5\\$(rounds=[0-9]+\\$)?[a-z0-9\\/.]{0,16}\\$[a-z0-9\\/.]{43}$",
|
||||
"matches": [
|
||||
"SHA-256 Crypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x[a-f0-9]{4}[a-f0-9]{16}[a-f0-9]{64}$",
|
||||
"matches": [
|
||||
"Sybase ASE"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$6\\$(rounds=[0-9]+\\$)?[a-z0-9\\/.]{0,16}\\$[a-z0-9\\/.]{86}$",
|
||||
"matches": [
|
||||
"SHA-512 Crypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$sha\\$[a-z0-9]{1,16}\\$([a-f0-9]{32}|[a-f0-9]{40}|[a-f0-9]{64}|[a-f0-9]{128}|[a-f0-9]{140})$",
|
||||
"matches": [
|
||||
"Minecraft(AuthMe Reloaded)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^sha256\\$[a-z0-9]+\\$[a-f0-9]{64}$",
|
||||
"matches": [
|
||||
"Django(SHA-256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^sha384\\$[a-z0-9]+\\$[a-f0-9]{96}$",
|
||||
"matches": [
|
||||
"Django(SHA-384)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^crypt1:[a-z0-9+=]{12}:[a-z0-9+=]{12}$",
|
||||
"matches": [
|
||||
"Clavister Secure Gateway"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{112}$",
|
||||
"matches": [
|
||||
"Cisco VPN Client(PCF-File)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{1329}$",
|
||||
"matches": [
|
||||
"Microsoft MSTSC(RDP-File)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[^\\\\\\/:*?\"<>|]{1,20}[:]{2,3}([^\\\\\\/:*?\"<>|]{1,20})?:[a-f0-9]{48}:[a-f0-9]{48}:[a-f0-9]{16}$",
|
||||
"matches": [
|
||||
"NetNTLMv1-VANILLA / NetNTLMv1+ESS"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^([^\\\\\\/:*?\"<>|]{1,20}\\\\)?[^\\\\\\/:*?\"<>|]{1,20}[:]{2,3}([^\\\\\\/:*?\"<>|]{1,20}:)?[^\\\\\\/:*?\"<>|]{1,20}:[a-f0-9]{32}:[a-f0-9]+$",
|
||||
"matches": [
|
||||
"NetNTLMv2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$(krb5pa|mskrb5)\\$([0-9]{2})?\\$.+\\$[a-f0-9]{1,}$",
|
||||
"matches": [
|
||||
"Kerberos 5 AS-REQ Pre-Auth"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$scram\\$[0-9]+\\$[a-z0-9\\/.]{16}\\$sha-1=[a-z0-9\\/.]{27},sha-256=[a-z0-9\\/.]{43},sha-512=[a-z0-9\\/.]{86}$",
|
||||
"matches": [
|
||||
"SCRAM Hash"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{40}:[a-f0-9]{0,32}$",
|
||||
"matches": [
|
||||
"Redmine Project Management Web App"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(.+)?\\$[a-f0-9]{16}$",
|
||||
"matches": [
|
||||
"SAP CODVN B (BCODE)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(.+)?\\$[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"SAP CODVN F/G (PASSCODE)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(.+\\$)?[a-z0-9\\/.+]{30}(:.+)?$",
|
||||
"matches": [
|
||||
"Juniper Netscreen/SSG(ScreenOS)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^0x[a-f0-9]{60}\\s0x[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"EPi"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{40}:[^*]{1,25}$",
|
||||
"matches": [
|
||||
"SMF \u2265 v1.1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$wbb3\\$\\*1\\*)?[a-f0-9]{40}[:*][a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"Woltlab Burning Board 3.x"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{130}(:[a-f0-9]{40})?$",
|
||||
"matches": [
|
||||
"IPMI2 RAKP HMAC-SHA1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{32}:[0-9]+:[a-z0-9_.+-]+@[a-z0-9-]+\\.[a-z0-9-.]+$",
|
||||
"matches": [
|
||||
"Lastpass"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/.]{16}([:$].{1,})?$",
|
||||
"matches": [
|
||||
"Cisco-ASA(MD5)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$vnc\\$\\*[a-f0-9]{32}\\*[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"VNC"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9]{32}(:([a-z0-9-]+\\.)?[a-z0-9-.]+\\.[a-z]{2,7}:.+:[0-9]+)?$",
|
||||
"matches": [
|
||||
"DNSSEC(NSEC3)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(user-.+:)?\\$racf\\$\\*.+\\*[a-f0-9]{16}$",
|
||||
"matches": [
|
||||
"RACF"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$3\\$\\$[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"NTHash(FreeBSD Variant)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$sha1\\$[0-9]+\\$[a-z0-9\\/.]{0,64}\\$[a-z0-9\\/.]{28}$",
|
||||
"matches": [
|
||||
"SHA-1 Crypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{70}$",
|
||||
"matches": [
|
||||
"hMailServer"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[:\\$][AB][:\\$]([a-f0-9]{1,8}[:\\$])?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"MediaWiki"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{140}$",
|
||||
"matches": [
|
||||
"Minecraft(xAuth)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$pbkdf2(-sha1)?\\$[0-9]+\\$[a-z0-9\\/.]+\\$[a-z0-9\\/.]{27}$",
|
||||
"matches": [
|
||||
"PBKDF2-SHA1(Generic)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$pbkdf2-sha256\\$[0-9]+\\$[a-z0-9\\/.]+\\$[a-z0-9\\/.]{43}$",
|
||||
"matches": [
|
||||
"PBKDF2-SHA256(Generic)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$pbkdf2-sha512\\$[0-9]+\\$[a-z0-9\\/.]+\\$[a-z0-9\\/.]{86}$",
|
||||
"matches": [
|
||||
"PBKDF2-SHA512(Generic)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$p5k2\\$[0-9]+\\$[a-z0-9\\/+=-]+\\$[a-z0-9\\/+-]{27}=$",
|
||||
"matches": [
|
||||
"PBKDF2(Cryptacular)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$p5k2\\$[0-9]+\\$[a-z0-9\\/.]+\\$[a-z0-9\\/.]{32}$",
|
||||
"matches": [
|
||||
"PBKDF2(Dwayne Litzenberger)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{FSHP[0123]\\|[0-9]+\\|[0-9]+}[a-z0-9\\/+=]+$",
|
||||
"matches": [
|
||||
"Fairly Secure Hashed Password"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$PHPS\\$.+\\$[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"PHPS"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[0-9]{4}:[a-f0-9]{16}:[a-f0-9]{2080}$",
|
||||
"matches": [
|
||||
"1Password(Agile Keychain)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{64}:[a-f0-9]{32}:[0-9]{5}:[a-f0-9]{608}$",
|
||||
"matches": [
|
||||
"1Password(Cloud Keychain)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{256}:[a-f0-9]{256}:[a-f0-9]{16}:[a-f0-9]{16}:[a-f0-9]{320}:[a-f0-9]{16}:[a-f0-9]{40}:[a-f0-9]{40}:[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"IKE-PSK MD5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{256}:[a-f0-9]{256}:[a-f0-9]{16}:[a-f0-9]{16}:[a-f0-9]{320}:[a-f0-9]{16}:[a-f0-9]{40}:[a-f0-9]{40}:[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"IKE-PSK SHA1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/+]{27}=$",
|
||||
"matches": [
|
||||
"PeopleSoft"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^crypt\\$[a-f0-9]{5}\\$[a-z0-9\\/.]{13}$",
|
||||
"matches": [
|
||||
"Django(DES Crypt Wrapper)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$django\\$\\*1\\*)?pbkdf2_sha256\\$[0-9]+\\$[a-z0-9]+\\$[a-z0-9\\/+=]{44}$",
|
||||
"matches": [
|
||||
"Django(PBKDF2-HMAC-SHA256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^pbkdf2_sha1\\$[0-9]+\\$[a-z0-9]+\\$[a-z0-9\\/+=]{28}$",
|
||||
"matches": [
|
||||
"Django(PBKDF2-HMAC-SHA1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^bcrypt(\\$2[axy]|\\$2)\\$[0-9]{2}\\$[a-z0-9\\/.]{53}$",
|
||||
"matches": [
|
||||
"Django(bcrypt)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^md5\\$[a-f0-9]+\\$[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"Django(MD5)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\{PKCS5S2\\}[a-z0-9\\/+]{64}$",
|
||||
"matches": [
|
||||
"PBKDF2(Atlassian)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^md5[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"PostgreSQL MD5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\([a-z0-9\\/+]{49}\\)$",
|
||||
"matches": [
|
||||
"Lotus Notes/Domino 8"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^SCRYPT:[0-9]{1,}:[0-9]{1}:[0-9]{1}:[a-z0-9:\\/+=]{1,}$",
|
||||
"matches": [
|
||||
"scrypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$8\\$[a-z0-9\\/.]{14}\\$[a-z0-9\\/.]{43}$",
|
||||
"matches": [
|
||||
"Cisco Type 8"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$9\\$[a-z0-9\\/.]{14}\\$[a-z0-9\\/.]{43}$",
|
||||
"matches": [
|
||||
"Cisco Type 9"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$office\\$\\*2007\\*[0-9]{2}\\*[0-9]{3}\\*[0-9]{2}\\*[a-z0-9]{32}\\*[a-z0-9]{32}\\*[a-z0-9]{40}$",
|
||||
"matches": [
|
||||
"Microsoft Office 2007"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$office\\$\\*2010\\*[0-9]{6}\\*[0-9]{3}\\*[0-9]{2}\\*[a-z0-9]{32}\\*[a-z0-9]{32}\\*[a-z0-9]{64}$",
|
||||
"matches": [
|
||||
"Microsoft Office 2010"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$office\\$\\*2013\\*[0-9]{6}\\*[0-9]{3}\\*[0-9]{2}\\*[a-z0-9]{32}\\*[a-z0-9]{32}\\*[a-z0-9]{64}$",
|
||||
"matches": [
|
||||
"Microsoft Office 2013"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$fde\\$[0-9]{2}\\$[a-f0-9]{32}\\$[0-9]{2}\\$[a-f0-9]{32}\\$[a-f0-9]{3072}$",
|
||||
"matches": [
|
||||
"Android FDE \u2264 4.3"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$oldoffice\\$[01]\\*[a-f0-9]{32}\\*[a-f0-9]{32}\\*[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"Microsoft Office \u2264 2003 (MD5+RC4)",
|
||||
"Microsoft Office \u2264 2003 (MD5+RC4) collider-mode #1",
|
||||
"Microsoft Office \u2264 2003 (MD5+RC4) collider-mode #2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$oldoffice\\$[34]\\*[a-f0-9]{32}\\*[a-f0-9]{32}\\*[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"Microsoft Office \u2264 2003 (SHA1+RC4)",
|
||||
"Microsoft Office \u2264 2003 (SHA1+RC4) collider-mode #1",
|
||||
"Microsoft Office \u2264 2003 (SHA1+RC4) collider-mode #2"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$radmin2\\$)?[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"RAdmin v2.x"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^{x-issha,\\s[0-9]{4}}[a-z0-9\\/+=]+$",
|
||||
"matches": [
|
||||
"SAP CODVN H (PWDSALTEDHASH) iSSHA-1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$cram_md5\\$[a-z0-9\\/+=-]+\\$[a-z0-9\\/+=-]{52}$",
|
||||
"matches": [
|
||||
"CRAM-MD5"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{16}:2:4:[a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"SipHash"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-f0-9]{4,}$",
|
||||
"matches": [
|
||||
"Cisco Type 7"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^[a-z0-9\\/.]{13,}$",
|
||||
"matches": [
|
||||
"BigCrypt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$cisco4\\$)?[a-z0-9\\/.]{43}$",
|
||||
"matches": [
|
||||
"Cisco Type 4"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^bcrypt_sha256\\$\\$(2[axy]|2)\\$[0-9]+\\$[a-z0-9\\/.]{53}$",
|
||||
"matches": [
|
||||
"Django(bcrypt-SHA256)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$postgres\\$.[^\\*]+[*:][a-f0-9]{1,32}[*:][a-f0-9]{32}$",
|
||||
"matches": [
|
||||
"PostgreSQL Challenge-Response Authentication (MD5)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$siemens-s7\\$[0-9]{1}\\$[a-f0-9]{40}\\$[a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"Siemens-S7"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$pst\\$)?[a-f0-9]{8}$",
|
||||
"matches": [
|
||||
"Microsoft Outlook PST"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^sha256[:$][0-9]+[:$][a-z0-9\\/+]+[:$][a-z0-9\\/+]{32,128}$",
|
||||
"matches": [
|
||||
"PBKDF2-HMAC-SHA256(PHP)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^(\\$dahua\\$)?[a-z0-9]{8}$",
|
||||
"matches": [
|
||||
"Dahua"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$mysqlna\\$[a-f0-9]{40}[:*][a-f0-9]{40}$",
|
||||
"matches": [
|
||||
"MySQL Challenge-Response Authentication (SHA1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"regex": "^\\$pdf\\$[24]\\*[34]\\*128\\*[0-9-]{1,5}\\*1\\*(16|32)\\*[a-f0-9]{32,64}\\*32\\*[a-f0-9]{64}\\*(8|16|32)\\*[a-f0-9]{16,64}$",
|
||||
"matches": [
|
||||
"PDF 1.4 - 1.6 (Acrobat 5 - 8)"
|
||||
]
|
||||
}
|
||||
]
|
||||
Reference in New Issue
Block a user