class SnifferProcess(Process): ''' Takes the KillerBee instance which will be used for sniffing and receives packets, feeding each into the given pipe to the FilterProcess, until the stopevent fires. ''' def __init__(self, pipe, kb, stopevent, drone, parent): super(SnifferProcess, self).__init__() self.pipe = pipe self.kb = kb self.stopevent = stopevent self.name = '{0}.Sniffer'.format(parent) self.logutil = KBLogUtil(drone, self.name) def run(self): ''' Start receiving and returning packets until the stopevent flag is set. ''' self.logutil.log('Initializing') self.logutil.log('Turning on interface: {0}'.format(self.kb.device)) self.kb.sniffer_on() while not self.stopevent.is_set(): recvpkt = self.kb.pnext() #nonbocking # Check for empty packet (timeout) and valid FCS if recvpkt is not None: # and recvpkt[1]: self.logutil.debug("Received Frame") self.pipe.send(recvpkt) self.logutil.log('Turning off interface: {0}'.format(self.kb.device)) self.kb.sniffer_off() self.logutil.log('Terminating Execution')
class SnifferProcess(Process): """ Takes the KillerBee instance which will be used for sniffing and receives packets, feeding each into the given pipe to the FilterProcess, until the stopevent fires. """ def __init__(self, pipe, kb, stopevent, drone, parent): super(SnifferProcess, self).__init__() self.pipe = pipe self.kb = kb self.stopevent = stopevent self.name = "{0}.Sniffer".format(parent) self.logutil = KBLogUtil(drone, self.name) def run(self): """ Start receiving and returning packets until the stopevent flag is set. """ self.logutil.log("Initializing") self.logutil.log("Turning on interface: {0}".format(self.kb.device)) self.kb.sniffer_on() while not self.stopevent.is_set(): recvpkt = self.kb.pnext() # nonbocking # Check for empty packet (timeout) and valid FCS if recvpkt is not None: # and recvpkt[1]: self.logutil.debug("Received Frame") self.pipe.send(recvpkt) self.logutil.log("Turning off interface: {0}".format(self.kb.device)) self.kb.sniffer_off() self.logutil.log("Terminating Execution")
def __init__(self, pipe, kb, stopevent, drone, parent): super(SnifferProcess, self).__init__() self.pipe = pipe self.kb = kb self.stopevent = stopevent self.name = '{0}.Sniffer'.format(parent) self.logutil = KBLogUtil(drone, self.name)
def __init__(self, name, port): signal.signal(signal.SIGINT, self.SIGINT) self.port = port self.name = name self.logutil = KBLogUtil(self.name, 'Daemon', os.getpid()) self.interfaces = {} self.plugins = {} self.pid = os.getpid()
class BaseDronePlugin(object): def __init__(self, interfaces, channel, drone, name): #TODO: add interface validation self.interfaces = interfaces self.name = name self.kb = None self.channel = channel self.drone = drone self.childprocesses = [] self.tasks = {} self.done_event = Event() self.task_update_event = Event() self.timeout = 5 self.status = True self.active = True self.desc = None self.pid = os.getpid() self.logutil = KBLogUtil(self.drone, '{0}.Main'.format(self.name)) def info(self): info = {} info['name'] = self.name info['pid'] = self.pid info['status'] = self.status info['active'] = self.active info['processes'] = list(({'desc':process.desc, 'pid':process.pid} for process in self.childprocesses)) info['tasks'] = list(({'uuid': task[0], 'parameters':task[1] } for task in self.tasks.items())) return info def shutdown(self): self.logutil.log('Initiating shutdown') self.done_event.set() for process in self.childprocesses: if process.is_alive(): process.join(self.timeout) if process.is_alive(): process.terminate() time.sleep(self.timeout) if process.is_alive(): raise Exception("Failed to terminate process") self.active = False #self.kb.plugin = None self.kb.active = False self.logutil.log('Successful shutdown') def task(self, uuid, data): ''' overwrite this function ''' pass def detask(self, uuid): ''' overwrite this function ''' pass
def __init__(self, config): Process.__init__(self) self.name = 'RuleEngine' self.config = config self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name) self.wids = WIDSClient(self.config.server_ip, self.config.server_port) self.active = None self.rules = [] #///dev/// self.rules.append(rule1)
def __init__(self, pipe, task_queue, stopevent, task_update_event, drone, parent): super(FilterProcess, self).__init__() self.pipe = pipe self.task_queue = task_queue self.stopevent = stopevent self.taskevent = task_update_event self.drone = drone self.parent = parent self.name = '{0}.Filter'.format(self.parent) self.logutil = KBLogUtil(self.drone, self.name, None) self.callbacks = 0
def __init__(self, settings, config, shutdown_event, name): Process.__init__(self) self.name = name self.settings = settings self.config = config self.shutdown_event = shutdown_event self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name, None) self.wids_api = WIDSClient(self.config.server_ip, self.config.server_port) self.tasks = {} self.active = False self.running = False
def __init__(self, parameters=None, config=None): signal.signal(signal.SIGINT, self.SIGINT) self.config = WIDSConfig(parameters, config) self.config.daemon_pid = os.getpid() self.logutil = KBLogUtil(self.config.name, 'Daemon') self.database = DatabaseHandler(self.config.name) self.engine = None self.module_store = {} self.module_counter = 0 self.task_store = {} self.task_counter = 0 self.drone_store = {} self.drone_counter = 0
def __init__(self, pipe, kb, stopevent, drone, parent): super(SnifferProcess, self).__init__() self.pipe = pipe self.kb = kb self.stopevent = stopevent self.name = "{0}.Sniffer".format(parent) self.logutil = KBLogUtil(drone, self.name)
def __init__(self, interfaces, channel, drone, name): #TODO: add interface validation self.interfaces = interfaces self.name = name self.kb = None self.channel = channel self.drone = drone self.childprocesses = [] self.tasks = {} self.done_event = Event() self.task_update_event = Event() self.timeout = 5 self.status = True self.active = True self.desc = None self.pid = os.getpid() self.logutil = KBLogUtil(self.drone, '{0}.Main'.format(self.name))
class RuleEngine(Process): def __init__(self, config): Process.__init__(self) self.name = 'RuleEngine' self.config = config self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name) self.wids = WIDSClient(self.config.server_ip, self.config.server_port) self.active = None self.rules = [] #///dev/// self.rules.append(rule1) #//////// def run(self): self.logutil.log('Starting Execution') self.active = True self.start_time = dateToMicro(datetime.utcnow()) while self.active: if DEV_DEBUG: self.logutil.debug('Checking for new rules') time.sleep(3) # check server for new rules: 'GET /rules/updatecheck', if so load new rules ''' if self.wids.checkNewRules(): new_rules = self.wids.getNewRules() ''' # evaluate each rule serially self.logutil.debug('Evaluating rules') for RuleObject in self.rules: self.evaluateRule(RuleObject) self.logutil.log('Terminating Execution') # TODO - replace the internal database with a REST call to query database for events def evaluateRule(self, RuleObject): try: self.logutil.dev('Evaluating Rule: {0} (EventIndex: {1})'.format( RuleObject.name, RuleObject.event_index)) for condition in RuleObject.conditions: module = condition[0] event = condition[1] count = condition[2] # TODO - replace this direct database query with REST call ???? query = self.database.session.query(Event).filter( Event.module == module).filter(Event.name == event).filter( Event.datetime > self.start_time).filter( Event.id > RuleObject.event_index) results_count = query.limit(count).count() self.logutil.dev( 'Event: {0} - Found: {1} (Events Needed: {2})'.format( event, results_count, count)) if not results_count >= count: return False last_result = query.order_by( Event.id.desc()).limit(count).first() RuleObject.event_index = last_result.id self.logutil.log('>>> Rule Conditions Met ({0})'.format( RuleObject.name)) for action in RuleObject.actions: actionType = action[0] actionParams = action[1] if actionType == 'GenerateAlert': self.action_GenerateAlert(RuleObject.name, actionParams) if actionType == 'GenerateLog': self.action_GenerateLog(RuleObject.name, actionParams) except Exception: traceback.print_exc() def action_GenerateLog(self, rule_name, action_parameters): self.logutil.log( 'Execution GenerateLog Action for Rule {0}'.format(rule_name)) pass def action_GenerateAlert(self, rule_name, action_parameters): self.logutil.log( 'Executing GenerateAlert Action for Rule {0}'.format(rule_name)) self.wids.generateAlert(rule_name) def shutdown(self): self.active = False self.terminate()
class WIDSDaemon: def __init__(self, parameters=None, config=None): signal.signal(signal.SIGINT, self.SIGINT) self.config = WIDSConfig(parameters, config) self.config.daemon_pid = os.getpid() self.logutil = KBLogUtil(self.config.name, 'Daemon') self.database = DatabaseHandler(self.config.name) self.engine = None self.module_store = {} self.module_counter = 0 self.task_store = {} self.task_counter = 0 self.drone_store = {} self.drone_counter = 0 def SIGINT(self, s, f): if self.config.daemon_pid == os.getpid(): self.logutil.log('SIGINT') self.stopDaemon() def startDaemon(self): self.logutil.writePID() self.logutil.startlog() self.logutil.log('Starting Daemon') self.loadDrones() self.loadModules() self.startServer() def stopDaemon(self): self.logutil.log('Initiating Shutdown') self.unloadModules() self.unloadDrones() self.logutil.log('Successfull Shutdown') self.logutil.cleanup() sys.exit() def loadDrones(self): count = len(self.config.drones) self.logutil.log('Loading Drones (Found {0} Drones in the Config)'.format(count)) for droneConfig in self.config.drones: self.loadDrone(droneConfig) def loadDrone(self, droneConfigDict): try: print(droneConfigDict) drone_ip = str(droneConfigDict.get('ip', None)) drone_port = str(droneConfigDict.get('port', None)) if drone_ip == None or drone_port == None: error = 'Error: Missing Parameter: "address"' self.logutil.log(error) return self.formatResponse(error, None) else: droneIndex = self.drone_counter droneObject = DroneContainer(droneIndex, drone_ip, drone_port) self.drone_store[droneIndex] = droneObject self.drone_counter += 1 self.logutil.log('Loading Drone {0} - {1}:{2}'.format(droneIndex, drone_ip, drone_port)) return self.formatResponse(None, None) except: self.handleException() def unloadDrones(self): self.logutil.log('Unloading Drones') self.logutil.log('Found {0} Active Drones'.format(len(self.drone_store))) for i in range(len(self.drone_store)): self.unloadDrone(i) def unloadDrone(self, droneIndexInt): try: droneObject = self.drone_store.get(droneIndexInt, None) if droneObject == None: error = 'Error: Drone with Index {0} does not exist'.format(droneIndexInt) self.logutil.log(error) return self.formatResponse(False, error) else: droneObject.release() self.logutil.log('Releasing Drone {0} - {1}:{2}'.format(droneIndexInt, droneObject.address, droneObject.port)) del(self.drone_store[droneIndexInt]) del(droneObject) return self.formatResponse(True, None) except: self.handleException() def taskDrone(self, taskConfigDict): try: droneIndexList = taskConfigDict.get('droneIndexList') for droneIndexInt in droneIndexList: droneObject = self.drone_store.get(droneIndexInt, None) task_uuid = taskConfigDict.get('uuid', None) task_plugin = taskConfigDict.get('plugin', None) task_channel = taskConfigDict.get('channel', None) task_parameters = taskConfigDict.get('parameters', None) module_index = taskConfigDict.get('module_index', None) if droneObject == None: error = ec.ERROR_DRONE_InvalidDroneIndex data = droneIndexInt return (error,data) if task_uuid == None: error = ec.ERROR_DRONE_MissingDroneTaskParameter data = 'uuid' return (error, data) if task_channel == None: error = ec.ERROR_DRONE_MissingDroneTaskParameter data = 'channel' return (error, data) if task_plugin == None: error = ec.ERROR_MissingDroneTaskParameter data = 'plugin' return (error, data) if task_parameters == None: error = ec.ERROR_MissingDroneTaskParameter data = 'parameters' return (error, data) (data,error) = droneObject.api.task(task_plugin, task_channel, task_uuid, task_parameters) if error == None: self.task_store[self.task_counter] = TaskContainer(self.task_counter, task_uuid, task_plugin, task_channel, task_parameters, droneIndexList, module_index) self.task_counter += 1 return (data,error) except: self.handleException() def detaskDrone(self, droneIndexList, task_uuid): try: for int_DroneIndex in droneIndexList: droneObject = self.drone_store.get(int_DroneIndex, None) droneObject.api.detask(task_uuid) except Exception: self.handleException() def loadModules(self): count = len(self.config.modules) self.logutil.log('Loading Modules (Found {0} Modules in the Config)'.format(count)) for moduleConfigDict in self.config.modules: self.loadModule(moduleConfigDict) pass def unloadModules(self): self.logutil.log('Unloading Modules') self.logutil.log('Found {0} Active Modules'.format(len(self.module_store))) for i in range(len(self.module_store)): self.unloadModule(i) def loadModuleClass(self, module): if module == 'BeaconRequestMonitor' : return BeaconRequestMonitor if module == 'DisassociationStormMonitor' : return DisassociationStormMonitor if module == 'DosAesCtrMonitor' : return DosAesCtrMonitor def loadModule(self, moduleConfigDict): self.logutil.debug('Loading Module: {0}'.format(moduleConfigDict)) try: moduleName = moduleConfigDict.get('name', None) moduleSettings = moduleConfigDict.get('settings', None) moduleClass = self.loadModuleClass(moduleName) if moduleName == None: error = ec.ERROR_WIDS_MissingModuleParameter data = 'name' self.logutil.log('Failed to Load Module - Missing Parameter: "name" in {0}\n'.format(moduleConfigDict)) return self.formatResponse(error,data) elif moduleSettings == None: error = ec.ERROR_WIDS_MissingModuleParameter data = 'settings' self.logutil.log('Failed to Load Module - Missing Parameter: "settings" in {0}\n'.format(moduleConfigDict)) return self.formatResponse(error,data) elif moduleClass == None: error = ec.ERROR_WIDS_MissingModuleClass data = moduleName self.logutil.log('Failed to Load Module - Could not load class: {0}'.format(moduleName)) return self.formatResponse(error,data) else: moduleIndex = self.module_counter moduleShutdownEvent = Event() moduleSettings['module_index'] = moduleIndex self.logutil.debug('Found module class: {0}'.format(moduleClass)) ''' (error,data) = moduleClass.validate_settings(moduleSettings) if not error == None: return self.formatResponse(error,data) ''' moduleProcess = moduleClass(moduleSettings, self.config, moduleShutdownEvent) moduleProcess.start() moduleObject = ModuleContainer(moduleIndex, moduleName, moduleSettings, moduleProcess, moduleShutdownEvent) self.module_store[moduleIndex] = moduleObject self.module_counter += 1 self.logutil.log('Loading Module {0} - {1}'.format(moduleIndex, moduleObject.name)) return self.formatResponse(None, None) except: self.handleException() def unloadModule(self, moduleIndexInt): try: moduleObject = self.module_store.get(moduleIndexInt, None) if moduleObject == None: error = 'Error: Module with Index {0} does not exist'.format(moduleIndexInt) self.logutil.log(error) return self.formatResponse(False, error) else: self.logutil.log('Unloading Module {0} ({1} - {2})'.format(moduleIndexInt, moduleObject.name, moduleObject.process.pid)) self.logutil.log('Detasking Module Tasks') for taskObject in self.task_store.values(): if taskObject.module_index == moduleObject.index: drones = taskObject.drones uuid = taskObject.uuid self.logutil.log('Removing Task {0} from Drones {1}'.format(uuid, drones)) self.detaskDrone(drones, uuid) moduleObject.process.terminate() moduleObject.process.join() del(self.module_store[moduleIndexInt]) del(moduleObject) return self.formatResponse(True, None) except: self.handleException() def startServer(self): self.logutil.log('Starting Server on port {0}'.format(self.config.server_port)) app = flask.Flask(__name__) app.add_url_rule('/active', None, self.processActiveGetRequest, methods=['GET'] ) app.add_url_rule('/status', None, self.processStatusGetRequest, methods=['GET'] ) app.add_url_rule('/data/upload', None, self.processDataUploadRequest, methods=['POST']) app.add_url_rule('/data/download', None, self.processDataDownloadRequest, methods=['POST']) app.add_url_rule('/drone/task', None, self.processDroneTaskRequest, methods=['POST']) app.add_url_rule('/drone/detask', None, self.processDroneDetaskRequest, methods=['POST']) app.add_url_rule('/drone/add', None, self.processDroneAddRequest, methods=['POST']) app.add_url_rule('/drone/delete', None, self.processDroneDeleteRequest, methods=['POST']) app.add_url_rule('/alerts', None, self.processAlertGetRequest, methods=['POST']) app.add_url_rule('/alerts/generate', None, self.processAlertGenerateRequest, methods=['POST']) app.add_url_rule('/module/load', None, self.processModuleLoadRequest, methods=['POST']) app.add_url_rule('/module/unload', None, self.processModuleUnloadRequest, methods=['POST']) app.run(threaded=True, port=int(self.config.server_port)) def handleException(self): etb = traceback.format_exc() self.logutil.trace(etb) return self.formatResponse(error=ec.ERROR_GENERAL_UnknownException, data=str(etb)) def formatResponse(self, error, data): return json.dumps({'error':error, 'data':data}) def processActiveGetRequest(self): self.logutil.debug('Processing Active Get Request') return self.formatResponse(error=None, data=True) def processDataUploadRequest(self): self.logutil.debug('Processing Data Upload Request') try: data = json.loads(flask.request.data) packetdata = data.get('pkt') self.database.storePacket(packetdata) return self.formatResponse(error=None, data=None) except Exception: return self.handleException() def processDataDownloadRequest(self): self.logutil.debug('Processing Data Upload Request') try: return self.formatResponse(error=None, data=None) except Exception: return self.handleException() def processDroneTaskRequest(self): self.logutil.debug('Processing Drone Task Request') try: request_data = json.loads(flask.request.data) (error,data) = self.taskDrone(request_data) return self.formatResponse(error,data) except Exception: return self.handleException() def processDroneDetaskRequest(self): self.logutil.debug('Processing Drone Detask Request') try: data = json.loads(flask.request.data) return self.detaskDrone(data) except Exception: return self.handleException() def processDroneAddRequest(self): self.logutil.debug('Processing Drone Add Request') try: data = json.loads(flask.request.data) return self.loadDrone(data) except Exception: return self.handleException() def processDroneDeleteRequest(self): self.logutil.debug('Processing Drone Delete Request') try: data = json.loads(flask.request.data) drone_index = int(data.get('drone_index')) return self.unloadDrone(drone_index) except: return self.handleException() def processModuleLoadRequest(self): self.logutil.debug('Processing Module Load Request') try: data = json.loads(flask.request.data) return self.loadModule(data) except: return self.handleException() def processModuleUnloadRequest(self): self.logutil.debug('Processing Module Unload Request') try: data = json.loads(flask.request.data) module_index = int(data.get('module_index')) return self.unloadModule(module_index) except: return self.handleException() def processAlertGenerateRequest(self): self.logutil.debug('Processing Alert Generate Request') try: data = json.loads(flask.request.data) alert_name = str(data.get('alert_name')) self.database.storeAlert(alert_name) return self.formatResponse(True, None) except: return self.handleException() def processAlertGetRequest(self): #self.logutil.debug('Processing Alert Request') try: alerts = [] for alert in self.database.session.query(Alert).all(): alerts.append('{0} - {1}'.format(microToDate(alert.datetime), alert.name)) return self.formatResponse(None, alerts) except: return self.handleException() def processStatusGetRequest(self): self.logutil.log('Processing Status Request') try: config = self.config.json() modules = list((module.json() for module in self.module_store.values())) tasks = list((task.json() for task in self.task_store.values())) rules = list((rule.json() for rule in self.rule_store.values())) drones = list((drone.json() for drone in self.drone_store.values())) status = {'config':config, 'modules':modules, 'tasks':tasks, 'drones':drones, 'rules':rules} return json.dumps({'success':True, 'data':status}) except: return self.handleException()
class AnalyticModule(Process): def __init__(self, settings, config, shutdown_event, name): Process.__init__(self) self.name = name self.settings = settings self.config = config self.shutdown_event = shutdown_event self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name, None) self.wids_api = WIDSClient(self.config.server_ip, self.config.server_port) self.tasks = {} self.active = False self.running = False def SIGTERM(self, a, b): self.logutil.log('SIGTERM') self.shutdown() def moduleIndex(self): return self.settings.get('module_index') def waitForWIDS(self): while not self.wids_api.isActive(): sleep(0.1) def taskDrone(self, droneIndexList, task_plugin, task_channel, task_parameters, module_index): try: task_uuid = str((uuid4())) (error, data) = self.wids_api.taskDrone(droneIndexList, task_uuid, task_plugin, task_channel, task_parameters, module_index) if error == None: self.tasks[task_uuid] = { 'plugin': task_plugin, 'channel': task_channel, 'parameters': task_parameters, 'drones': droneIndexList, 'uuid': task_uuid, 'module_index': module_index } return task_uuid else: return False except Exception: etb = traceback.format_exc() self.logutil.trace(etb) return False def detaskDrone(self, droneIndexList, uuid): self.logutil.log('Detasking UUID: {0} from Drones: {1}'.format( uuid, droneIndexList)) try: self.wids_api.detaskDrone(droneIndexList, uuid) except Exception: etb = traceback.format_exc() self.logutil.trace(etb) def detaskAll(self): self.logutil.log('Detasking all active tasks ({0} found)'.format( len(self.tasks.values()))) for task in self.tasks.values(): uuid = task.get('uuid') droneIndexList = task.get('drones') self.detaskDrone(droneIndexList, uuid) def getPackets(self, valueFilterList=[], uuidFilterList=[], new=False, maxcount=0, count=False): return self.database.getPackets(valueFilterList, uuidFilterList, new, maxcount, count) def getEvents(self, valueFilterList=[], new=False, maxcount=0, count=False): return self.database.getPackets(valueFilterList, new, maxcount, count) def registerEvent(self, name, details={}, related_packets=[], related_uuids=[]): event_data = { 'module': self.name, 'name': name, 'details': details, 'related_packets': related_packets, 'related_uuids': related_uuids, 'datetime': dateToMicro(datetime.utcnow()) } return self.database.storeEvent(event_data) def generateAlert(self, alert_name): return self.database.storeAlert(alert_name) def cleanup(self): ''' This should be overridden by modules which need to do housekeeping before shutdown. ''' pass def shutdown(self, detask=True): self.logutil.log('Received Shutdown Request') self.cleanup() self.logutil.log('Module Shutdown Complete') sys.exit()
class DroneDaemon: def __init__(self, name, port): signal.signal(signal.SIGINT, self.SIGINT) self.port = port self.name = name self.logutil = KBLogUtil(self.name, 'Daemon', os.getpid()) self.interfaces = {} self.plugins = {} self.pid = os.getpid() def SIGINT(self, s, f): #TODO find a cleaner way to do only handle signals from the parent process ? if self.pid == os.getpid(): self.logutil.log("SIGINT") signal.signal(signal.SIGINT, signal.SIG_IGN) self.shutdown = True self.shutdownDaemon() def handleException(self): etb = traceback.format_exc() print(etb) self.logutil.trace(etb) return json.dumps({'success':False, 'data':str(etb)}) def runChecks(self): try: s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) s.bind(('', self.port)) s.close() except socket.error: print("Error Starting Drone:") print("Socket TCP {0} already bound".format(self.port)) sys.exit() def startDaemon(self): self.runChecks() self.logutil.writePID() self.logutil.startlog() self.logutil.log("Starting DroneDaemon") self.enumerateInterfaces() self.startRestServer() def shutdownDaemon(self): self.logutil.log('Initiating shutdown') self.stopRunningPlugins() self.logutil.log('Completed shutdown') self.logutil.cleanup() # TODO: verify that all subprocess have been terminated sys.exit() def startRestServer(self): self.logutil.log('Starting REST Server on port {0}'.format(self.port)) app = flask.Flask(__name__) app.add_url_rule('/task', None, self.processTaskRequest, methods=['POST']) app.add_url_rule('/detask', None, self.processDetaskRequest, methods=['POST']) app.add_url_rule('/status', None, self.processStatusGetRequest, methods=['POST']) app.run(port=self.port, threaded=True) def handleUnknownException(self): etb = traceback.format_exc() self.logutil.trace(etb) return self.formatResult(error=ec.ERROR_UnknownException, data=str(etb)) def formatResponse(self, error, data): return json.dumps({'error':error, 'data':data}) def processTaskRequest(self): self.logutil.log('Processing Task Request') try: data = json.loads(flask.request.data) uuid = data.get('uuid') plugin = data.get('plugin') channel = data.get('channel') parameters = data.get('parameters') self.logutil.log('Processing Task Request: {0} ({1})'.format(uuid, plugin)) (error,data) = self.taskPlugin(plugin, channel, uuid, parameters) return self.formatResponse(error,data) except Exception: return self.handleUnknownException() def processDetaskRequest(self): self.logutil.log('Processing Detask Request') try: data = json.loads(flask.request.data) uuid = data.get('uuid') (error,data) = self.detaskPlugin(uuid) return self.formatResponse(error,None) except Exception: return self.handleUnknownException() def processStatusGetRequest(self): self.logutil.log('Processing Status Get Request') try: status = {} status['config'] = {} status['config']['pid'] = self.pid status['config']['name'] = self.name status['interfaces'] = list((interface.info() for interface in self.interfaces.values())) status['plugins'] = list((plugin.info() for plugin in self.plugins.values())) return self.formatResponse(None, status) except Exception: self.handleUnknownException() def loadPluginClass(self, plugin): if plugin == 'CapturePlugin': return CapturePlugin def taskPlugin(self, plugin, channel, uuid, parameters): self.logutil.debug('Tasking Plugin ({0},{1})'.format(plugin,channel)) pluginObject = self.plugins.get((plugin,channel), None) if pluginObject == None: self.logutil.log('No Instance of ({0},{1}) Found - Starting New one'.format(plugin, channel)) (error,data) = self.startPlugin(plugin,channel) if error == None: pluginObject = data else: return (error,data) try: self.logutil.log('Tasking Plugin: ({0}, ch.{1}) with Task {2}'.format(plugin, channel, uuid)) success = pluginObject.task(uuid, parameters) if success == False: error = ec.ERROR_DRONE_UnknownTaskingFailure else: error = None return (error,None) except Exception: self.handleException() def startPlugin(self, plugin, channel): self.logutil.debug('Starting Plugin ({0},{1})'.format(plugin,channel)) try: interface = self.getAvailableInterface() if interface == None: self.logutil.log('Failed to Start Plugin - No Avilable Interfaces') error = ec.ERROR_DRONE_UnavailableInterface return (error, None) pluginClass = self.loadPluginClass(plugin) if pluginClass == None: self.logutil.log('Failed to Start Plugin - Plugin Module: {0} does not exist'.format(plugin)) error = ec.ERROR_DroneFailedToLoadPlugin return (error,plugin) self.logutil.log('Acquired Interface: {0}'.format(interface.device)) self.logutil.log('Loaded Plugin Class: {0}'.format(pluginClass)) pluginObject = pluginClass([interface], channel, self.name) self.plugins[(plugin,channel)] = pluginObject self.logutil.log('Successfully Started Plugin') time.sleep(0.5) error = None data = pluginObject return (error,data) except Exception: self.handleException() def detaskPlugin(self, uuid): self.logutil.log('Processing Detask Request for {0}'.format(uuid)) try: for pluginKey,pluginObject in self.plugins.items(): for task_uuid in pluginObject.tasks.keys(): if task_uuid == uuid: detask_success = pluginObject.detask(uuid) if detask_success == False: error = ec.ERROR_DroneUnknownDetaskingFailure return (error,None) time.sleep(2) if pluginObject.active == False: del(self.plugins[pluginKey]) self.logutil.log('Succesfully detasked {0} from {1}'.format(uuid, str(pluginObject.desc))) return (None,None) except Exception: return self.handleException() def stopRunningPlugins(self): self.logutil.log('Stopping Running Plugins') for plugin in self.plugins.values(): if plugin.active == True: self.logutil.log("Stopping Plugin: {0}".format(plugin.desc)) plugin.shutdown() if plugin.active: print("had a problem shutting down plugin") self.logutil.log('Running plugins have been terminated') def getAvailableInterface(self): for interface in self.interfaces.values(): if not interface.active: return interface return None def enumerateInterfaces(self): self.logutil.log("Enumerating Interfaces") try: for interface in kbutils.devlist(): device = interface[0] description = interface[1] self.logutil.log("Added new interface: {0}".format(device)) self.interfaces[device] = KBInterface(device) except Exception: self.handleUnknownException()
class AnalyticModule(Process): def __init__(self, settings, config, shutdown_event, name): Process.__init__(self) self.name = name self.settings = settings self.config = config self.shutdown_event = shutdown_event self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name, None) self.wids_api = WIDSClient(self.config.server_ip, self.config.server_port) self.tasks = {} self.active = False self.running = False def SIGTERM(self,a,b): self.logutil.log('SIGTERM') self.shutdown() def moduleIndex(self): return self.settings.get('module_index') def waitForWIDS(self): while not self.wids_api.isActive(): sleep(0.1) def taskDrone(self, droneIndexList, task_plugin, task_channel, task_parameters, module_index): try: task_uuid = str((uuid4())) (error,data) = self.wids_api.taskDrone(droneIndexList, task_uuid, task_plugin, task_channel, task_parameters, module_index) if error == None: self.tasks[task_uuid] = {'plugin':task_plugin, 'channel':task_channel, 'parameters':task_parameters, 'drones':droneIndexList, 'uuid':task_uuid, 'module_index':module_index} return task_uuid else: return False except Exception: etb = traceback.format_exc() self.logutil.trace(etb) return False def detaskDrone(self, droneIndexList, uuid): self.logutil.log('Detasking UUID: {0} from Drones: {1}'.format(uuid,droneIndexList)) try: self.wids_api.detaskDrone(droneIndexList, uuid) except Exception: etb = traceback.format_exc() self.logutil.trace(etb) def detaskAll(self): self.logutil.log('Detasking all active tasks ({0} found)'.format(len(self.tasks.values()))) for task in self.tasks.values(): uuid = task.get('uuid') droneIndexList = task.get('drones') self.detaskDrone(droneIndexList, uuid) def getPackets(self, valueFilterList=[], uuidFilterList=[], new=False, maxcount=0, count=False): return self.database.getPackets(valueFilterList, uuidFilterList, new, maxcount, count) def getEvents(self, valueFilterList=[], new=False, maxcount=0, count=False): return self.database.getPackets(valueFilterList, new, maxcount, count) def registerEvent(self, name, details={}, related_packets=[], related_uuids=[]): event_data = {'module':self.name, 'name':name, 'details':details, 'related_packets':related_packets, 'related_uuids':related_uuids, 'datetime':dateToMicro(datetime.utcnow())} return self.database.storeEvent(event_data) def generateAlert(self, alert_name): return self.database.storeAlert(alert_name) def cleanup(self): ''' This should be overridden by modules which need to do housekeeping before shutdown. ''' pass def shutdown(self, detask=True): self.logutil.log('Received Shutdown Request') self.cleanup() self.logutil.log('Module Shutdown Complete') sys.exit()
class FilterProcess(Process): def __init__(self, pipe, task_queue, stopevent, task_update_event, drone, parent): super(FilterProcess, self).__init__() self.pipe = pipe self.task_queue = task_queue self.stopevent = stopevent self.taskevent = task_update_event self.drone = drone self.parent = parent self.name = '{0}.Filter'.format(self.parent) self.logutil = KBLogUtil(self.drone, self.name, None) self.callbacks = 0 def do_callback(self, uuid, cburl, pkt): pkt['uuid'] = uuid pkt['datetime'] = dateToMicro(pkt['datetime']) pkt['bytes'] = base64.b64encode(pkt['bytes']) if 0 in pkt: del pkt[0] # Kill KillerBee's backwards compatible keys if 1 in pkt: del pkt[1] if 2 in pkt: del pkt[2] http_headers = {'Content-Type' : 'application/json', 'User-Agent' : 'Drone'} post_data_json = json.dumps({'uuid':uuid, 'pkt':pkt}) post_object = urllib2.Request(cburl, post_data_json, http_headers) try: response = urllib2.urlopen(post_object) self.logutil.debug('Successful Data Upload task {0} data to: {1}'.format(uuid, cburl)) except(IOError): self.logutil.debug('Failed Data Upload task {0} to: {1}'.format(uuid, cburl)) self.callbacks += 1 def run(self): ''' This part runs in a separate process as invoked by Multiprocessing. It recieves packets from the SnifferProcess via a pipe, and compares them against the data currently in the filters Manager. ''' self.logutil.log('Started') tasks = [] while not self.stopevent.is_set(): # check if there are new tasks and update while not self.task_queue.empty(): self.logutil.debug('Detected Tasking Update in Queue') tasks = [] pickleTaskDict = self.task_queue.get_nowait() for uuid,data in cPickle.loads(pickleTaskDict).items(): tasks.append( (uuid, data['filter'], data['callback']) ) self.task_queue.task_done() self.logutil.log('Tasking Updated ({0} tasks total)'.format(len(tasks))) # get packet from sniffer and match against tasked filters try: pkt = self.pipe.recv() self.logutil.debug('Received Packet: {0}'.format(pkt['bytes'].encode('hex'))) self.logutil.dev('Filtering against {0} tasks ({1})'.format(len(tasks), list((x[0] for x in tasks)))) # Do the basic filtering, and run the callback function on packets that match for (uuid, filt, cb) in tasks: # We check to see if the tasking has each test, and # if it does, we see if it meets the defined condition. # If it does not meet a condition, fail out right away. if 'size' in filt: (minB, maxB) = filt['size'] pktB = len(pkt['bytes']) if pktB < minB or pktB > maxB: continue if 'fcf' in filt: (mask, val) = filt['fcf'] if (unpack('>H', pkt['bytes'][0:2])[0] & mask) != val: continue if 'byteoffset' in filt: (offset, mask, val) = filt['byteoffset'] if offset >= len(pkt['bytes']): continue if (unpack('B', pkt['bytes'][offset])[0] & mask) != val: continue # The cases of: # (a) no conditions, aka send all packets, and # (b) unknown condition we don't have coded for # Both come to here and cause a callback to occur self.logutil.debug('Matched Packet against task: {0}'.format(uuid)) self.do_callback(uuid, cb, pkt) except Exception as e: traceback.print_exc() print "Sniffer pipe on the filter end received an IOError, OK at shutdown:", e
class RuleEngine(Process): def __init__(self, config): Process.__init__(self) self.name = 'RuleEngine' self.config = config self.database = DatabaseHandler(self.config.name) self.logutil = KBLogUtil(self.config.name, self.name) self.wids = WIDSClient(self.config.server_ip, self.config.server_port) self.active = None self.rules = [] #///dev/// self.rules.append(rule1) #//////// def run(self): self.logutil.log('Starting Execution') self.active = True self.start_time = dateToMicro(datetime.utcnow()) while self.active: if DEV_DEBUG: self.logutil.debug('Checking for new rules') time.sleep(3) # check server for new rules: 'GET /rules/updatecheck', if so load new rules ''' if self.wids.checkNewRules(): new_rules = self.wids.getNewRules() ''' # evaluate each rule serially self.logutil.debug('Evaluating rules') for RuleObject in self.rules: self.evaluateRule(RuleObject) self.logutil.log('Terminating Execution') # TODO - replace the internal database with a REST call to query database for events def evaluateRule(self, RuleObject): try: self.logutil.dev('Evaluating Rule: {0} (EventIndex: {1})'.format(RuleObject.name, RuleObject.event_index)) for condition in RuleObject.conditions: module = condition[0] event = condition[1] count = condition[2] # TODO - replace this direct database query with REST call ???? query = self.database.session.query(Event).filter(Event.module == module).filter(Event.name == event).filter(Event.datetime > self.start_time).filter(Event.id > RuleObject.event_index) results_count = query.limit(count).count() self.logutil.dev('Event: {0} - Found: {1} (Events Needed: {2})'.format(event, results_count, count)) if not results_count >= count: return False last_result = query.order_by(Event.id.desc()).limit(count).first() RuleObject.event_index = last_result.id self.logutil.log('>>> Rule Conditions Met ({0})'.format(RuleObject.name)) for action in RuleObject.actions: actionType = action[0] actionParams = action[1] if actionType == 'GenerateAlert': self.action_GenerateAlert(RuleObject.name, actionParams) if actionType == 'GenerateLog': self.action_GenerateLog(RuleObject.name, actionParams) except Exception: traceback.print_exc() def action_GenerateLog(self, rule_name, action_parameters): self.logutil.log('Execution GenerateLog Action for Rule {0}'.format(rule_name)) pass def action_GenerateAlert(self, rule_name, action_parameters): self.logutil.log('Executing GenerateAlert Action for Rule {0}'.format(rule_name)) self.wids.generateAlert(rule_name) def shutdown(self): self.active = False self.terminate()
class FilterProcess(Process): def __init__(self, pipe, task_queue, stopevent, task_update_event, drone, parent): super(FilterProcess, self).__init__() self.pipe = pipe self.task_queue = task_queue self.stopevent = stopevent self.taskevent = task_update_event self.drone = drone self.parent = parent self.name = '{0}.Filter'.format(self.parent) self.logutil = KBLogUtil(self.drone, self.name, None) self.callbacks = 0 def do_callback(self, uuid, cburl, pkt): pkt['uuid'] = uuid pkt['datetime'] = dateToMicro(pkt['datetime']) pkt['bytes'] = base64.b64encode(pkt['bytes']) if 0 in pkt: del pkt[0] # Kill KillerBee's backwards compatible keys if 1 in pkt: del pkt[1] if 2 in pkt: del pkt[2] http_headers = { 'Content-Type': 'application/json', 'User-Agent': 'Drone' } post_data_json = json.dumps({'uuid': uuid, 'pkt': pkt}) post_object = urllib2.Request(cburl, post_data_json, http_headers) try: response = urllib2.urlopen(post_object) self.logutil.debug( 'Successful Data Upload task {0} data to: {1}'.format( uuid, cburl)) except (IOError): self.logutil.debug('Failed Data Upload task {0} to: {1}'.format( uuid, cburl)) self.callbacks += 1 def run(self): ''' This part runs in a separate process as invoked by Multiprocessing. It recieves packets from the SnifferProcess via a pipe, and compares them against the data currently in the filters Manager. ''' self.logutil.log('Started') tasks = [] while not self.stopevent.is_set(): # check if there are new tasks and update while not self.task_queue.empty(): self.logutil.debug('Detected Tasking Update in Queue') tasks = [] pickleTaskDict = self.task_queue.get_nowait() for uuid, data in cPickle.loads(pickleTaskDict).items(): tasks.append((uuid, data['filter'], data['callback'])) self.task_queue.task_done() self.logutil.log('Tasking Updated ({0} tasks total)'.format( len(tasks))) # get packet from sniffer and match against tasked filters try: pkt = self.pipe.recv() self.logutil.debug('Received Packet: {0}'.format( pkt['bytes'].encode('hex'))) self.logutil.dev('Filtering against {0} tasks ({1})'.format( len(tasks), list((x[0] for x in tasks)))) # Do the basic filtering, and run the callback function on packets that match for (uuid, filt, cb) in tasks: # We check to see if the tasking has each test, and # if it does, we see if it meets the defined condition. # If it does not meet a condition, fail out right away. if 'size' in filt: (minB, maxB) = filt['size'] pktB = len(pkt['bytes']) if pktB < minB or pktB > maxB: continue if 'fcf' in filt: (mask, val) = filt['fcf'] if (unpack('>H', pkt['bytes'][0:2])[0] & mask) != val: continue if 'byteoffset' in filt: (offset, mask, val) = filt['byteoffset'] if offset >= len(pkt['bytes']): continue if (unpack('B', pkt['bytes'][offset])[0] & mask) != val: continue # The cases of: # (a) no conditions, aka send all packets, and # (b) unknown condition we don't have coded for # Both come to here and cause a callback to occur self.logutil.debug( 'Matched Packet against task: {0}'.format(uuid)) self.do_callback(uuid, cb, pkt) except Exception as e: traceback.print_exc() print "Sniffer pipe on the filter end received an IOError, OK at shutdown:", e
class WIDSDaemon: def __init__(self, parameters=None, config=None): signal.signal(signal.SIGINT, self.SIGINT) self.config = WIDSConfig(parameters, config) self.config.daemon_pid = os.getpid() self.logutil = KBLogUtil(self.config.name, 'Daemon') self.database = DatabaseHandler(self.config.name) self.engine = None self.module_store = {} self.module_counter = 0 self.task_store = {} self.task_counter = 0 self.drone_store = {} self.drone_counter = 0 def SIGINT(self, s, f): if self.config.daemon_pid == os.getpid(): self.logutil.log('SIGINT') self.stopDaemon() def startDaemon(self): self.logutil.writePID() self.logutil.startlog() self.logutil.log('Starting Daemon') self.loadDrones() self.loadModules() self.startServer() def stopDaemon(self): self.logutil.log('Initiating Shutdown') self.unloadModules() self.unloadDrones() self.logutil.log('Successfull Shutdown') self.logutil.cleanup() sys.exit() def loadDrones(self): count = len(self.config.drones) self.logutil.log( 'Loading Drones (Found {0} Drones in the Config)'.format(count)) for droneConfig in self.config.drones: self.loadDrone(droneConfig) def loadDrone(self, droneConfigDict): try: print(droneConfigDict) drone_ip = str(droneConfigDict.get('ip', None)) drone_port = str(droneConfigDict.get('port', None)) if drone_ip == None or drone_port == None: error = 'Error: Missing Parameter: "address"' self.logutil.log(error) return self.formatResponse(error, None) else: droneIndex = self.drone_counter droneObject = DroneContainer(droneIndex, drone_ip, drone_port) self.drone_store[droneIndex] = droneObject self.drone_counter += 1 self.logutil.log('Loading Drone {0} - {1}:{2}'.format( droneIndex, drone_ip, drone_port)) return self.formatResponse(None, None) except: self.handleException() def unloadDrones(self): self.logutil.log('Unloading Drones') self.logutil.log('Found {0} Active Drones'.format(len( self.drone_store))) for i in range(len(self.drone_store)): self.unloadDrone(i) def unloadDrone(self, droneIndexInt): try: droneObject = self.drone_store.get(droneIndexInt, None) if droneObject == None: error = 'Error: Drone with Index {0} does not exist'.format( droneIndexInt) self.logutil.log(error) return self.formatResponse(False, error) else: droneObject.release() self.logutil.log('Releasing Drone {0} - {1}:{2}'.format( droneIndexInt, droneObject.address, droneObject.port)) del (self.drone_store[droneIndexInt]) del (droneObject) return self.formatResponse(True, None) except: self.handleException() def taskDrone(self, taskConfigDict): try: droneIndexList = taskConfigDict.get('droneIndexList') for droneIndexInt in droneIndexList: droneObject = self.drone_store.get(droneIndexInt, None) task_uuid = taskConfigDict.get('uuid', None) task_plugin = taskConfigDict.get('plugin', None) task_channel = taskConfigDict.get('channel', None) task_parameters = taskConfigDict.get('parameters', None) module_index = taskConfigDict.get('module_index', None) if droneObject == None: error = ec.ERROR_DRONE_InvalidDroneIndex data = droneIndexInt return (error, data) if task_uuid == None: error = ec.ERROR_DRONE_MissingDroneTaskParameter data = 'uuid' return (error, data) if task_channel == None: error = ec.ERROR_DRONE_MissingDroneTaskParameter data = 'channel' return (error, data) if task_plugin == None: error = ec.ERROR_MissingDroneTaskParameter data = 'plugin' return (error, data) if task_parameters == None: error = ec.ERROR_MissingDroneTaskParameter data = 'parameters' return (error, data) (data, error) = droneObject.api.task(task_plugin, task_channel, task_uuid, task_parameters) if error == None: self.task_store[self.task_counter] = TaskContainer( self.task_counter, task_uuid, task_plugin, task_channel, task_parameters, droneIndexList, module_index) self.task_counter += 1 return (data, error) except: self.handleException() def detaskDrone(self, droneIndexList, task_uuid): try: for int_DroneIndex in droneIndexList: droneObject = self.drone_store.get(int_DroneIndex, None) droneObject.api.detask(task_uuid) except Exception: self.handleException() def loadModules(self): count = len(self.config.modules) self.logutil.log( 'Loading Modules (Found {0} Modules in the Config)'.format(count)) for moduleConfigDict in self.config.modules: self.loadModule(moduleConfigDict) pass def unloadModules(self): self.logutil.log('Unloading Modules') self.logutil.log('Found {0} Active Modules'.format( len(self.module_store))) for i in range(len(self.module_store)): self.unloadModule(i) def loadModuleClass(self, module): if module == 'BeaconRequestMonitor': return BeaconRequestMonitor if module == 'DisassociationStormMonitor': return DisassociationStormMonitor if module == 'DosAesCtrMonitor': return DosAesCtrMonitor def loadModule(self, moduleConfigDict): self.logutil.debug('Loading Module: {0}'.format(moduleConfigDict)) try: moduleName = moduleConfigDict.get('name', None) moduleSettings = moduleConfigDict.get('settings', None) moduleClass = self.loadModuleClass(moduleName) if moduleName == None: error = ec.ERROR_WIDS_MissingModuleParameter data = 'name' self.logutil.log( 'Failed to Load Module - Missing Parameter: "name" in {0}\n' .format(moduleConfigDict)) return self.formatResponse(error, data) elif moduleSettings == None: error = ec.ERROR_WIDS_MissingModuleParameter data = 'settings' self.logutil.log( 'Failed to Load Module - Missing Parameter: "settings" in {0}\n' .format(moduleConfigDict)) return self.formatResponse(error, data) elif moduleClass == None: error = ec.ERROR_WIDS_MissingModuleClass data = moduleName self.logutil.log( 'Failed to Load Module - Could not load class: {0}'.format( moduleName)) return self.formatResponse(error, data) else: moduleIndex = self.module_counter moduleShutdownEvent = Event() moduleSettings['module_index'] = moduleIndex self.logutil.debug( 'Found module class: {0}'.format(moduleClass)) ''' (error,data) = moduleClass.validate_settings(moduleSettings) if not error == None: return self.formatResponse(error,data) ''' moduleProcess = moduleClass(moduleSettings, self.config, moduleShutdownEvent) moduleProcess.start() moduleObject = ModuleContainer(moduleIndex, moduleName, moduleSettings, moduleProcess, moduleShutdownEvent) self.module_store[moduleIndex] = moduleObject self.module_counter += 1 self.logutil.log('Loading Module {0} - {1}'.format( moduleIndex, moduleObject.name)) return self.formatResponse(None, None) except: self.handleException() def unloadModule(self, moduleIndexInt): try: moduleObject = self.module_store.get(moduleIndexInt, None) if moduleObject == None: error = 'Error: Module with Index {0} does not exist'.format( moduleIndexInt) self.logutil.log(error) return self.formatResponse(False, error) else: self.logutil.log('Unloading Module {0} ({1} - {2})'.format( moduleIndexInt, moduleObject.name, moduleObject.process.pid)) self.logutil.log('Detasking Module Tasks') for taskObject in self.task_store.values(): if taskObject.module_index == moduleObject.index: drones = taskObject.drones uuid = taskObject.uuid self.logutil.log( 'Removing Task {0} from Drones {1}'.format( uuid, drones)) self.detaskDrone(drones, uuid) moduleObject.process.terminate() moduleObject.process.join() del (self.module_store[moduleIndexInt]) del (moduleObject) return self.formatResponse(True, None) except: self.handleException() def startServer(self): self.logutil.log('Starting Server on port {0}'.format( self.config.server_port)) app = flask.Flask(__name__) app.add_url_rule('/active', None, self.processActiveGetRequest, methods=['GET']) app.add_url_rule('/status', None, self.processStatusGetRequest, methods=['GET']) app.add_url_rule('/data/upload', None, self.processDataUploadRequest, methods=['POST']) app.add_url_rule('/data/download', None, self.processDataDownloadRequest, methods=['POST']) app.add_url_rule('/drone/task', None, self.processDroneTaskRequest, methods=['POST']) app.add_url_rule('/drone/detask', None, self.processDroneDetaskRequest, methods=['POST']) app.add_url_rule('/drone/add', None, self.processDroneAddRequest, methods=['POST']) app.add_url_rule('/drone/delete', None, self.processDroneDeleteRequest, methods=['POST']) app.add_url_rule('/alerts', None, self.processAlertGetRequest, methods=['POST']) app.add_url_rule('/alerts/generate', None, self.processAlertGenerateRequest, methods=['POST']) app.add_url_rule('/module/load', None, self.processModuleLoadRequest, methods=['POST']) app.add_url_rule('/module/unload', None, self.processModuleUnloadRequest, methods=['POST']) app.run(threaded=True, port=int(self.config.server_port)) def handleException(self): etb = traceback.format_exc() self.logutil.trace(etb) return self.formatResponse(error=ec.ERROR_GENERAL_UnknownException, data=str(etb)) def formatResponse(self, error, data): return json.dumps({'error': error, 'data': data}) def processActiveGetRequest(self): self.logutil.debug('Processing Active Get Request') return self.formatResponse(error=None, data=True) def processDataUploadRequest(self): self.logutil.debug('Processing Data Upload Request') try: data = json.loads(flask.request.data) packetdata = data.get('pkt') self.database.storePacket(packetdata) return self.formatResponse(error=None, data=None) except Exception: return self.handleException() def processDataDownloadRequest(self): self.logutil.debug('Processing Data Upload Request') try: return self.formatResponse(error=None, data=None) except Exception: return self.handleException() def processDroneTaskRequest(self): self.logutil.debug('Processing Drone Task Request') try: request_data = json.loads(flask.request.data) (error, data) = self.taskDrone(request_data) return self.formatResponse(error, data) except Exception: return self.handleException() def processDroneDetaskRequest(self): self.logutil.debug('Processing Drone Detask Request') try: data = json.loads(flask.request.data) return self.detaskDrone(data) except Exception: return self.handleException() def processDroneAddRequest(self): self.logutil.debug('Processing Drone Add Request') try: data = json.loads(flask.request.data) return self.loadDrone(data) except Exception: return self.handleException() def processDroneDeleteRequest(self): self.logutil.debug('Processing Drone Delete Request') try: data = json.loads(flask.request.data) drone_index = int(data.get('drone_index')) return self.unloadDrone(drone_index) except: return self.handleException() def processModuleLoadRequest(self): self.logutil.debug('Processing Module Load Request') try: data = json.loads(flask.request.data) return self.loadModule(data) except: return self.handleException() def processModuleUnloadRequest(self): self.logutil.debug('Processing Module Unload Request') try: data = json.loads(flask.request.data) module_index = int(data.get('module_index')) return self.unloadModule(module_index) except: return self.handleException() def processAlertGenerateRequest(self): self.logutil.debug('Processing Alert Generate Request') try: data = json.loads(flask.request.data) alert_name = str(data.get('alert_name')) self.database.storeAlert(alert_name) return self.formatResponse(True, None) except: return self.handleException() def processAlertGetRequest(self): #self.logutil.debug('Processing Alert Request') try: alerts = [] for alert in self.database.session.query(Alert).all(): alerts.append('{0} - {1}'.format(microToDate(alert.datetime), alert.name)) return self.formatResponse(None, alerts) except: return self.handleException() def processStatusGetRequest(self): self.logutil.log('Processing Status Request') try: config = self.config.json() modules = list( (module.json() for module in self.module_store.values())) tasks = list((task.json() for task in self.task_store.values())) rules = list((rule.json() for rule in self.rule_store.values())) drones = list( (drone.json() for drone in self.drone_store.values())) status = { 'config': config, 'modules': modules, 'tasks': tasks, 'drones': drones, 'rules': rules } return json.dumps({'success': True, 'data': status}) except: return self.handleException()