def _check_command_support(self, octet, mask): """ Checks if a certain command is supported by the Bluetooth sensor. @param octet The octet of the command. @param mask The bitmask of the command. Both as defined in the Bluetooth specification v4.0 pp. 447 (pdf 693). """ # save current filter old_filter = self.sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # read_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(0x04, 0x0002) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) # Send the Read Local Supported Commands command bluez.hci_send_cmd(self.sock, 0x04, 0x0002) pkt = self.sock.recv(65) status = struct.unpack("65B", pkt) status = status[6:] # restore old filter self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) # Check if the requested bit is set. if len(status) >= octet+1: return status[octet+1] & mask == mask return False
def write_inquiry_mode(sock, mode): """returns 0 on success, -1 on failure""" # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # write_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(bluez.OGF_HOST_CTL, bluez.OCF_WRITE_INQUIRY_MODE) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) # send the command! bluez.hci_send_cmd(sock, bluez.OGF_HOST_CTL, bluez.OCF_WRITE_INQUIRY_MODE, struct.pack("B", mode) ) pkt = sock.recv(255) status = struct.unpack("xxxxxxB", pkt)[0] # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) if status != 0: return -1 return 0
def read_inquiry_scan_activity(sock): """returns the current inquiry scan interval and window, or -1 on failure""" # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # read_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(bluez.OGF_HOST_CTL, bluez.OCF_READ_INQ_ACTIVITY) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) # first read the current inquiry mode. bluez.hci_send_cmd(sock, bluez.OGF_HOST_CTL, bluez.OCF_READ_INQ_ACTIVITY ) pkt = sock.recv(255) status,interval,window = struct.unpack("!xxxxxxBHH", pkt) interval = bluez.btohs(interval) interval = (interval >> 8) | ( (interval & 0xFF) << 8 ) window = (window >> 8) | ( (window & 0xFF) << 8 ) if status != 0: mode = -1 # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return interval, window
def _write_inquiry_tx_power(self, power): """ Returns 0 on success, error status code or -1 on failure. """ if not self._check_command_support(18, 0b10): return -1 # save current filter old_filter = self.sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # read_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(bluez.OGF_HOST_CTL, 0x0059) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) # first read the current inquiry mode. bluez.hci_send_cmd(self.sock, bluez.OGF_HOST_CTL, 0x0059, struct.pack("b", power)) pkt = self.sock.recv(255) status = struct.unpack("xxxxxxB", pkt)[0] # restore old filter self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return status
def find_devices (s, lookup_names=True, duration=8, flush_cache=True): if s.is_inquiring: raise BluetoothError ("Already inquiring!") s.lookup_names = lookup_names s.sock = _gethcisock () flt = _bt.hci_filter_new () _bt.hci_filter_all_events (flt) _bt.hci_filter_set_ptype (flt, _bt.HCI_EVENT_PKT) try: s.sock.setsockopt (_bt.SOL_HCI, _bt.HCI_FILTER, flt) except: raise BluetoothError ("problem with local bluetooth device.") # send the inquiry command max_responses = 255 cmd_pkt = struct.pack ("BBBBB", 0x33, 0x8b, 0x9e, \ duration, max_responses) s.pre_inquiry () try: _bt.hci_send_cmd (s.sock, _bt.OGF_LINK_CTL, \ _bt.OCF_INQUIRY, cmd_pkt) except: raise BluetoothError ("problem with local bluetooth device.") s.is_inquiring = True s.names_to_find = {}
def fetch_rssi(socket, bdaddr): flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) socket.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) cmd_pkt = struct.pack("????") bluez.hci_send_cmd(socket, bluez.OGF_LINK_CTL, bluez.OCF_READ_RSSI, cmd_pkt) pkt = socket.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: pkt = pkt[3:] nrsp = bluetooth.get_byte(pkt[0]) for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) rssi = bluetooth.byte_to_signed_int( bluetooth.get_byte(pkt[1+13*nrsp+i])) results.append( ( addr, rssi ) ) print("[%s] RSSI: [%d]" % (addr, rssi)) elif event == bluez.EVT_CMD_STATUS: status, ncmd, opcode = struct.unpack("BBH", pkt[3:7]) if status != 0: print("uh oh...") done = True elif event == bluez.EVT_INQUIRY_RESULT: pkt = pkt[3:] nrsp = bluetooth.get_byte(pkt[0]) for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) results.append( ( addr, -1 ) ) print("[%s] (no RRSI)" % addr) else: print("unrecognized packet type 0x%02x" % ptype) print("event ", event)
def device_inquiry_with_with_rssi(sock): global FOUND # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) duration = 4 max_responses = 255 cmd_pkt = struct.pack("BBBBB", 0x33, 0x8b, 0x9e, duration, max_responses) bluez.hci_send_cmd(sock, bluez.OGF_LINK_CTL, bluez.OCF_INQUIRY, cmd_pkt) results = [] done = False while not done: pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: pkt = pkt[3:] nrsp = struct.unpack("B", pkt[0])[0] for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) rssi = struct.unpack("b", pkt[1+13*nrsp+i])[0] results.append( ( addr, rssi ) ) print("[%s] RSSI: [%d]" % (addr, rssi)) if addr == ADDR: FOUND = True return elif event == bluez.EVT_INQUIRY_COMPLETE: done = True elif event == bluez.EVT_CMD_STATUS: status, ncmd, opcode = struct.unpack("BBH", pkt[3:7]) if status != 0: print("uh oh...") printpacket(pkt[3:7]) done = True elif event == bluez.EVT_INQUIRY_RESULT: pkt = pkt[3:] nrsp = struct.unpack("B", pkt[0])[0] for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) results.append( ( addr, -1 ) ) print("[%s] (no RRSI)" % addr) else: print("unrecognized packet type 0x%02x" % ptype) print("event ", event) # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return results
def read_inquiry_mode(sock): """returns the current mode, or -1 on failure""" # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # read_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(bluez.OGF_HOST_CTL, bluez.OCF_READ_INQUIRY_MODE) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) # first read the current inquiry mode. bluez.hci_send_cmd(sock, bluez.OGF_HOST_CTL, bluez.OCF_READ_INQUIRY_MODE ) pkt = sock.recv(255) status,mode = struct.unpack("xxxxxxBB", pkt) if status != 0: mode = -1 # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return mode
def _hci_set_le_scan_params(self): # set scan parameter self._old_filter = self._dev_sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) new_filter = bluez.hci_filter_new() bluez.hci_filter_all_events(new_filter) bluez.hci_filter_set_ptype(new_filter, bluez.HCI_EVENT_PKT) self._dev_sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, new_filter)
def Catch_and_Store_advertisement_meassages(sock): global tags_list global semaphore global CHANGES_TO_DATABASE #Setup filter to receive only the events what we need flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) # Enable all events, then mask it with HCI_EVENT_PKT = 0x04 check bluez source/lib/hci.h bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) #HCI Packet types: Bluetooth specification (4.2) page 2406, Vol 4, Part A, Section: 2 - Protocol sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) #(socket level)SOL_HCI = 0 check bluez source/lib/bluetooth.h while(True): if(BLOCK_THREADS == False): try: packet = sock.recv(46) if packet: entry = process_BLE_packet(packet) if entry: tags_list.append(entry) if (len(tags_list)>20): semaphore.acquire() status = update_detected_tags(tags_list) tags_list =[] CHANGES_TO_DATABASE = 1 semaphore.release() except Exception,e: error_reporting(("ERROR - Catch_and_Store_advertisement_meassages..." + str(e))) else: print "close ble thread..." break
def find_local_bdaddr(self): dev_id = 0 hci_sock = _bt.hci_open_dev(dev_id) old_filter = hci_sock.getsockopt( _bt.SOL_HCI, _bt.HCI_FILTER, 14) flt = _bt.hci_filter_new() opcode = _bt.cmd_opcode_pack(_bt.OGF_INFO_PARAM, _bt.OCF_READ_BD_ADDR) _bt.hci_filter_set_ptype(flt, _bt.HCI_EVENT_PKT) _bt.hci_filter_set_event(flt, _bt.EVT_CMD_COMPLETE); _bt.hci_filter_set_opcode(flt, opcode) hci_sock.setsockopt(_bt.SOL_HCI, _bt.HCI_FILTER, flt) _bt.hci_send_cmd(hci_sock, _bt.OGF_INFO_PARAM, _bt.OCF_READ_BD_ADDR) pkt = hci_sock.recv(255) status,raw_bdaddr = struct.unpack("xxxxxxB6s", pkt) assert status == 0 t = [ "%X" % ord(b) for b in raw_bdaddr ] t.reverse() bdaddr = ":".join(t) # restore old filter hci_sock.setsockopt( _bt.SOL_HCI, _bt.HCI_FILTER, old_filter ) return bdaddr
def Listen(self): try: old_filter = self.sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on blue tooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) while True: pkt = self.sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: # print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): if DEBUG == True: print "-------------" print "\t", "full packet: ", self.printpacket(pkt) print "\t", "MAC address: ", self.packed_bdaddr_to_string( pkt[report_pkt_offset + 3 : report_pkt_offset + 9] ) # build the return string id = pkt[report_pkt_offset + 12 : report_pkt_offset + 26] if DEBUG == True: print "\t", "id: ", id if id == "MSOT_BLE_Demo:": # MAC address macAddress = self.packed_bdaddr_to_string( pkt[report_pkt_offset + 3 : report_pkt_offset + 9] ) # string representation of Water Volume Content (unit-less) floating point value value = pkt[report_pkt_offset + 26 : report_pkt_offset + 36] if DEBUG == True: print "\t", "address=", macAddress, " value=", value if self.callback != None: print "calling event handler" self.callback(macAddress, value) except: self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) print "error in BLE Listen loop" sys.exit(1)
def save_filter(sock): # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) return old_filter
def handle_events(self, callback=None): if callback is None: callback = self.print_detect self.old_filter = self.sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) self.sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) while True: pkt = self.sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if DEBUG: print "-------------- ptype: 0x%02x event: 0x%02x plen: 0x%02x" % (ptype, event, plen) if event != LE_META_EVENT: continue subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if DEBUG: print "LE META EVENT subevent: 0x%02x" %(subevent,) if subevent != EVT_LE_ADVERTISING_REPORT: continue if DEBUG: print "advertising report" num_reports, = struct.unpack("B", pkt[0]) report_pkt_offset = 0 if DEBUG: print "Number of reports in the report: 0x%02x" % num_reports for i in range(0, num_reports): if DEBUG: print "report", i report_event_type = struct.unpack("B", pkt[report_pkt_offset + 1])[0] bdaddr_type = struct.unpack("B", pkt[report_pkt_offset + 2])[0] if DEBUG: print "\tadvertising report event type: 0x%02x" % report_event_type if DEBUG: print "\tbdaddr type: 0x%02x" % (bdaddr_type,) bdaddr = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) if DEBUG: print "\tdevice address: ", bdaddr report_data_length, = struct.unpack("B", pkt[report_pkt_offset + 9]) if DEBUG: print "\tadvertising packet metadata length: ", report_data_length report_event_type_human = ADV_TYPES.get(report_event_type, 'Unknown(%s)' % report_event_type) if DEBUG: print "\ttype: ", report_event_type_human name = None if report_event_type == ADV_SCAN_RSP: local_name_len, = struct.unpack("B", pkt[report_pkt_offset + 11]) # TODO: the line below is probably bugged name = pkt[report_pkt_offset + 12:report_pkt_offset + 12+local_name_len].split('\x00')[0] if DEBUG: print "\tname:", name # each report is 2 (event type, bdaddr type) + 6 (the address) # + 1 (data length field) + data length + 1 (rssi) report_pkt_offset = report_pkt_offset + 10 + report_data_length + 1 rssi, = struct.unpack("b", pkt[report_pkt_offset -1]) if DEBUG: print "\tRSSI:", rssi callback(bdaddr, rssi, report_event_type_human, name)
def device_inquiry_with_with_rssi(sock, wanted_addr): global results # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) duration = 4 max_responses = 255 # 0x9e8b33 is the reserved code for general inquiry of Bluetooth devices cmd_pkt = struct.pack("BBBBB", 0x33, 0x8b, 0x9e, duration, max_responses) bluez.hci_send_cmd(sock, bluez.OGF_LINK_CTL, bluez.OCF_INQUIRY, cmd_pkt) done = False while not done: pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: pkt = pkt[3:] nrsp = struct.unpack("B", pkt[0])[0] for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) rssi = struct.unpack("b", pkt[1+13*nrsp+i])[0] if addr == wanted_addr: results.append( rssi ) # print "*** ", # print "[%s] RSSI: [%d]" % (addr, rssi) elif event == bluez.EVT_INQUIRY_COMPLETE: done = True elif event == bluez.EVT_CMD_STATUS: status, ncmd, opcode = struct.unpack("BBH", pkt[3:7]) if status != 0: print "uh oh..." done = True else: # print "unrecognized packet type 0x%02x" % ptype continue # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) if len(results) > 10: results = results[-10:] return results
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) done = False results = [] myFullList = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack('BBB', pkt[:3]) #print '--------------' if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i =0 elif event == bluez.EVT_NUM_COMP_PKTS: i =0 elif event == bluez.EVT_DISCONN_COMPLETE: i =0 elif event == LE_META_EVENT: subevent, = struct.unpack('B', pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print 'advertising report' num_reports = struct.unpack('B', pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): #print '\tfullpacket: ', printpacket(pkt) device = bledevice() device.udid = returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset - 6]) device.major = returnnumberpacket(pkt[report_pkt_offset -6: report_pkt_offset - 4]) device.minor = returnnumberpacket(pkt[report_pkt_offset -4: report_pkt_offset - 2]) device.macaddress = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) device.txpower = struct.unpack('b', pkt[report_pkt_offset -2]) device.rssi = struct.unpack('b', pkt[report_pkt_offset -1]) #print returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset - 6]) #print returnnumberpacket(pkt[report_pkt_offset -6: report_pkt_offset - 4]) #print returnnumberpacket(pkt[report_pkt_offset -4: report_pkt_offset - 2]) #print packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) #print struct.unpack('b', pkt[report_pkt_offset -2]) #print struct.unpack('b', pkt[report_pkt_offset -1]) myFullList.append(device) done = True sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return myFullList
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) done = False results = [] myFullList = [] beacons = {} for i in range(0, loop_count): sock.settimeout(10) try: pkt = sock.recv(255) except (socket.timeout, socket.error, bluez.timeout) as e: print "Connection error: {}".format(e) return {} ptype, event, plen = struct.unpack("BBB", pkt[:3]) #print "--------------" if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i =0 elif event == bluez.EVT_NUM_COMP_PKTS: i =0 elif event == bluez.EVT_DISCONN_COMPLETE: i =0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): beacon_data = {} beacon_data['udid'] = returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset - 6]) beacon_data['major'] = returnstringpacket(pkt[report_pkt_offset -6: report_pkt_offset - 4]) beacon_data['minor'] = returnstringpacket(pkt[report_pkt_offset -4: report_pkt_offset - 2]) mac_addr = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) beacon_data['txpower'] = struct.unpack("b", pkt[report_pkt_offset -2]) beacon_data['rssi'] = struct.unpack("b", pkt[report_pkt_offset -1]) beacons[mac_addr] = beacon_data done = True sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return beacons
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) message = dict() for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) #print "--------------" if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 mac = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) for i in range(0, num_reports): if mac not in message: message[mac] = {'uuid': returnstringpacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]), 'majorid': returnnumberpacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]), 'minorid': returnnumberpacket(pkt[report_pkt_offset - 4:report_pkt_offset - 2]), 'calibratedtx': struct.unpack("b", pkt[report_pkt_offset - 2])[0], 'rssi': struct.unpack("b", pkt[report_pkt_offset - 1])[0] } if DEBUG: print "\n-------------" print "\tUDID: ", printpacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]) print "\tMAJOR: ", printpacket(pkt[report_pkt_offset - 6:report_pkt_offset - 4]) print "\tMINOR: ", printpacket(pkt[report_pkt_offset - 4:report_pkt_offset - 2]) print "\tMAC address: ", packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) # commented out - don't know what this byte is. It's NOT TXPower LOOK AT BLE Specification print "\t(Unknown):", struct.unpack("b", pkt[report_pkt_offset - 2]) print "\tRSSI:", struct.unpack("b", pkt[report_pkt_offset - 1]) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return message
def device_inquiry_with_with_rssi(sock): # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) duration = 4 max_responses = 255 cmd_pkt = struct.pack("BBBBB", 0x33, 0x8b, 0x9e, duration, max_responses) bluez.hci_send_cmd(sock, bluez.OGF_LINK_CTL, bluez.OCF_INQUIRY, cmd_pkt) results = [] done = False while not done: pkt = sock.recv(255) __, event, __ = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: pkt = pkt[3:] nrsp = bluetooth.get_byte(pkt[0]) for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) rssi = bluetooth.byte_to_signed_int( bluetooth.get_byte(pkt[1+13*nrsp+i])) results.append( ( addr, rssi ) ) elif event == bluez.EVT_INQUIRY_COMPLETE: done = True elif event == bluez.EVT_CMD_STATUS: status, __, __ = struct.unpack("BBH", pkt[3:7]) if status != 0: done = True elif event == bluez.EVT_INQUIRY_RESULT: pkt = pkt[3:] nrsp = bluetooth.get_byte(pkt[0]) for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) results.append( ( addr, -1 ) ) # restore old filter sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return results
def parse_le_events(socket): old_filter = socket.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) nfilter = bluez.hci_filter_new() bluez.hci_filter_all_events(nfilter) # HCI_EVENT_PKT = 0x04 bluez.hci_filter_set_ptype(nfilter, bluez.HCI_EVENT_PKT) # socket.setsockopt(level, optname, value) socket.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, nfilter) bluez.hci_send_cmd(socket, bluez.OGF_HOST_CTL, bluez.OCF_READ_INQUIRY_MODE ) #while(true): for i in range(0, 5000): pkt = socket.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) # BLE EVENTS if event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): report_event_type = struct.unpack("B", pkt[report_pkt_offset + 1])[0] bdaddr_type = struct.unpack("B", pkt[report_pkt_offset + 2])[0] report_data_length, = struct.unpack("B", pkt[report_pkt_offset + 9]) payload = "{" payload += "\"addr\": \"%s\"" % packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) report_pkt_offset = report_pkt_offset + 10 + report_data_length + 1 rssi, = struct.unpack("b", pkt[report_pkt_offset -1]) payload += ", \"rssi\": %s " % rssi payload += ", \"source\": \"%s\" " % adress payload += ", \"captured\": \"%s\"" % datetime.datetime.now().isoformat() payload += "}" print payload requests.post(url, data=payload, headers=headers) #requests.post(url, data=json.dumps(payload), headers=headers) sleep(1.00) socket.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter )
def process_ble_advertisements(sock, loop_count=100): def packet2string(pkt): return ''.join(map(lambda x: "%02x" % struct.unpack("B", x)[0], pkt)) def packed_bdaddr_to_string(bdaddr_packed): return ':'.join('%02x'%i for i in struct.unpack("<BBBBBB", bdaddr_packed[::-1])) def fmt_major_minor(value): return sum(map(lambda c: struct.unpack("B", c)[0], value[1:]), struct.unpack("B", value[0])[0] * 256.0) old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) reports = {} for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 if not isBean.match(packet2string(pkt[report_pkt_offset-22: report_pkt_offset-6])): continue for i in range(0, num_reports): report = { "udid": packet2string(pkt[report_pkt_offset - 22: report_pkt_offset - 6]), "temp": fmt_major_minor(pkt[report_pkt_offset - 6: report_pkt_offset - 4]), "sg": fmt_major_minor(pkt[report_pkt_offset - 4: report_pkt_offset - 2]) / 1000.0, "addr": packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) } reports[report["addr"]] = report sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return reports
def parse_events(sock, loop_count=100): flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) for i in range(loop_count): pkt = sock.recv(255) parsed_packet = ble.hci_le_parse_response_packet(pkt) if ( "bluetooth_le_subevent_name" in parsed_packet and parsed_packet["bluetooth_le_subevent_name"] == "EVT_LE_ADVERTISING_REPORT" ): for report in parsed_packet["advertising_reports"]: print "Found BLE device:", report["peer_bluetooth_address"] for k, v in report.items(): print "\t%s: %s" % (k, v)
def create_socket(self): try: self.socket = bluez.hci_open_dev(self.dev_id) except: raise BluetoothError.BluetoothError("Error al acceder al dispositivo") return # Establece el filtro para recibir todos los eventos flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) try: # Establece opciones: nivel nombre opción valor self.socket.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) except: raise BluetoothError.BluetoothError("Problema al establecer filtro de eventos.") return
def parse_events(sock, loop_count, source, influx, coll, lastDoc): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) points = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) now = datetime.datetime.now(tzlocal()) nowMs = int(time.time() * 1000) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: print "EVT_INQUIRY_RESULT_WITH_RSSI" elif event == bluez.EVT_NUM_COMP_PKTS: print "EVT_NUM_COMP_PKTS" elif event == bluez.EVT_DISCONN_COMPLETE: print "EVT_DISCONN_COMPLETE" elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3:4]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: pass elif subevent == EVT_LE_ADVERTISING_REPORT: rows = list(evt_le_advertising_report_dump(pkt)) for row in sorted(rows): rssi = row.pop('rssi') if row['addr_type'] == 'Public': # or, someday, if it's a device we know points.append(dict( measurement='rssi', tags={'from': source, 'toAddr': row['addr']}, fields={'value': rssi}, time=nowMs, )) key = (row['addr'], row['evt_type']) if lastDoc.get(key) != row: # should check mongodb here- maybe another # node already wrote this row lastDoc.put(key, row) row = row.copy() row['t'] = now coll.insert(row) influx.write_points(points, time_precision='ms') sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter )
def createSocket(port_id): try: sock = bluez.hci_open_dev(port_id) print "ble thread started on ", port_id blescan.hci_le_set_scan_parameters(sock) blescan.hci_enable_le_scan(sock) old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) test.append(sock) except: print "error accessing bluetooth device on ", port_id
def run(self): """Continously scan for BLE advertisements.""" self.socket = bluez.hci_open_dev(self.bt_device_id) filtr = bluez.hci_filter_new() bluez.hci_filter_all_events(filtr) bluez.hci_filter_set_ptype(filtr, bluez.HCI_EVENT_PKT) self.socket.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, filtr) self.toggle_scan(True) while self.keep_going: pkt = self.socket.recv(255) event = to_int(pkt[1]) subevent = to_int(pkt[3]) if event == LE_META_EVENT and subevent == EVT_LE_ADVERTISING_REPORT: # we have an BLE advertisement self.process_packet(pkt)
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) results = {} for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for x in range(0, num_reports): txpower, = struct.unpack("b", pkt[report_pkt_offset - 2]) rssi, = struct.unpack("b", pkt[report_pkt_offset - 1]) results[ ( packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]), returnstringpacket(pkt[report_pkt_offset - 22: report_pkt_offset - 6]), returnnumberpacket(pkt[report_pkt_offset - 6: report_pkt_offset - 4]), returnnumberpacket(pkt[report_pkt_offset - 4: report_pkt_offset - 2]) ) ] = { 'udid': returnstringpacket(pkt[report_pkt_offset - 22: report_pkt_offset - 6]), 'mac': packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]), 'major': returnnumberpacket(pkt[report_pkt_offset - 6: report_pkt_offset - 4]), 'minor': returnnumberpacket(pkt[report_pkt_offset - 4: report_pkt_offset - 2]), 'rssi': rssi, 'txpower': txpower } sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return results
def parse_events(sock, loop_count=30): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) # result = {} # sock.setblocking(0) # sock.settimeout(1.0) try: pkt = sock.recv(255) except Exception as e: print("Error in socket receiving, reason: ", str(e)) return False else: if not pkt: print "no data received by sock" return False else: ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 # print pkt device_type = findDeviceType("BLESCAN", pkt) if (device_type != None): jsonDict = parseDeviceStruct(deviceStruct(device_type), pkt) return jsonDict else: print "Wrong Device Type" return False else: print "Not advertising data" return False else: print "Not LE Meta Event" return False
def getBeacons(sock, loop_count=10): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) done = False results = [] beaconsList = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) #print "--------------" if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i =0 elif event == bluez.EVT_NUM_COMP_PKTS: i =0 elif event == bluez.EVT_DISCONN_COMPLETE: i =0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): pass beacon = {'uuid': 'none', 'rssi': 0} beacon['uuid'] = returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset - 6]) beacon['rssi'] = struct.unpack("b", pkt[report_pkt_offset -1]) beaconsList.append(beacon) done = True sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return beaconsList
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) myFullList = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3:4]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0:1])[0] report_pkt_offset = 0 for i in range(0, num_reports): # build the return string Adstring = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) Adstring += ',' + returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset - 6]) #Adstring += ',' + "%i" % returnnumberpacket(pkt[report_pkt_offset -6: report_pkt_offset - 4]) Adstring += ',' + returnstringpacket(pkt[report_pkt_offset -6: report_pkt_offset - 4]) #Adstring += ',' + "%i" % returnnumberpacket(pkt[report_pkt_offset -4: report_pkt_offset - 2]) Adstring += ',' + returnstringpacket(pkt[report_pkt_offset -4: report_pkt_offset - 2]) try: #Adstring += ',' + "%i" % struct.unpack("b", pkt[report_pkt_offset -2:report_pkt_offset -1]) Adstring += ',' + returnstringpacket(pkt[report_pkt_offset -2:report_pkt_offset -1]) #The last byte is always 00; we don't really need it #Adstring += ',' + "%i" % struct.unpack("b", pkt[report_pkt_offset -1:report_pkt_offset]) #Adstring += ',' + returnstringpacket(pkt[report_pkt_offset -1:report_pkt_offset]) except: 1 #Prevent duplicates in results if Adstring not in myFullList: myFullList.append(Adstring) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return myFullList
def get_localAdapter(self, deviceNr): "Return name and address of a local adapter" name = None address = None sock = bt.hci_open_dev(deviceNr) if sock.getsockid() >= 0: sock.settimeout(3) # Save original filter orig_filter = sock.getsockopt(bt.SOL_HCI, bt.HCI_FILTER, 14) # Create new filter new_filter = orig_filter new_filter = bt.hci_filter_new() bt.hci_filter_set_ptype(new_filter, bt.HCI_EVENT_PKT) bt.hci_filter_set_event(new_filter, bt.EVT_CMD_COMPLETE) # CMD Read local name opcode = bt.cmd_opcode_pack(bt.OGF_HOST_CTL, bt.OCF_READ_LOCAL_NAME) bt.hci_filter_set_opcode(new_filter, opcode) sock.setsockopt(bt.SOL_HCI, bt.HCI_FILTER, new_filter) bt.hci_send_cmd(sock, bt.OGF_HOST_CTL, bt.OCF_READ_LOCAL_NAME) try: data = sock.recv(255) name = data[7:] name = name[:name.find('\0')] except bluetooth._bluetooth.timeout: print 'bluetooth timeout during local device scan for name' # CMD Read local address opcode = bt.cmd_opcode_pack(bt.OGF_INFO_PARAM, bt.OCF_READ_BD_ADDR) bt.hci_filter_set_opcode(new_filter, opcode) sock.setsockopt(bt.SOL_HCI, bt.HCI_FILTER, new_filter) bt.hci_send_cmd(sock, bt.OGF_INFO_PARAM, bt.OCF_READ_BD_ADDR) try: data = sock.recv(255) status, raw_bdaddr = struct.unpack('xxxxxxB6s', data) address = ['%02X' % ord(b) for b in raw_bdaddr] address.reverse() address = ':'.join(address) except bluetooth._bluetooth.timeout: print 'bluetooth timeout during local device scan for address' # Restore original filter sock.setsockopt(bt.SOL_HCI, bt.HCI_FILTER, orig_filter) sock.close() return name, address
def hci_le_set_scan_parameters(sock): SCAN_TYPE = 0x01 INTERVAL = 0x10 WINDOW = 0x10 OWN_TYPE = 0x00 FILTER = 0x00 # all advertisements, not just whitelisted devices cmd_pkt = struct.pack("<BBBBBBB", SCAN_TYPE, 0x0, INTERVAL, 0x0, WINDOW, OWN_TYPE, FILTER) bluez.hci_send_cmd(sock, OGF_LE_CTL, OCF_LE_SET_SCAN_PARAMETERS, cmd_pkt) old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) filtr = bluez.hci_filter_new() bluez.hci_filter_all_events(filtr) bluez.hci_filter_set_ptype(filtr, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(filtr, LE_META_EVENT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, filtr)
def scan(devices): try: # Open the bluetooth device sock = bluez.hci_open_dev(0) except: # Failed to open sock = None if sock: # We have device access, start BLE scan cmd_pkt = struct.pack("<BB", 0x01, 0x00) bluez.hci_send_cmd(sock, OGF_LE_CTL, OCF_LE_SET_SCAN_ENABLE, cmd_pkt) time_pre = datetime.datetime.now() while True: # Save the current filter setting old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Set filter for getting HCI events flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) # Get and decode data buffers = sock.recv(255) mac_address, rssi, tx_power = process_input(buffers) if mac_address != None: devices.append(mac_address, rssi, tx_power) time_now = datetime.datetime.now() if (time_now - time_pre).total_seconds() > env.TIME_INTERVAL: break #Restore the filter setting sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) clients = devices.get_device() if DEBUG: print(clients) send(clients)
def __init__(self, callback=None): try: self.sock = sock = bluez.hci_open_dev() except: raise OSError("error accessing bluetooth device...") self.callback = callback or self._print_data # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices self.flt = bluez.hci_filter_new() bluez.hci_filter_all_events(self.flt) bluez.hci_filter_set_ptype(self.flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, self.flt) self.parser_thread = Thread(target=self.parse_events) self.parser_thread.daemon = True self.parser_thread.start()
def init(self): if self.on_message is None: raise NoCallBackException('callback function is none. Please set self.on_message') self.sock = deviceOpen(self.device_id) hci_le_set_scan_parameters(self.sock) hci_le_enable_scan(self.sock) # preserve old filter setting old_filter = self.sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt)
def reset(self) -> dict: dd = hci_open_dev(self.devid) flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode(flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_RESET)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_RESET) event_params = dd.recv(3 + EVT_CMD_COMPLETE_SIZE + 1)[3:] num_hci_cmd_pkts, cmd_opcode, status = struct.unpack( '<BHB', event_params) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status } hci_close_dev(dd.fileno()) return event_params
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) beacons = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack('BBB', pkt[:3]) if event == LE_META_EVENT: subevent = pkt[3] pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = pkt[0] report_pkt_offset = 0 for i in range(0, num_reports): uuid = returnstringpacket(pkt[report_pkt_offset - 22: report_pkt_offset - 6]) #if one of the beacons matches known tilt keys (only purple matters) if uuid in TILTS.keys(): beacons.append({ 'color': TILTS.get(uuid), 'grav': returnnumberpacket(pkt[report_pkt_offset - 4: report_pkt_offset - 2])/1000, 'temp': returnnumberpacket(pkt[report_pkt_offset - 6: report_pkt_offset - 4]) }) #I only have 1 tilt for now, so just break and return the valid datapoint break done = True #WHAT IS THIS???? # Quit scanning after the first hit if len(beacons) > 0 : break sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return beacons
def read_remote_extended_features(self, cmd_params: dict) -> dict: ''' cmd_params -- { 'Connection_Handle': 0x0000 to 0x0EFF, 'Page_Number': int } ''' dd = hci_open_dev(self.devid) bin_cmd_params = cmd_params[ 'Connection_Handle'].to_bytes(2, 'little') + \ cmd_params['Page_Number'].to_bytes(1, 'little') flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_READ_REMOTE_EXT_FEATURES_COMPLETE) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_LINK_CTL, OCF_READ_REMOTE_EXT_FEATURES, bin_cmd_params) while True: event_params = dd.recv(3 + \ EVT_READ_REMOTE_EXT_FEATURES_COMPLETE_SIZE)[3:] status, conn_handle, page_num, max_page_num, ext_lmp_features = \ struct.unpack('<BHBB8s', event_params) event_params = { 'Status': status, 'Connection_Handle': conn_handle, 'Page_Number': page_num, 'Maximum_Page_Number': max_page_num, 'Extended_LMP_Features': ext_lmp_features } if event_params['Connection_Handle'] == cmd_params['Connection_Handle'] and \ event_params['Page_Number'] == cmd_params['Page_Number']: break hci_close_dev(dd.fileno()) return event_params
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) done = False results = [] Adstring = '' for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): if returnstringpacket( pkt[report_pkt_offset - 22:report_pkt_offset - 6]) == "7ae665810af04d0ab947b85635f21d91": Adstring = struct.unpack("b", pkt[report_pkt_offset - 1])[0] if Adstring != '': Adstring = float(Adstring) done = True sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return Adstring
def parseEvents(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush # its cache of previosuly discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) beacons = [] for i in range(0, loop_count): pkt = sock.recv(255) pktype, event, plen = struct.unpack('BBB', pkt[:3]) if event == LE_META_EVENT: subevent, = struct.unpack('B', pkt[3:4]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack('B', pkt[0:1])[0] report_pkt_offset = 0 for i in range(0, num_reports): beacons.append({ 'uuid': returnStringPacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]), 'minor': returnNumberPacket(pkt[report_pkt_offset - 4:report_pkt_offset - 2]), 'major': returnNumberPacket(pkt[report_pkt_offset - 6:report_pkt_offset - 4]) }) done = True sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return beacons
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) myFullList = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for _ in range(0, num_reports): Adstring = packed_bdaddr_to_string( pkt[report_pkt_offset + 3:report_pkt_offset + 9]) Adstring += "," Adstring += returnstringpacket( pkt[report_pkt_offset - 22:report_pkt_offset - 6]) Adstring += "," Adstring += "%i" % returnnumberpacket( pkt[report_pkt_offset - 6:report_pkt_offset - 4]) Adstring += "," Adstring += "%i" % returnnumberpacket( pkt[report_pkt_offset - 4:report_pkt_offset - 2]) Adstring += "," Adstring += "%i" % struct.unpack( "b", pkt[report_pkt_offset - 2]) Adstring += "," Adstring += "%i" % struct.unpack( "b", pkt[report_pkt_offset - 1]) myFullList.append(Adstring) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return myFullList
def set_bt_name(payload, src_hci, src, dst): # Create raw HCI sock to set our BT name raw_sock = bt.hci_open_dev(bt.hci_devid(src_hci)) flt = bt.hci_filter_new() bt.hci_filter_all_ptypes(flt) bt.hci_filter_all_events(flt) raw_sock.setsockopt(bt.SOL_HCI, bt.HCI_FILTER, flt) # Send raw HCI command to our controller to change the BT name (first 3 bytes are padding for alignment) raw_sock.sendall(binascii.unhexlify('01130cf8cccccc') + payload.ljust(MAX_BT_NAME, b'\x00')) raw_sock.close() #time.sleep(1) time.sleep(0.1) # Connect to BNEP to "refresh" the name (does auth) bnep = bluetooth.BluetoothSocket(bluetooth.L2CAP) bnep.bind((src, 0)) bnep.connect((dst, BNEP_PSM)) bnep.close() # Close ACL connection os.system('hcitool dc %s' % (dst,))
def device_inquiry_with_with_rssi(sock): # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) #filter duration = 4 max_responses = 255 cmd_pkt = struct.pack("BBBBB", 0x33, 0x8b, 0x9e, duration, max_responses) bluez.hci_send_cmd(sock, bluez.OGF_LINK_CTL, bluez.OCF_INQUIRY, cmd_pkt) #send command results = [] done = False while not done: pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: pkt = pkt[3:] nrsp = bluetooth.get_byte(pkt[0]) for i in range(nrsp): addr = bluez.ba2str( pkt[1+6*i:1+6*i+6] ) rssi = bluetooth.byte_to_signed_int( bluetooth.get_byte(pkt[1+13*nrsp+i])) results.append( ( addr, rssi ) )# store rssi and mac print("[%s] RSSI: [%d]" % (addr, rssi)) elif event == bluez.EVT_INQUIRY_COMPLETE: #scanning complete done = True
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) results = [] for i in range(0, loop_count): pkt = sock.recv(255) event, subevent, something = struct.unpack("BBB", pkt[1:4]) if subevent != 42: continue for p in split_packets(pkt): results.append(extract(p)) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return results
def read_local_bdaddr(hci_sock): old_filter = hci_sock.getsockopt(_bt.SOL_HCI, _bt.HCI_FILTER, 14) flt = _bt.hci_filter_new() opcode = _bt.cmd_opcode_pack(_bt.OGF_INFO_PARAM, _bt.OCF_READ_BD_ADDR) _bt.hci_filter_set_ptype(flt, _bt.HCI_EVENT_PKT) _bt.hci_filter_set_event(flt, _bt.EVT_CMD_COMPLETE) _bt.hci_filter_set_opcode(flt, opcode) hci_sock.setsockopt(_bt.SOL_HCI, _bt.HCI_FILTER, flt) _bt.hci_send_cmd(hci_sock, _bt.OGF_INFO_PARAM, _bt.OCF_READ_BD_ADDR) pkt = hci_sock.recv(255) status, raw_bdaddr = struct.unpack("xxxxxxB6s", pkt) assert status == 0 t = ["%X" % ord(get_byte(b)) for b in raw_bdaddr] t.reverse() bdaddr = ":".join(t) # restore old filter hci_sock.setsockopt(_bt.SOL_HCI, _bt.HCI_FILTER, old_filter) return bdaddr
def read_inquiry_mode(sock): """returns the current mode, or -1 on failure""" # save current filter old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # Setup socket filter to receive only events related to the # read_inquiry_mode command flt = bluez.hci_filter_new() opcode = bluez.cmd_opcode_pack(bluez.OGF_HOST_CTL, bluez.OCF_READ_INQUIRY_MODE) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) bluez.hci_filter_set_event(flt, bluez.EVT_CMD_COMPLETE); bluez.hci_filter_set_opcode(flt, opcode) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt ) # first read the current inquiry mode. bluez.hci_send_cmd(sock, bluez.OGF_HOST_CTL, bluez.OCF_READ_INQUIRY_MODE ) pkt = sock.recv(255) status,mode = struct.unpack("xxxxxxBB", pkt) if status != 0: mode = -1
def get_BT_addr_around(sock, loop_count=100): old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices new_filter = bluez.hci_filter_new() bluez.hci_filter_all_events(new_filter) bluez.hci_filter_set_ptype(new_filter, bluez.HCI_EVENT_PKT) sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, new_filter ) done = False results = [] BLE_addr_List = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i =0 elif event == bluez.EVT_NUM_COMP_PKTS: i =0 elif event == bluez.EVT_DISCONN_COMPLETE: i =0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): BLE_addr = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) if BLE_addr not in BLE_addr_List: BLE_addr_List.append(BLE_addr) done = True sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter ) return BLE_addr_List
def write_page_timeout(self, cmd_params={'Page_Timeout': 0x2000}) -> dict: dd = hci_open_dev(self.devid) bin_cmd_params = cmd_params['Page_Timeout'].to_bytes(2, 'little') flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode( flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_WRITE_PAGE_TIMEOUT)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_WRITE_PAGE_TIMEOUT, bin_cmd_params) event_params = dd.recv(3 + EVT_CMD_COMPLETE_SIZE + 3)[3:] num_hci_cmd_pkts, cmd_opcode, status = struct.unpack( '<BHB', event_params) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status } hci_close_dev(dd.fileno()) return event_params
def write_inquiry_mode(self, cmd_params={'Inquiry_Mode': 0x00}) -> dict: dd = hci_open_dev(self.devid) bin_cmd_params = cmd_params['Inquiry_Mode'].to_bytes(1, 'little') flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode( flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_WRITE_INQUIRY_MODE)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_WRITE_INQUIRY_MODE, bin_cmd_params) event_params = dd.recv(3 + EVT_CMD_COMPLETE_SIZE + 1)[3:] num_hci_cmd_pkts, cmd_opcode, status = struct.unpack( '<BHB', event_params) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status } hci_close_dev(dd.fileno()) return event_params
def read_local_name(self) -> dict: dd = hci_open_dev(self.devid) flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode( flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_READ_LOCAL_NAME)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_READ_LOCAL_NAME) event_params = dd.recv(3 + EVT_CMD_COMPLETE_SIZE + 249)[3:] num_hci_cmd_pkts, cmd_opcode, status, local_name = struct.unpack( '<BHB248s', hci_cmd_complete) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status, 'Local_Name': local_name.decode() } hci_close_dev(dd.fileno()) return event_params
def read_remote_version_information(self, cmd_params: dict) -> dict: ''' cmd_params -- { 'Connection_Handle': 0x0000 } ''' dd = hci_open_dev(self.devid) bin_cmd_params = cmd_params['Connection_Handle'].to_bytes(2, 'little') flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_READ_REMOTE_VERSION_COMPLETE) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_LINK_CTL, OCF_READ_REMOTE_VERSION, bin_cmd_params) while True: event_params = dd.recv(3 + \ EVT_READ_REMOTE_VERSION_COMPLETE_SIZE)[3:] status, conn_handle, ver, manufacturer_name, subver = \ struct.unpack('<BHBHH', event_params) event_params = { 'Status': status, 'Connection_Handle': conn_handle, 'Version': ver, 'Manufacturer_Name': manufacturer_name, 'Subversion': subver } if event_params['Connection_Handle'] == cmd_params[ 'Connection_Handle']: break hci_close_dev(dd.fileno()) return event_params
def _parse_events(self, sock, loop_count=100): """parse ble device output, filter and return ble advertisments""" old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) results = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == self.LE_META_EVENT: subevent = pkt[3] pkt = pkt[4:] if subevent == self.EVT_LE_CONN_COMPLETE: self.le_handle_connection_complete(pkt) elif subevent == self.EVT_LE_ADVERTISING_REPORT: num_reports = pkt[0] report_pkt_offset = 0 for i in range(0, num_reports): results.append({ "data": pkt.hex(), "ts": str(datetime.datetime.utcnow()) }) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return results
def parse_events(self, loop_count=100): old_filter = self.sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) done = False results = [] myFullList = [] for i in range(0, loop_count): pkt = self.sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3:4]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: num_reports = struct.unpack("B", pkt[0:1])[0] report_pkt_offset = 0 for i in range(0, num_reports): try: if isBeacon(pkt): b = Beacon(pkt) myFullList.append(b) except: pass done = True self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return myFullList
def read_class_of_device(self) -> dict: dd = hci_open_dev(self.devid) flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode( flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_READ_CLASS_OF_DEV)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_READ_CLASS_OF_DEV) event_params = dd.recv(3 + HCI_MAX_EVENT_SIZE)[3:] num_hci_cmd_pkts, cmd_opcode, status, cod = struct.unpack( '<BHB3s', event_params) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status, 'Class_Of_Device': cod[::-1] } hci_close_dev(dd.fileno()) return event_params
def read_extended_page_timeout(self): dd = hci_open_dev(self.devid) flt = hci_filter_new() hci_filter_set_ptype(flt, HCI_EVENT_PKT) hci_filter_set_event(flt, EVT_CMD_COMPLETE) hci_filter_set_opcode( flt, cmd_opcode_pack(OGF_HOST_CTL, OCF_READ_EXT_PAGE_TIMEOUT)) dd.setsockopt(SOL_HCI, HCI_FILTER, flt) hci_send_cmd(dd, OGF_HOST_CTL, OCF_READ_EXT_PAGE_TIMEOUT) event_params = dd.recv(3 + EVT_CMD_COMPLETE_SIZE + 3)[3:] num_hci_cmd_pkts, cmd_opcode, status, \ ext_page_timeout = struct.unpack('<BHBH', event_params) event_params = { 'Num_HCI_Command_Packets': num_hci_cmd_pkts, 'Command_Opcode': cmd_opcode, 'Status': status, 'Extended_Page_Timeout': ext_page_timeout } hci_close_dev(dd.fileno()) return event_params
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) done = False results = [] myFullList = [] for i in range(0, loop_count): pkt = sock.recv(255) ptype, event, plen = struct.unpack("BBB", pkt[:3]) #print "--------------" if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): if (DEBUG == True): print "-------------" #print "\tfullpacket: ", printpacket(pkt) print "\tUDID: ", printpacket( pkt[report_pkt_offset - 22:report_pkt_offset - 6]) print "\tMAJOR: ", printpacket( pkt[report_pkt_offset - 6:report_pkt_offset - 4]) print "\tMINOR: ", printpacket( pkt[report_pkt_offset - 4:report_pkt_offset - 2]) print "\tMAC address: ", packed_bdaddr_to_string( pkt[report_pkt_offset + 3:report_pkt_offset + 9]) # commented out - don't know what this byte is. It's NOT TXPower txpower, = struct.unpack("b", pkt[report_pkt_offset - 2]) print "\t(Unknown):", txpower rssi, = struct.unpack("b", pkt[report_pkt_offset - 1]) print "\tRSSI:", rssi # build the return string Adstring = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) Adstring = packed_bdaddr_to_string( pkt[report_pkt_offset + 3:report_pkt_offset + 9]) Adstring += "," Adstring += returnstringpacket( pkt[report_pkt_offset - 22:report_pkt_offset - 6]) Adstring += "," Adstring += "%i" % returnnumberpacket( pkt[report_pkt_offset - 6:report_pkt_offset - 4]) Adstring += "," Adstring += "%i" % returnnumberpacket( pkt[report_pkt_offset - 4:report_pkt_offset - 2]) Adstring += "," Adstring += "%i" % struct.unpack( "b", pkt[report_pkt_offset - 2]) Adstring += "," Adstring += "%i" % struct.unpack( "b", pkt[report_pkt_offset - 1]) # myFullList.append(Adstring) # if(get_host(uuid) and get_dup(myFullList, 'uuid',uuid)): # if(get_host(returnstringpacket(pkt[report_pkt_offset -22: report_pkt_offset -6]))and get_dup(myFullList, 'uuid',uuid)): uuid = returnstringpacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]) if (get_host(uuid) and get_dup(myFullList, uuid)): myFullList.append(Adstring) done = True sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return myFullList
def parse_events(sock, loop_count=100): old_filter = sock.getsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, 14) # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) done = False results = [] myFullList = [] for i in range(0, loop_count): pkt = sock.recv(255) if DEBUG == True: print "Iteration " + str(i) printpacket(pkt) ptype, event, plen = struct.unpack("BBB", pkt[:3]) #print "--------------" if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI: i = 0 elif event == bluez.EVT_NUM_COMP_PKTS: i = 0 elif event == bluez.EVT_DISCONN_COMPLETE: i = 0 elif event == LE_META_EVENT: subevent, = struct.unpack("B", pkt[3]) pkt = pkt[4:] if subevent == EVT_LE_CONN_COMPLETE: le_handle_connection_complete(pkt) elif subevent == EVT_LE_ADVERTISING_REPORT: #print "advertising report" num_reports = struct.unpack("B", pkt[0])[0] report_pkt_offset = 0 for i in range(0, num_reports): if (DEBUG == True): print "-------------" #print "\tfullpacket: ", printpacket(pkt) print "\tUDID: ", printpacket( pkt[report_pkt_offset - 22:report_pkt_offset - 6]) print "\tMAJOR: ", printpacket( pkt[report_pkt_offset - 6:report_pkt_offset - 4]) print "\tMINOR: ", printpacket( pkt[report_pkt_offset - 4:report_pkt_offset - 2]) print "\tMAC address: ", packed_bdaddr_to_string( pkt[report_pkt_offset + 3:report_pkt_offset + 9]) # commented out - don't know what this byte is. It's NOT TXPower txpower, = struct.unpack("b", pkt[report_pkt_offset - 2]) print "\t(Unknown):", txpower print struct.unpack("b", pkt[report_pkt_offset - 1]) rssi, = struct.unpack("b", pkt[report_pkt_offset - 1]) print "\tRSSI:", rssi # build the Beacon dict uuid = returnstringpacket(pkt[report_pkt_offset - 22:report_pkt_offset - 6]) mac = packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]) major = returnnumberpacket(pkt[report_pkt_offset - 6:report_pkt_offset - 4]) minor = returnnumberpacket(pkt[report_pkt_offset - 4:report_pkt_offset - 2]) txp, = struct.unpack("b", pkt[report_pkt_offset - 2]) rssi, = struct.unpack("b", pkt[report_pkt_offset - 1]) beac = { 'uuid': uuid, 'mac': mac, 'major': major, 'minor': minor, 'txp': txp, 'rssi': rssi } myFullList.append(beac) done = True sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, old_filter) return myFullList
try: result = bthandler.bt_write_inquiry_mode(self.sock, 1) except Exception, e: self.ui.show_error_dlg("Error writing inquiry mode.", 1) self.stop() return if result != True: self.ui.show_error_dlg("Error setting inquiry mode.", 1) self.stop() return # perform a device inquiry on bluetooth device #0 # The inquiry should last 8 * 1.28 = 10.24 seconds # before the inquiry is performed, bluez should flush its cache of # previously discovered devices flt = bluez.hci_filter_new() bluez.hci_filter_all_events(flt) bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT) self.sock.setsockopt(bluez.SOL_HCI, bluez.HCI_FILTER, flt) duration = 16 max_responses = 255 self.cmd_pkt = struct.pack("BBBBB", 0x33, 0x8b, 0x9e, duration, max_responses) bluez.hci_send_cmd(self.sock, bluez.OGF_LINK_CTL, bluez.OCF_INQUIRY, self.cmd_pkt) # Gtk object callback on socket data availability # pttimer = gobject.io_add_watch(self.sock, gobject.IO_IN, self.ptr_timeout, self.ui.speedo, self.ui.devlistview)