def execute(self): """Execute the test.""" TLog.generic("Sending request to server({}) on port({})".format( self.args.rhost, self.args.rport)) TLog.trydo("Searching imaginary database") self.output_handler(found_entry_in_db="FooEntry") # Or if you need to print extra message for only the console # but not required for the actual result output (chaining plugins) self.output_handler( msg="Found matching entry in database - ({})".format("FooEntry"), logkwargs=LOGNO, found_entry_in_db="FooEntry2") snd = "GET / HTTP/1.1" TLog.generic("Sending command to server ({}) on port ({})".format( self.args.rhost, self.args.rport)) if self.args.verbose is True: TLog.generic( "More verbose output. Sending payload ({})".format(snd)) TLog.fail("No response received") TLog.generic("Re-sending command") response = "Response received from the server" # In case of failure (Nothing to do in case of success) if response: self.output_handler(status="Server is vulnerable", services_available=["ssh", "foo"]) else: self.result.setstatus(passed=False, reason="Server is not vulnerable")
def send_receive(self, ip_addr, port, message): """ Send and then receive encrypted data to/from the smart plug. Args: ip_addr(str): The IP address of the smartplug port(int): Port number of the listening service message(str): The plaintext message Returns: bytes: The response received from the smart plug """ response = None sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) try: sock.connect((ip_addr, port)) sock.settimeout(20) sock.send(self.encrypt_decrypt(message)) response = sock.recv(1024) response = self.encrypt_decrypt(response, encrypt=False) except: # noqa: E722 TLog.fail("Couldn't receive/decrypt response.") raise finally: sock.close() return response
def execute(self): """Execute the test.""" TLog.generic( "Sending request to server({}) on port({})".format( self.args.rhost, self.args.rport ) ) TLog.trydo("Searching imaginary database") TLog.success("Found matching entry in database - ({})".format("FooEntry")) snd = "GET / HTTP/1.1" TLog.generic( "Sending command to server ({}) on port ({})".format( self.args.rhost, self.args.rport ) ) if self.args.verbose is True: TLog.generic("More verbose output. Sending payload ({})".format(snd)) TLog.fail("No response received") TLog.generic("Re-sending command") response = "Response received from the server" # In case of failure (Nothing to do in case of success) if response: self.result.setstatus(passed=True, reason="Server is vulnerable") else: self.result.setstatus(passed=False, reason="Server is not vulnerable")
def execute(self): """Execute the plugin.""" TLog.generic( "Publishing message on topic ({}) to MQTT Broker ({}) on port " "({})".format(self.args.topic, self.args.rhost, self.args.rport)) try: client = MqttClient(client_id=self.args.id) client.easy_config( user=self.args.user, passwd=self.args.passwd, on_connect=client.on_connectcb, on_publish=client.on_publishcb, ) client.connect(self.args.rhost, self.args.rport) client.publish(self.args.topic, self.args.msg, 1) client.loop_forever() if client.connect_rc != MQTT_ERR_SUCCESS: self.result.setstatus(passed=False, reason=client.rcstr(client.connect_rc)) TLog.fail("MQTT Connection Failed. Return code ({}:{})".format( client.connect_rc, client.rcstr(client.connect_rc))) else: TLog.success("Message published") except: # noqa: E722 self.result.exception()
def enumerate(self): """ Enumerate the services and/or characteristics of the specified BLE device. :return: """ # Documentation is wrong, the first keyword argument is deviceAddr instead of # deviceAddress. http://ianharvey.github.io/bluepy-doc/ if self.args.services is False and self.args.chars is False: TLog.fail( "Specify the enumerations option(s). Either or both - services, chars" ) self.reason = "Incomplete arguments" return TLog.generic( "Enumerating services/characteristics of the device {}".format( self.args.addr ) ) device = BlePeripheral() try: device.connect( self.args.addr, addrType=( ADDR_TYPE_RANDOM if self.args.randaddrtype else ADDR_TYPE_PUBLIC ), ) self.found = True if self.args.services is True: services = device.getServices() for service in services: TLog.success( "(service uuid={})(handlestart={})(handleend={})".format( service.uuid, hex(service.hndStart), hex(service.hndEnd) ) ) if self.args.chars is True: chars = device.getCharacteristics() for char in chars: TLog.success( "(characteristic uuid={})(handle={})".format( char.uuid, hex(char.getHandle()) ) ) if self.args.verbose is True: support_property = char.propertiesToString() supports_read = char.supportsRead() TLog.success(" (supported_properties={})".format(support_property)) if supports_read is True: TLog.success(" (value={})".format(char.read())) except: # noqa: E722 self.reason = "Exception caught: {}".format(sysexcinfo()) finally: device.disconnect() if self.found is False and self.reason is None: self.reason = "Couldn't find any devices"
def execute(self): """Execute the test.""" TLog.generic( "Attempting to authenticate with the MQTT broker ({}) on port " "({})".format(self.args.rhost, self.args.rport)) found = False try: if self.args.pfile and self.args.user: for password in readlines(self.args.pfile): if self.args.verbose: TLog.generic( "Checking username {} with password {}".format( self.args.user, password)) return_code, state = SimpleMqttClient.connauth( self.args.rhost, client_id=self.args.id, user=self.args.user, passwd=password, port=self.args.rport, ) if return_code == 0: TLog.success( "FOUND - (user={})(passwd={})(return code={}:{})". format(self.args.user, password, return_code, state)) found = True break elif self.args.verbose: TLog.fail( "Auth failed - (user={})(passwd={})(return code={}:{})" .format(self.args.user, password, return_code, state)) if found is False: self.result.setstatus( passed=False, reason="Auth failed for all passwords") else: return_code, state = SimpleMqttClient.connauth( self.args.rhost, client_id=self.args.id, user=self.args.user, passwd=self.args.passwd, port=self.args.rport, ) if return_code == 0: TLog.success( "FOUND - (user={})(passwd={})(return code={}:{})". format(self.args.user, self.args.passwd, return_code, state)) else: self.result.setstatus(passed=False, reason=state) if self.args.verbose: TLog.fail( "Auth failed - (user={})(passwd={})(return code={}:{})" .format(self.args.user, self.args.passwd, return_code, state)) except: # noqa: E722 self.result.exception()
def execute(self): """Execute the test.""" TLog.generic( "Attempting to send file ({}) to DICOM server ({}) on port ({})". format(self.args.file, self.args.rhost, self.args.rport)) TLog.generic("Using Calling AET ({}) Called AET ({})".format( self.args.aetscu, self.args.aetscp)) file = None assoc = None try: app_entity = AE(ae_title=self.args.aetscu) app_entity.requested_contexts = StoragePresentationContexts input_file = open(self.args.file, "rb") dataset = dcmread(input_file, force=True) # 0 means assign random port in pynetdicom if self.args.lport != 0: TLog.generic("Using source port number ({})".format( self.args.lport)) if (self.args.lport < 1024) and (os.geteuid() != 0): TLog.fail("Oops! Need to run as root for privileged port") raise ValueError( "Using privileged port ({}) without root privileges". format(self.args.lport)) assoc = app_entity.associate( self.args.rhost, self.args.rport, bind_address=("", self.args.lport), ae_title=self.args.aetscp, ) TLog.trydo("Server implementation version name ({})".format( assoc.acceptor.implementation_version_name)) TLog.trydo("Server implementation class UID ({})".format( assoc.acceptor.implementation_class_uid)) if assoc.is_established: status = assoc.send_c_store(dataset) if status.Status == 0x0000: TLog.success("C-STORE Success (status=0x{0:04x})".format( status.Status)) else: reason = "C-STORE Failed to store file (status=0x{0:04x})".format( status.Status) TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) else: self.result.setstatus( passed=False, reason="Could not establish association with the server", ) except: # noqa: E722 self.result.exception() finally: if assoc: assoc.release() if file: file.close()
def check_baud(self, baud): """ Scan a serial connection for ASCII data with a given baud rate. :param baud: The baud rate to use for the serial connection :return: Percentage of ASCII characters present in the received data """ sock = None output = { "baud": baud, "ascii_percent": -1, "received_data": None, "ascii_data": None, "status": None, "exception": None } TLog.trydo("Checking baud rate: {}".format(baud)) try: sock = Serial(self.args.port, baud, timeout=self.args.timeout) output["received_data"] = sock.read(self.args.count) sock.flush() output["ascii_data"] = "".join([ chr(entry) for entry in output["received_data"] if chr(entry) in string.printable ]) received_length = len(output["received_data"]) ascii_length = len(output["ascii_data"]) if received_length == 0: output["status"] = "No data received" TLog.fail("\t{}".format(output["status"])) else: output["status"] = "Data received" output["ascii_percent"] = round( ascii_length / received_length * 100, 2) if self.args.verbose: TLog.success("\tdata: {}, ASCII: {}".format( output["received_data"], output["ascii_data"])) TLog.success("\tASCII ratio: {}/{}, {} %".format( ascii_length, received_length, output["ascii_percent"])) except: # noqa: E722 output["exception"] = sysexcinfo() TLog.fail("\tError: {}".format(output["exception"])) finally: if sock: sock.close() self.output_handler(logkwargs=LOGNO, **output) return output["ascii_percent"]
def send_recv(self, ip, port, message): """ Send and then receive encrypted data to/from the smart plug. :param ip: The IP address of the smartplug :param port: Port number of the listening service :param message: The plaintext message :return: The response received from the smart plug """ ret = None sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) try: sock.connect((ip, port)) sock.send(self.cipher(message)) ret = sock.recv(1024) ret = self.cipher(ret, encrypt=False) except: # noqa: E722 TLog.fail("Couldn't receive/decrypt response") finally: sock.close() return ret
def execute(self): """Execute the plugin.""" TLog.generic( "Subscribing to topic ({}) on MQTT broker ({}) on port ({})". format(self.args.topic, self.args.rhost, self.args.rport)) timer = Timer(self.args.timeout) try: client = MqttClient(client_id=self.args.id) client.easy_config(user=self.args.user, passwd=self.args.passwd, on_connect=client.on_connectcb, on_message=MqttSub.on_msg, on_disconnect=client.on_disconnectcb) client.connect(self.args.rhost, self.args.rport) client.loop_start() client.subscribe(self.args.topic, qos=1) while not timer.is_timeout(): sleep(0.1) if client.connect_rc != MQTT_ERR_SUCCESS: self.result.setstatus(passed=False, reason=client.rcstr( client.connect_rc)) TLog.fail( "MQTT Connection Failed. Return code ({}:{})".format( client.connect_rc, client.rcstr(client.connect_rc))) return if client.disconnect_rc != MQTT_ERR_SUCCESS: reason = "Unexpected disconnection. Return code = ({}:{})".format( client.disconnect_rc, client.rcstr(client.disconnect_rc)) self.result.setstatus( passed=False, reason=reason, ) TLog.fail(reason) return client.loop_stop() except: # noqa: E722 self.result.exception()
def execute(self): """ Execute the plugin. Scan for BLE devices in the proximity. Returns: Nothing """ found = False TLog.generic("Scanning BLE devices for {} second(s)".format( self.args.timeout)) try: devices = Ble.scan(iface=self.args.iface, tout=self.args.timeout) for device in devices: found = True outdict = { "name": device.getValueText(Ble.ADTYPE_NAME) or "Unknown", "addr": device.addr, "addrtype": device.addrType, "rssi": "{} dBm".format(device.rssi), "connectable": device.connectable, "adtype_data": [] } for scan_data in device.getScanData(): outdict["adtype_data"].append({ "adtype": scan_data[0], "description": scan_data[1], "value": scan_data[2] }) self.output_handler(**outdict) except: # noqa: E722 self.result.setstatus(passed=False, reason="Exception caught: {}".format( sysexcinfo())) if found is False: TLog.fail("No BLE devices found")
def check_baud(self, baud): """ Scan a serial connection for ASCII data with a given baud rate. :param baud: The baud rate to use for the serial connection :return: Percentage of ASCII characters present in the received data """ sock = None percentage_ascii = -1 TLog.success("Checking baud rate: {}".format(baud)) try: sock = Serial(self.args.port, baud, timeout=self.args.timeout) received = sock.read(self.args.count) sock.flush() ascii_data = "".join([ chr(entry) for entry in received if chr(entry) in string.printable ]) received_length = len(received) ascii_length = len(ascii_data) if received_length == 0: TLog.fail("\tNo data received") else: percentage_ascii = round(ascii_length / received_length * 100, 2) if self.args.verbose: TLog.success("\tdata: {}, ASCII: {}".format( received, ascii_data)) TLog.success("\tASCII ratio: {}/{}, {} %".format( ascii_length, received_length, percentage_ascii)) except: # noqa: E722 TLog.fail("\tError: {}".format(sysexcinfo())) finally: if sock: sock.close() return percentage_ascii
def execute(self): """Execute the test.""" possible_permutations = 0 # Start channel cannot be less than zero or greater than 15 if self.args.start < CHANNEL_MIN or self.args.start > CHANNEL_MAX: self.result.setstatus(passed=False, reason="Invalid start channel.") return # End channel cannot be less than zero or greater than 15 if self.args.end < CHANNEL_MIN or self.args.end > CHANNEL_MAX: self.result.setstatus(passed=False, reason="Invalid end channel.") return # Start and End channel cannot be same if self.args.start == self.args.end: self.result.setstatus(passed=False, reason="Same start and end channel.") return # Start > End channel if self.args.start > self.args.end: self.result.setstatus( passed=False, reason="Start channel greater than end channel.") return # compute possible permutations ch_count = len(range(self.args.start, self.args.end + 1)) if self.args.include_trst: if ch_count < 5: self.result.setstatus( passed=False, reason="Minimum 5 pins required for jtag scan.") return possible_permutations = int( factorial(ch_count) / factorial(ch_count - 5)) else: if ch_count < 4: self.result.setstatus( passed=False, reason="Minimum 4 pins required for jtag scan.") return possible_permutations = int( factorial(ch_count) / factorial(ch_count - 4)) if self.args.volts not in VOLTAGE_RANGE: self.result.setstatus(passed=False, reason="Unsupported target voltage.") return TLog.generic("Start Pin ({}), End Pin ({})".format( self.args.start, self.args.end)) TLog.generic("Target Voltage ({})".format(self.args.volts)) if self.args.include_trst: TLog.generic("TRST pin included in scan") else: TLog.generic("TRST pin excluded from scan") TLog.generic("Possible permutations to be tested: ({})".format( possible_permutations)) TLog.generic("") auditor = None found = False try: auditor = BusAuditor() resp = auditor.jtag_scan(self.args.start, self.args.end, self.args.volts, self.args.include_trst) if resp: found = True TLog.success("JTAG Devices:") for dev in resp: self.output_handler(**dev) except: # noqa: E722 self.result.exception() finally: if auditor: auditor.close() if found is False: TLog.fail("Couldn't find jtag pins")
def execute(self): """Execute the test.""" try: # Step 1 : Connect to socket host:port sock_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock_tcp.connect((self.args.rhost, self.args.rport)) # Step 2 : Send encrypted data and save response data = crypto.encrypt(self.args.data) sock_tcp.settimeout(10.0) sock_tcp.send(data) data_tp = sock_tcp.recv(2048) # Step 3 : Check for Empty or no response if data_tp is None or len(data_tp) == 0: reason = "Empty or no reponse received" TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) else: # Step 4 : Convert bytes array to hex string data_tp = "".join(map(chr, list(data_tp))) data_tp = [hex(ord(b))[2:] for b in list(data_tp)] data_tp = [i if len(i) == 2 else "0" + i for i in data_tp] data_tp = "".join(data_tp) # Step 5 : Decrypt the hex string TLog.generic("Received Response: {}".format(data_tp)) data_tp = crypto.decrypt(data_tp) TLog.generic("Decrypted Response: {}".format(data_tp)) data_tp = json.loads(data_tp) # Step 6 : Check for reason of failture if data_tp.get("system") and\ data_tp.get("system").get("err_msg"): reason = data_tp.get("system").get("err_msg") TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) elif data_tp.get("system") and\ not data_tp.get("system").get("err_msg") and\ data_tp.get("system").get("set_relay_state") and\ data_tp.get("system").get("set_relay_state").get("err_msg"): reason = data_tp.get("system").get("set_relay_state").get( "err_msg") TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) elif data_tp.get("system") and\ not data_tp.get("system").get("err_msg") and\ data_tp.get("system").get("set_relay_state") and\ not data_tp.get("system").get("set_relay_state").get("err_msg"): TLog.generic("Test Passed") else: reason = "Invalid Response." TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) except socket.timeout: reason = "Connection timed out." TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) except socket.error: reason = "Could not connect to host {}:{}".format( self.args.rhost, str(self.args.rport)) TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) finally: if sock_tcp: sock_tcp.close()
def execute(self): """Execute the test.""" if self.args.model not in MODELS: self.result.setstatus( passed=False, reason="Unknown model ({}) specified".format(self.args.model) ) return TLog.generic( "Attempting to search for patient ({}) on DICOM server ({}) on port ({})".format( self.args.name, self.args.rhost, self.args.rport ) ) TLog.generic( "Using Calling AET ({}) Called AET ({}) Information model ({})".format( self.args.aetscu, self.args.aetscp, self.args.model ) ) assoc = None try: app_entity = AE(ae_title=self.args.aetscu) app_entity.requested_contexts = ( QueryRetrievePresentationContexts + BasicWorklistManagementPresentationContexts ) data_set = Dataset() data_set.PatientName = self.args.name # May need to move this as cmdline argument for other SOP Class UIDs data_set.QueryRetrieveLevel = "PATIENT" # 0 means assign random port in pynetdicom if self.args.lport != 0: TLog.generic("Using source port number ({})".format(self.args.lport)) if (self.args.lport < 1024) and (os.geteuid() != 0): TLog.fail("Oops! Need to run as root for privileged port") raise ValueError( "Using privileged port ({}) without root privileges".format( self.args.lport ) ) assoc = app_entity.associate( self.args.rhost, self.args.rport, bind_address=("", self.args.lport), ae_title=self.args.aetscp, ) self.output_handler( tlogtype=TLog.TRYDO, server_implementation_version_name=assoc.acceptor.implementation_version_name, server_implementation_class_uid=assoc.acceptor.implementation_class_uid, ) if assoc.is_established: responses = assoc.send_c_find(data_set, MODELS[self.args.model]) if responses: for (status, identifier) in responses: # As per pynetdicom if status is either of below, then responses contain valid identifier # datasets, else None. Ref: pynetdicom/pynetdicom/apps/findscu/findscu.py # if status.Status in (0xFF00, 0xFF01): statdict = {"cfind_query_status": "0x{0:04x}".format(status.Status), "cfind_query_identifier": str(identifier)} self.output_handler(**statdict) else: reason = "Did not receive any response data sets" TLog.fail(reason) self.result.setstatus(passed=False, reason=reason) else: self.result.setstatus( passed=False, reason="Could not establish association with the server", ) except: # noqa: E722 self.result.exception() finally: if assoc: assoc.release()
def execute(self): """Execute the test.""" # Start channel cannot be less than zero or greater than 15 if self.args.start < CHANNEL_MIN or self.args.start > CHANNEL_MAX: self.result.setstatus(passed=False, reason="Invalid start channel.") return # End channel cannot be less than zero or greater than 15 if self.args.end < CHANNEL_MIN or self.args.end > CHANNEL_MAX: self.result.setstatus(passed=False, reason="Invalid end channel.") return # Start and End channel cannot be same if self.args.start == self.args.end: self.result.setstatus(passed=False, reason="Same start and end channel.") return # Start > End channel if self.args.start > self.args.end: self.result.setstatus( passed=False, reason="Start channel greater than end channel.") return if self.args.volts not in VOLTAGE_RANGE: self.result.setstatus(passed=False, reason="Unsupported target voltage.") return TLog.generic("Start Pin ({}), End Pin ({})".format( self.args.start, self.args.end)) TLog.generic("Target Voltage ({})".format(self.args.volts)) # compute possible permutations ch_count = len(range(self.args.start, self.args.end + 1)) possible_permutations = int( factorial(ch_count) / factorial(ch_count - 2)) TLog.generic("Possible permutations to be tested: ({})".format( possible_permutations)) auditor = None found = False try: auditor = BusAuditor() resp = auditor.uart_scan(self.args.start, self.args.end, self.args.volts) if resp: found = True for dev in resp: self.output_handler(logkwargs=LOGNO, **dev) self.display_uart_scan_result(resp) except: # noqa: E722 self.result.exception() finally: if auditor: auditor.close() if found is False: TLog.fail("Couldn't find uart pins")