def logout(): """ Logouts the user and removes the password hash from the session. """ logout_user() PasswordManager.pop_session_pwdh() return redirect(url_for('login'))
def login(): if current_user is not None and current_user.is_authenticated(): return redirect(url_for('index')) form = LoginForm(request.form) if form.validate_on_submit(): user = User.query.filter_by(username=form.username.data).first() login_user(user) PasswordManager.set_session_pwdh(form.password.data) return redirect(url_for('index')) else: return render_template("login.html", form=form)
def async_analysis_start(): """ Starts the Analysis and set the lock. """ task = async_analysis.apply_async((PasswordManager.get_session_pwdh(),)) redis.Redis().set(ANALYSE_KEY, task.id) return jsonify({'key': task.id})
def start_scan_all_devices_async(): """ Starts the scan and set the lock. """ task = scan_all_devices_async.apply_async((PasswordManager.get_session_pwdh(),)) redis.Redis().set(SCAN_KEY, task.id) return jsonify({'key': task.id})
def settings(): form = SettingsForm(request.form) if form.validate_on_submit(): if form.newpassword.data and form.oldpassword.data and form.repeat.data: # Handling the decryption and re-encryption of the passwords in case of a password change new_pwdh = PasswordManager.generate_pwdh_from_password(form.newpassword.data) for device in Device.query.all(): # Decrypts the password using the session pwdh and encrypts it with the new pwdh (not in session) device.password = PasswordManager.encrypt_string(device.decrypt_password(), new_pwdh) device.save(encrypt=False) # The password is already encrypted PasswordManager.set_session_pwdh(form.newpassword.data) current_user.set_password(form.newpassword.data) current_user.save() flash("Successfully set new password", "info") return redirect(url_for('settings')) else: return render_template("settings.html", form=form, active_page="settings")
def inspect_configuration(configuration_id): flash_default_password() configuration = Configuration.query.filter_by(id=configuration_id).first_or_404() try: content = PasswordManager.decrypt_file_content_from_session_pwdh(configuration.path) return render_template("inspect_configuration.html", content=content, active_page='configurations') except Exception as e: app.logger.exception(msg="Something went wrong : {}".format(e)) return redirect(url_for('configurations'))
def save(self, encrypt=True): self.date = datetime.now() if encrypt: self.password = PasswordManager.encrypt_string_from_session_pwdh(self.password) db.session.add(self) try: db.session.commit() except: db.session.rollback() return False return True
def download_configuration(configuration_id): configuration = Configuration.query.filter_by(id=configuration_id).first_or_404() try: content = PasswordManager.decrypt_file_content_from_session_pwdh(configuration.path) directory, filename = os.path.split(configuration.path) response = make_response(content) response.headers["Content-Disposition"] = "attachment; filename={}".format(filename) return response except Exception as e: app.logger.exception(msg="Something went wrong while downloading configuration : {}".format(e)) flash("Something went wrong. Check the log file for more information.", "error") return redirect(url_for('configurations'))
def async_analysis(self, pwdh): have_lock = False try: app.logger.info("Started Analysis") have_lock = ANALYSE_LOCK.acquire(blocking=False) if VulnBasic.query.count() == 0: app.logger.info("VulnBasic table is empty, adding the preco") list_preco = open(CISCO_PRECO_FILE).readlines() for i in list_preco: x = i.split(';') preco = VulnBasic(match=(x[0]), expectmatch=(x[1]), description=(x[2])) db.session.add(preco) db.session.commit() total = Device.query.count() self.update_state(state='PROGRESS', meta={'message': "Started Analysis for {total} device{total_plural}".format( total=total, total_plural="s" if total > 1 else "", ), 'percentage': 5}) done = 0 today = datetime.now() for d in Device.query.all(): for conf in Configuration.query.filter(Configuration.path.like('%run%.txt')).filter(Configuration.device_id == d.id).order_by(Configuration.date.desc()).limit(1): value = "" for v in VulnBasic.query.all(): pattern = re.compile(v.match) for i, line in enumerate(PasswordManager.decrypt_file_content(conf.path, pwdh).split('\n')): if re.match(pattern, line) and v.expectmatch == 0: value = 'ERROR : %s-%s found on line %s - file %s' % (pattern, v.expectmatch, i + 1, conf.path) vuln_values = ConfVuln() vuln_values.vulnbasic_id = v.id vuln_values.configuration_id = conf.id vuln_values.date = today db.session.add(vuln_values) elif re.match(pattern, line) and v.expectmatch == 1: value = '%s-%s found on line %s - file %s' % (pattern, v.expectmatch, i + 1, conf.path) if not value and v.expectmatch == 1: vuln_values = ConfVuln() vuln_values.vulnbasic_id = v.id vuln_values.configuration_id = conf.id vuln_values.date = today value = "" db.session.add(vuln_values) for conf in Configuration.query.filter(Configuration.path.like('%version%.txt')).filter(Configuration.device_id == d.id).order_by(Configuration.date.desc()).limit(1): for line in PasswordManager.decrypt_file_content(conf.path, pwdh).split('\n'): cisco_search = re.search('(?i)Cisco\sIOS.*,.*\((\w+\d*)-.*\).*Version\s(\d*.\d*)\(.*', line) if cisco_search: version_values = ConfigurationValues() version_values.version = cisco_search.group(2) version_values.model = cisco_search.group(1) version_values.configuration_id = conf.id db.session.add(version_values) for value in ConfigurationValues.query.filter(ConfigurationValues.configuration_id == conf.id): dev_version = value.version for cve in VulnCve.query.filter(not VulnCve.version == ''): cve_vers = cve.version inf = '' sep = '' sup = '' cvevers_search = re.search('(\d+\.\d)(?:([-,])(\d+\.\d))?', cve_vers) if cvevers_search: if cvevers_search.group(1): inf = cvevers_search.group(1) obj = ConfVuln() if cvevers_search.group(2): sep = cvevers_search.group(2) if cvevers_search.group(3): sup = cvevers_search.group(3) if sep and sep == ',': if dev_version in [inf, sup]: obj.configuration_id = conf.id obj.vulncve_id = cve.id if sep and sep == '-': if inf <= dev_version <= sup: obj.configuration_id = conf.id obj.vulncve_id = cve.id else: if dev_version == inf: obj.configuration_id = conf.id obj.vulncve_id = cve.id if obj.vulncve_id: obj.date = today db.session.add(obj) done += 1 self.update_state( state='PROGRESS', meta={'message': "Done {done} device{done_plural} over {total} device{total_plural}".format( done=done, done_plural="s" if done > 1 else "", total=total, total_plural="s" if total > 1 else "" ), 'percentage': done/total*100-1}) db.session.commit() app.logger.info("Finished Analysis") self.update_state(state='PROGRESS', meta={'message': "Analysis Finished", 'percentage': 100}) time.sleep(5) finally: if have_lock: ANALYSE_LOCK.release()
@celery.task(bind=True) def scan_device_async(self, device, devicetype, manufacturer, pwdh): """ Calls the scan_device function async way. """ scan_device(device, devicetype, manufacturer, pwdh, async=self) def scan_device(device, devicetype, manufacturer, pwdh, async=None): """ Scan a single device. Device is a pickle object. TODO: Async information for each device """ password = PasswordManager.decrypt_string(device.password, pwdh) enapassword = PasswordManager.decrypt_string(device.enapassword, pwdh) derror = {} app.logger.info("Started for {}".format(device.name)) if device.method in ['ssh', 'telnet']: if async: async.update_state(state='PROGRESS', meta={'message': "Connecting", 'percentage': 5}) if device.method == "ssh": s_tunnel = 'ssh -o ConnectTimeout=25 ' child = pexpect.spawn(s_tunnel + device.username + '@' + device.ip) else: s_tunnel = 'telnet ' child = pexpect.spawn(s_tunnel + device.ip) q = child.expect(generate_pexpect_list([PROMPT_REGEX_CISCO])) if perror(device, derror, m): return derror
def decrypt_password(self): return PasswordManager.decrypt_string_from_session_pwdh(self.password)
def logout(): logout_user() PasswordManager.pop_session_pwdh() return redirect(url_for('login'))
def mainsendcommand(): # derror={} exit_flag = 0 class myThread(threading.Thread): def __init__(self, threadID, name, q): threading.Thread.__init__(self) self.threadID = threadID self.name = name self.q = q def run(self): print("Starting " + self.name) process_data(self.name, self.q) print("Exiting " + self.name) def process_data(threadName, q): while not exit_flag: queueLock.acquire() if not workQueue.empty(): data = q.get() queueLock.release() print( send(data)) else: queueLock.release() time.sleep(1) threadList = ["Thread-1", "Thread-2", "Thread-3"] queueLock = threading.Lock() workQueue = Queue.Queue(2000) threads = [] threadID = 1 nameList = [] for device in Device.query.all(): password = PasswordManager.decrypt_string(device.password, PasswordManager.generate_pwdh_from_password("root")) username = device.username method = 'ssh' enable = PasswordManager.decrypt_string(device.enapassword, PasswordManager.generate_pwdh_from_password("root")) nameList.append(method + "," + device.name + "," + device.ip + "," + username + "," + password + "," + enable + "," + device.devicetype.manufacturer.name) # Create new threads for tName in threadList: thread = myThread(threadID, tName, workQueue) thread.start() threads.append(thread) threadID += 1 # Fill the queue queueLock.acquire() for word in nameList: print(word) workQueue.put(word) queueLock.release() # Wait for queue to empty while not workQueue.empty(): pass # Notify threads it's time to exit exit_flag = 1 # Wait for all threads to complete for t in threads: t.join() print("Exiting Main Thread")