def __stopfilter__(self, packet): """ This is the stop filter for Scapy to be used to check if the packet was sent to this WirelessStateMachine instance. """ if get_destination(packet) == self.source_mac and get_bssid(packet) == self.bssid: # and real_source == self.dest_mac: self.lastpacket = packet return True self.lastpacket = None return False
def __stopfilter__(self, packet): """ This is the stop filter for Scapy to be used to check if the packet was sent to EAPeak. """ if packet.haslayer(Dot11Auth) or packet.haslayer(Dot11AssoReq): if get_bssid(packet) == self.bssid and get_source(packet) != self.bssid: self.lastpacket = packet return True return False elif packet.haslayer(Dot11ProbeReq): self.lastpacket = packet return True return False
def update_maps(self, packet): tmp = packet for x in range(0, SSID_SEARCH_RECURSION): # pylint: disable=unused-variable if 'ID' in tmp.fields and tmp.fields['ID'] == 0 and 'info' in tmp.fields: # Verifies that we found an SSID if tmp.fields['info'] == '\x00': break bssid = get_bssid(packet) if (self.targetSSIDs and tmp.fields['info'] not in self.targetSSIDs) or (self.targetBSSIDs and bssid not in self.targetBSSIDs): # Obi says: These are not the SSIDs you are looking for... break if not bssid: return ssid = ''.join([c for c in tmp.fields['info'] if (ord(c) > 31 or ord(c) == 9) and ord(c) < 128]) if self.targetBSSIDs: if not self.targetSSIDs: self.targetSSIDs = [] if ssid not in self.targetSSIDs: self.targetSSIDs.append(ssid) if not ssid: return if bssid in self.OrphanedBSSIDs: # If this info is relating to a BSSID that was previously considered to be orphaned newNetwork = self.KnownNetworks[bssid] # Retrieve the old one del self.KnownNetworks[bssid] # Delete the old network's orphaned reference self.OrphanedBSSIDs.remove(bssid) self.BSSIDToSSIDMap[bssid] = ssid # Changes the map from BSSID -> BSSID (for orphans) to BSSID -> SSID newNetwork.update_SSID(ssid) if ssid in self.KnownNetworks: newNetwork = merge_wireless_networks(newNetwork, self.KnownNetworks[ssid]) elif bssid in self.BSSIDToSSIDMap: continue elif ssid in self.KnownNetworks: # If this is a BSSID from a probe for an SSID we've seen before newNetwork = self.KnownNetworks[ssid] # Pick up where we left off by using the curent state of the WirelessNetwork object elif bssid: newNetwork = eapeak.networks.WirelessNetwork(ssid) self.BSSIDToSSIDMap[bssid] = ssid newNetwork.add_BSSID(bssid) self.KnownNetworks[ssid] = newNetwork del bssid, ssid break tmp = tmp.payload if tmp is None: break
def parse_wireless_packet(self, packet): """ This is the core packet parsing routine. It takes a Scapy style packet object as an argument. """ if packet.name == 'RadioTap dummy': packet = packet.payload # Offset it so we start with the Dot11 header shouldStop = False self.packetCounter += 1 # this section finds SSIDs in Bacons if packet.haslayer('Dot11Beacon') or packet.haslayer('Dot11ProbeResp') or packet.haslayer('Dot11AssoReq'): self.update_maps(packet) shouldStop = True if shouldStop: return # This section extracts useful EAP info cert_layer = None if 'EAP' in packet: fields = packet.getlayer('EAP').fields if fields['code'] not in [1, 2]: return eaptype = fields['type'] for x in range(1, 4): addr = 'addr' + str(x) if not addr in packet.fields: return bssid = get_bssid(packet) if not bssid: return if bssid and not bssid in self.BSSIDToSSIDMap: self.BSSIDToSSIDMap[bssid] = bssid self.OrphanedBSSIDs.append(bssid) self.KnownNetworks[bssid] = eapeak.networks.WirelessNetwork(UNKNOWN_SSID_NAME) self.KnownNetworks[bssid].add_BSSID(bssid) network = self.KnownNetworks[self.BSSIDToSSIDMap[bssid]] client_mac = get_source(packet) from_AP = False if client_mac == bssid: client_mac = get_destination(packet) from_AP = True if not bssid or not client_mac: return if network.has_client(client_mac): client = network.get_client(client_mac) else: client = eapeak.clients.WirelessClient(bssid, client_mac) if from_AP: network.addEapType(eaptype) elif eaptype > 4: client.addEapType(eaptype) elif eaptype == 3 and fields['code'] == 2: # Parses NAKs and attempts to harvest the desired EAP types, RFC 3748 self.get_client_eap_types(fields, client) if eaptype == 254 and packet.haslayer('EAP_Expanded'): network.add_expanded_vendor_id(packet.getlayer('EAP_Expanded').vendor_id) if from_AP: if packet.haslayer('LEAP'): self.get_leap_from_ap_data(packet, client) elif packet.getlayer(EAP).payload.name in ['EAP_TLS', 'EAP_TTLS', 'PEAP', 'EAP_Fast']: cert_layer = self.get_eap_data(packet, bssid, client_mac) elif packet.haslayer('EAP_Expanded') and packet.getlayer('EAP_Expanded').vendor_type == 1 and packet.haslayer('WPS') and packet.getlayer('WPS').opcode == 4: try: self.get_wps_data(packet, network) except: # pylint: disable=bare-except pass else: if eaptype == 1 and 'identity' in fields: client.add_identity(1, fields['identity']) if packet.haslayer('LEAP'): self.get_leap_data(packet, client) elif packet.haslayer('EAP_Expanded') and packet.getlayer('EAP_Expanded').vendor_type == 1 and packet.haslayer('WPS') and packet.getlayer('WPS').opcode == 4: try: self.get_client_wps_data(packet, client) except: # pylint: disable=bare-except pass # Data is corrupted network.add_client(client) if not cert_layer: shouldStop = True if shouldStop: return if cert_layer and 'certificate' in cert_layer.fields: self.get_cert_data(network, cert_layer) return