def add_action(self): """ Action add of module """ self.validate_main() pData = Registry().get('pData') name = self.options['host'].value descr = self.options['descr'].value if self.options['ip'].value: ip = self.options['ip'].value else: try: ip = socket.gethostbyname(name) print " IP for host '{0}' is '{1}'".format(name, ip) except socket.gaierror: raise WSException( "Can`t lookup hostname '{0}'. Check it or set ip-address in --ip param!" .format(name)) IPs = IpsModel() ip_exists = IPs.exists(pData['id'], ip) ip_id = IPs.get_id_or_add(pData['id'], ip) if not ip_exists: print " IP '{0}' was automatically added to project '{1}'".format( ip, pData['name']) if self.model.exists(pData['id'], name): raise WSException( "Host '{0}' already exists in project '{1}'!".format( name, pData['name'])) self.model.add(pData['id'], ip_id, name, descr) print " Host '{0}' successfully added to project '{1}' with IP '{2}' ! ".format( name, pData['name'], ip)
def __init__(self, mask, dict_file, parts, part, template): if not template.count("%m%"): raise WSException( "Template '{0}' not contains %m% (mask) marker ".format( template)) if not template.count("%d%"): raise WSException( "Template '{0}' not contains %d% (dict) marker ".format( template)) if not os.path.exists(dict_file): raise WSException("Dict '{0}' not exists ".format(dict_file)) self.template = template self.dict_generator = FileGenerator(dict_file) self.next_dict_line() self.mask = mask self.mask_generator = DictOfMask(mask) self.lines_count = (self.dict_generator.lines_count * self.template.count("%d%")) * \ (self.mask_generator.all_objects_count * self.template.count("%m%")) if parts and part: one_part_count = int(self.lines_count / parts) self.first_border = one_part_count * (part - 1) self.second_border = one_part_count * part while self.current_counter < self.first_border: self.get()
def validate_main(self): """ Check users params """ super(ParamsModules, self).validate_main() try: resp = Registry().get('http').get(self.options['url'].value) except requests.exceptions.ConnectionError: raise WSException("Target web-site not available") parsed_url = urlparse(self.options['url'].value) if not len(parsed_url.scheme) or not len(parsed_url.netloc): raise WSException("Target URL not valid") if self.options['params-method'].value.lower() not in [ 'get', 'post' ] and int(self.options['max-params-length'].value) > 100: raise WSException( "Attention! Too big --max-params-length. Big value here allowed only in GET and POST modes" ) if not len(self.options['not-found-re'].value ) and self.options['not-found-size'].value == "-1": raise WSException( "You must set one or more params for detect negative server respose: not-found-re, not-found-size" )
def validate_main(self): """ Check users params """ if not validate_host(self.options['host'].value): raise WSException("'{0}' is not valid host name!".format( self.options['host'].value)) if 'ip' in self.options and self.options['ip'].value: if not validate_ip(self.options['ip'].value): raise WSException("IP '{0}' is not valid ip-address!".format( self.options['ip'].value))
def validate_main(self): """ Check users params """ if not HostsModel().exists(Registry().get('pData')['id'], self.options['host'].value): raise WSException("Host '{0}' not found in this project!".format( self.options['host'].value)) if 'url' in self.options and self.options['url'].value[0] != '/': raise WSException("URL must start from the root ('/') !")
def validate_main(self): """ Check users params """ super(FuzzerModules, self).validate_main() if not len(self.options['urls-file'].value): raise WSException("You must specify 'urls-file' param") if not os.path.exists(self.options['urls-file'].value): raise WSException("File with urls '{0}' not exists!".format( self.options['urls-file'].value))
def add_mass(self, pid, host_id, data): """ Add many urls at once in table """ to_insert = [] for row in data: for field in [ 'url', 'referer', 'response_code', 'response_time', 'who_add', 'spidered', 'size', 'descr' ]: if field not in row.keys(): if field in [ 'referer', 'response_code', 'response_time', 'descr' ]: row[field] = '' elif field in ['spidered', 'size']: row[field] = 0 elif field == 'who_add': row[field] = 'human' elif field == 'url': raise WSException("URL row must have a 'url' key") for k in row.keys(): if k not in [ 'url', 'referer', 'response_code', 'response_time', 'who_add', 'spidered', 'size', 'descr' ]: raise WSException( "Key '{0}' must not be in url data".format(k)) to_insert.append({ 'project_id': pid, "host_id": host_id, "hash": md5(row['url']), "url": row['url'], "referer": row['referer'], "response_code": row['response_code'], "response_time": row['response_time'], "when_add": int(time.time()), "who_add": row['who_add'], "spidered": row['spidered'], "size": row['size'], "descr": row['descr'] }) if len(to_insert) % 50 == 0: self._db.insert_mass("urls", to_insert, 1) to_insert = [] if len(to_insert): self._db.insert_mass("urls", to_insert, 1) return True
def load_headers_from_file(self, _file): if not os.path.exists(_file): raise WSException("File '{0}' not exists".format(_file)) header_regex = re.compile('([a-zA-Z0-9\-]*): (.*)') fh = open(_file, 'r') for line in fh: try: if len(line.strip()): parsed_header = header_regex.findall(line)[0] self.headers[parsed_header[0]] = parsed_header[1] except BaseException: raise WSException("Wrong header line '{0}'".format( line.strip())) fh.close()
def validate_main(self): """ Check users params """ super(DnsBruterModules, self).validate_main() if not self.options['template'].value.count("."): raise WSException("Bad template structure, dot not found") if self.options['template'].value.endswith(".onion"): raise WSException("DNS bruteforce for .onion is pointless") if re.search( '[^a-zA-Z0-9\-\.]', self.options['template'].value.replace( self.options['msymbol'].value, '')): raise WSException( "Template contains bad symbols, check it. Allowed only a-zA-Z0-9, -, ., " + self.options['msymbol'].value)
def __init__(self, module_name, have_items): self.module_name = module_name logs_dir = "{0}/logs/{1}".format(Registry().get('wr_path'), module_name) curdate = t("%Y-%m-%d") curtime = t("%H_%M_%S") if not os.path.exists(logs_dir): raise WSException( "LOGGER ERROR: Path {0} for module {1} not exists!".format( logs_dir, module_name)) if not os.path.exists("{0}/{1}".format(logs_dir, curdate)): os.mkdir("{0}/{1}".format(logs_dir, curdate)) if not os.path.exists("{0}/{1}/{2}".format(logs_dir, curdate, curtime)): os.mkdir("{0}/{1}/{2}".format(logs_dir, curdate, curtime)) if have_items: self.items_dir = "{0}/{1}/{2}/items".format( logs_dir, curdate, curtime) os.mkdir(self.items_dir) self.logs_dir = "{0}/{1}/{2}".format(logs_dir, curdate, curtime) self.log_fh = open("{0}/run.log".format(self.logs_dir), "w")
def validate_main(self): """ Check users params """ super(HttpAuth, self).validate_main() try: resp = Registry().get('http').get(self.options['url'].value) if resp.status_code != 401: raise WSException( "Target URL has response code {0}, not 401".format( resp.status_code)) except requests.exceptions.ConnectionError: raise WSException("Target web-site not available") parsed_url = urlparse(self.options['url'].value) if not len(parsed_url.scheme) or not len(parsed_url.netloc): raise WSException("Target URL not valid")
def add_action(self): """ Action add of module """ pid = Registry().get('pData')['id'] self.validate_main() if self.model.exists(pid, self.options['host'].value, self.options['url'].value): raise WSException( "URL '{0}' already exists in this project in host '{1}'!". format(self.options['url'].value, self.options['host'].value)) host_id = HostsModel().get_id_by_name(pid, self.options['host'].value) if (self.options['url'].value[-1] == '/' and self.model.exists(pid, self.options['host'].value, self.options['url'].value[:-1])) or\ (self.options['url'].value[-1] != '/' and self.model.exists(pid, self.options['host'].value, self.options['url'].value + "/")): if raw_input( 'Url {0} have analogue in database (with or without end slash). ' 'Are you realy want to add it (y/n)?'.format( self.options['url'].value)).lower()[0] != 'y': print "Url {0} was not added!".format( self.options['url'].value) return self.model.add(Registry().get('pData')['id'], host_id, self.options['url'].value) print " URL '{0}' successfully added to host '{1}'".\ format(self.options['url'].value, self.options['host'].value)
def validate_main(self): """ Check users params """ super(ContentDiscovery, self).validate_main() if len(self.options['urls-file'].value) and not os.path.exists( self.options['urls-file'].value): raise WSException("File with urls '{0}' not exists!".format( self.options['urls-file'].value))
def validate_main(self): """ Check users params """ super(HostsModules, self).validate_main() try: resp = Registry().get( 'http').get(self.options['http-protocol'].value + "://" + self.options['ip'].value) except requests.exceptions.ConnectionError: raise WSException("Target web-site not available") if (not self.options['false-re'].value or not len(self.options['false-re'].value)) and ( not self.options['false-size'].value or not len(self.options['false-size'].value)): raise WSException( "You must specify --false-re param or --false-size param!")
def validate_main(self): """ Method for validate user params """ super(DnsBruteDict, self).validate_main() if not os.path.exists(self.options['dict'].value): raise WSException( "Dictionary '{0}' not exists or not readable".format( self.options['dict'].value))
def prepare(self, action): """ Prepare module for work """ if action not in self.options_sets: raise WSException( "Action '{0}' not exists! See help for actions list of this module." .format(action)) self.options = self.options_sets[action] self.action = action
def validate_main(self): """ Check users params """ super(FormBruter, self).validate_main() if self.options['url'].value[0] != '/': raise WSException("URL must start from root (/)") if self.options['selenium'].value: if not len(self.options['conffile'].value.strip()): raise WSException("You must specify param --conffile") if not os.path.exists(self.options['conffile'].value): raise WSException( "Config file '{0}' not exists or not readable!".format( self.options['conffile'].value)) else: if not len(self.options['confstr'].value.strip()): raise WSException("You must specify param --confstr") if not self.options['confstr'].value.count("^USER^"): raise WSException("--confstr must have a ^USER^ fragment") if not self.options['confstr'].value.count("^PASS^"): raise WSException("--confstr must have a ^PASS^ fragment") if not len(self.options['true-phrase'].value) and not len( self.options['false-phrase'].value): raise WSException( "You must specify --false-phrase param or --true-phrase param!" )
def add_action(self): """ Action add of module """ name = Registry().get('project') if self.model.exists(name): raise WSException( "Project with name '{0}' already exists!".format(name)) self.model.create(name, self.options['descr'].value) print " Project '{0}' with description '{1}' successfully created! ".\ format(name, self.options['descr'].value)
def add_option(self, internal_name, external_name=None): if internal_name not in self.all_options: raise WSException("Option '{0}' not exists".format(internal_name)) if external_name is not None: option = self.all_options[internal_name] option.flags = ['--' + external_name] self.options[external_name] = option else: self.options[internal_name] = self.all_options[internal_name]
def validate_main(self): """ Check users params """ super(UrlsModules, self).validate_main() skip_listings = Registry().get('config')['main']['skip_listings'] standart_msymbol = Registry().get('config')['main']['standart_msymbol'] source_url = self.options['template'].value.replace(standart_msymbol, "") try: resp = Registry().get('http').get(source_url) response_text = resp.text resp.close() if ("<title>Index of" in response_text or "<h1>Index of" in response_text) and skip_listings == "1": raise WSException("Source URL is listing, check it. Or change 'skip_listings' param in config") except requests.exceptions.ConnectionError: raise WSException("Target web-site not available") parsed_url = urlparse(self.options['template'].value) if not len(parsed_url.scheme) or not len(parsed_url.netloc): raise WSException("Target URL not valid") if self.options['not-found-size'].value != "-1" and self.options['method'].value.lower() == 'head': raise WSException( "You can`t use HEAD method with --false-size param" )
def delete_action(self): """ Delete action of module """ self.validate_main() if not self.model.exists(Registry().get('pData')['id'], self.options['host'].value, self.options['url'].value): raise WSException( "URL '{0}' not exists in this project in host '{1}'!".format( self.options['url'].value, self.options['host'].value)) self.model.delete(Registry().get('pData')['id'], self.options['host'].value, self.options['url'].value) print "URL '{0}' in host '{1}' successfully deleted."\ .format(self.options['host'].value, self.options['url'].value)
def add_action(self): """ Action add of module """ self.validate_main() pData = Registry().get('pData') ip = self.options['ip'].value descr = self.options['descr'].value if self.model.exists(pData['id'], ip): raise WSException( "IP '{0}' already exists in project '{1}'!".format( ip, pData['name'])) self.model.add(pData['id'], ip, descr) print " IP '{0}' successfully added to project '{1}' ! ".format( ip, pData['name'])
def delete_action(self): """ Delete action of module """ self.validate_main() name = self.options['host'].value if not self.model.exists(Registry().get('pData')['id'], name): raise WSException( "Host '{0}' not exists in this project!".format(name)) answer = raw_input( "You really want to delete host '{0}' [y/n]? ".format(name)) if answer.lower() == 'y': self.model.delete(Registry().get('pData')['id'], name) print "Host '{0}' successfully deleted.".format(name) else: print "Host '{0}' not deleted.".format(name)
def validate_main(self): """ Check users params """ super(Forms, self).validate_main() try: resp = Registry().get('http').get(self.options['url'].value) except requests.exceptions.ConnectionError: raise WSException("Target web-site not available") parsed_url = urlparse(self.options['url'].value) if not len(parsed_url.scheme) or not len(parsed_url.netloc): raise WSException("Target URL not valid") if self.options['selenium'].value: if not len(self.options['conf-file'].value.strip()): raise WSException("You must specify param --conf-file") if not os.path.exists(self.options['conf-file'].value): raise WSException( "Config file '{0}' not exists or not readable!".format( self.options['conf-file'].value)) else: if not len(self.options['conf-str'].value.strip()): raise WSException("You must specify param --conf-str") if not self.options['conf-str'].value.count("^USER^"): raise WSException("--conf-str must have a ^USER^ fragment") if not self.options['conf-str'].value.count("^PASS^"): raise WSException("--conf-str must have a ^PASS^ fragment") if not len(self.options['true-re'].value) and not len( self.options['false-re'].value ) and not self.options['false-size'].value: raise WSException( "You must specify --false-re param or --true-re param or --false-size param!" )
def make_queue(self): """ Abstract method for queue make """ raise WSException("This method must be described in child-class")
def load_objects(self, queue): """ Method for prepare test objects, here abstract """ raise WSException("This method must be described in child-class")
def validate_main(self): """ Common user params validate functions """ if 'selenium' in self.options.keys( ) and self.options['selenium'].value: if ('not-found-re' in self.options.keys() and 'not-found-size' in self.options.keys()) and \ (not len(self.options['not-found-re'].value) and self.options['not-found-size'].value == "-1"): raise WSException( "Selenium enabled, module need a not found phrase (--not-found-re) or not found size (--not-found-size) for work!" ) threads_count = int(self.options['threads'].value) if threads_count == 10: threads_count = int(Registry().get('config')['selenium'] ['default_threads_count']) self.options['threads'].value = int(Registry().get( 'config')['selenium']['default_threads_count']) if threads_count != 10 and threads_count > int( Registry().get('config')['selenium']['max_threads']): raise WSException( "Selenium enabled, very many threads value ({0}), see docs." .format(self.options['threads'].value)) if ('method' in self.options.keys() and self.options['method'].value.lower() != 'get') or \ ('params-method' in self.options.keys() and self.options['params-method'].value.lower() != 'get'): raise WSException("In Selenium mode only GET method allowed") if 'not-found-codes' in self.options.keys( ) and self.options['not-found-codes'].value != "404": raise WSException( "In Selenium mode param --not-found-codes not allowed") if 'headers-file' in self.options.keys( ) and self.options['headers-file'].value != "": raise WSException( "In Selenium mode param --headers-file not allowed") if 'protocol' in self.options.keys( ) and self.options['protocol'].value.lower() not in ['http', 'https']: raise WSException( "Protocol param must be 'http' or 'https', but have value '{0}' !" .format(self.options['protocol'].value)) if 'params-method' in self.options.keys( ) and self.options['params-method'].value.lower() not in [ 'get', 'post', 'cookies', 'files' ]: raise WSException( "Method param must be only 'get', 'post', 'cookies', 'files', but have value '{0}' !" .format(self.options['params-method'].value)) if 'method' in self.options.keys( ) and self.options['method'].value.lower() not in [ 'head', 'get', 'post' ]: raise WSException( "Method param must be only 'head', 'get' or 'post', but have value '{0}' !" .format(self.options['method'].value)) if 'not-found-codes' in self.options.keys() and len( self.options['not-found-codes'].value): for code in self.options['not-found-codes'].value.strip().split( ","): if len(code.strip()) and not re.match(r'^(\d+)$', code.strip()): raise WSException( "Not-found code must be digital, but it is '{0}'". format(code.strip())) if 'retest-codes' in self.options.keys() and len( self.options['retest-codes'].value): for code in self.options['retest-codes'].value.strip().split(","): if len(code.strip()) and not re.match(r'^(\d+)$', code.strip()): raise WSException( "Retest code must be digital, but it is '{0}'".format( code.strip())) for proxies_params in ['proxies', 'http-proxies']: if proxies_params in self.options.keys() and len(self.options[proxies_params].value) and \ not os.path.exists(self.options[proxies_params].value): raise WSException("Proxy list not found: '{0}'".format( self.options[proxies_params].value)) if 'not-found-re' in self.options.keys() and len( self.options['not-found-re'].value): try: re.compile(self.options['not-found-re'].value) except re.error: raise WSException("Invalid regex: '{0}'".format( self.options['not-found-re'].value)) if 'browser-recreate-re' in self.options.keys() and len( self.options['browser-recreate-re'].value): try: re.compile(self.options['browser-recreate-re'].value) except re.error: raise WSException("Invalid regex: '{0}'".format( self.options['browser-recreate-re'].value)) if 'dict' in self.options.keys() and not os.path.exists( self.options['dict'].value): raise WSException( "Dictionary '{0}' not exists or not readable!".format( self.options['dict'].value)) if 'delay' in self.options.keys( ) and self.options['delay'].value != '0': if not re.match(r'^(\d+)$', self.options['delay'].value): raise WSException( "Delay param must be digital, but it is '{0}'".format( self.options['delay'].value.strip())) if 'parts' in self.options.keys( ) and self.options['parts'].value != '0': if not re.match(r'^(\d+)$', self.options['parts'].value): raise WSException( "Parts param must be digital, but it is '{0}'".format( self.options['parts'].value.strip())) if 'part' in self.options.keys() and self.options['part'].value != '0': if not re.match(r'^(\d+)$', self.options['part'].value): raise WSException( "Part param must be digital, but it is '{0}'".format( self.options['part'].value.strip())) if 'parts' in self.options.keys( ) and self.options['parts'].value != '0': if 'part' not in self.options.keys( ) or self.options['part'].value == '0': raise WSException( "If you use '--parts' param, you must specify '--part'") if int(self.options['part'].value) > int( self.options['parts'].value): raise WSException( "Number of part ({0}) more than parts count ({1})".format( self.options['part'].value.strip(), self.options['parts'].value.strip())) if 'part' in self.options.keys() and self.options['part'].value != '0': if 'parts' not in self.options.keys( ) or self.options['parts'].value == '0': raise WSException( "If you use '--part' param, you must specify '--parts'") if 'template' in self.options.keys( ) and 'msymbol' in self.options.keys(): if self.options['template'].value.find( self.options['msymbol'].value) == -1: raise WSException( "Symbol of object position ({0}) not found in template ({1}) " .format(self.options['msymbol'].value, self.options['template'].value)) if 'zone' in self.options.keys() and self.options['zone'].value.upper( ) not in self.POSSIBLE_DNS_ZONES: raise WSException("Wrong DNS zone - '{0}', allowed: {1}".format( self.options['zone'].value, ", ".join(self.POSSIBLE_DNS_ZONES))) if 'dns-protocol' in self.options.keys( ) and self.options['dns-protocol'].value not in ['tcp', 'udp', 'auto']: raise WSException( "DNS Protocol mast be 'tcp', 'udp' or 'auto', but it is '{0}'". format(self.options['dns-protocol'].value))
def __init__(self, kernel): self.kernel = kernel if self.log_path is None: raise WSException('Module must have log path!')
def run(self): """ Run thread """ req_func = getattr(dns.query, self.proto.lower()) need_retest = False while not self.done: self.last_action = int(time.time()) if self.delay: time.sleep(self.delay) try: if not need_retest: check_host = self.queue.get() if not self.is_valid_hostname(check_host): continue self.check_name = self.template.replace( self.msymbol, check_host) query = dns.message.make_query(self.check_name, self.zone) try: result = req_func(query, self.dns_srv, timeout=5) ErrorsCounter.flush() except EOFError: ErrorsCounter.up() time.sleep(3) need_retest = True break except BaseException as e: if self.is_dns_retest_need(str(e)): time.sleep(3) need_retest = True continue raise e self.current_response_text = str(result.to_text()) response = self.re['ns_resp'].search(result.to_text()) if response is not None: if self.zone == 'A': self.parse_zone_a(response) elif self.zone == 'CNAME': self.parse_zone_cname(result) else: raise WSException("Wrong dns zone '{0}'".format( self.zone)) if len(self.result) >= int(Registry().get('config')['main'] ['positive_limit_stop']): Registry().set('positive_limit_stop', True) need_retest = False self.counter.up() except queue.Empty: self.done = True break except dns.exception.Timeout: need_retest = True time.sleep(1) except BaseException as e: self.logger.ex(e) self.logger.log("Exception with {0}".format(self.dns_srv)) time.sleep(5)
def start_pool(self): """ Abstract method for make threads pool """ raise WSException("This method must be decsribed in child-class")