diff --git a/scapy/layers/bluetooth4LE.py b/scapy/layers/bluetooth4LE.py index 82cee336037..cf51905f01d 100644 --- a/scapy/layers/bluetooth4LE.py +++ b/scapy/layers/bluetooth4LE.py @@ -14,9 +14,10 @@ PPI_BTLE from scapy.packet import Packet, bind_layers from scapy.fields import BitEnumField, BitField, ByteEnumField, ByteField, \ - Field, FlagsField, LEIntField, LEShortEnumField, LEShortField, \ + Field, LEIntField, LEShortEnumField, LEShortField, \ MACField, PacketListField, SignedByteField, X3BytesField, XBitField, \ XByteField, XIntField, XShortField, XLEIntField, XLEShortField +from scapy.contrib.ethercat import LEBitEnumField, LEBitField from scapy.layers.bluetooth import EIR_Hdr, L2CAP_Hdr from scapy.layers.ppi import PPI_Element, PPI_Hdr @@ -53,22 +54,47 @@ class BTLE_PPI(PPI_Element): class BTLE_RF(Packet): """Cooked BTLE link-layer pseudoheader. - http://www.whiterocker.com/bt/LINKTYPE_BLUETOOTH_LE_LL_WITH_PHDR.html + https://www.tcpdump.org/linktypes/LINKTYPE_BLUETOOTH_LE_LL_WITH_PHDR.html """ name = "BTLE RF info header" + + _TYPES = { + 0: "ADV_OR_DATA_UNKNOWN_DIR", + 1: "AUX_ADV", + 2: "DATA_M_TO_S", + 3: "DATA_S_TO_M", + 4: "CONN_ISO_M_TO_S", + 5: "CONN_ISO_S_TO_M", + 6: "BROADCAST_ISO", + 7: "RFU", + } + + _PHY = { + 0: "1M", + 1: "2M", + 2: "Coded", + 3: "RFU", + } + fields_desc = [ ByteField("rf_channel", 0), SignedByteField("signal", -128), SignedByteField("noise", -128), ByteField("access_address_offenses", 0), XLEIntField("reference_access_address", 0), - FlagsField("flags", 0, -16, [ - "dewhitened", "sig_power_valid", "noise_power_valid", - "decrypted", "reference_access_address_valid", - "access_address_offenses_valid", "channel_aliased", - "res1", "res2", "res3", "crc_checked", "crc_valid", - "mic_checked", "mic_valid", "res4", "res5" - ]) + LEBitField("dewhitened", 0, 1), + LEBitField("sig_power_valid", 0, 1), + LEBitField("noise_power_valid", 0, 1), + LEBitField("decrypted", 0, 1), + LEBitField("reference_access_address_valid", 0, 1), + LEBitField("access_address_offenses_valid", 0, 1), + LEBitField("channel_aliased", 0, 1), + LEBitEnumField("type", 0, 3, _TYPES), + LEBitField("crc_checked", 0, 1), + LEBitField("crc_valid", 0, 1), + LEBitField("mic_checked", 0, 1), + LEBitField("mic_valid", 0, 1), + LEBitEnumField("phy", 0, 2, _PHY), ] diff --git a/test/scapy/layers/bluetooth4LE.uts b/test/scapy/layers/bluetooth4LE.uts index 6a358975dfc..8a9a2b80932 100644 --- a/test/scapy/layers/bluetooth4LE.uts +++ b/test/scapy/layers/bluetooth4LE.uts @@ -65,19 +65,23 @@ assert BTLE_SCAN_RSP in pkt.layers() a = BTLE_RF()/BTLE()/BTLE_ADV()/BTLE_SCAN_REQ() a.ScanA = "aa:aa:aa:aa:aa:aa" a.AdvA = "bb:bb:bb:bb:bb:bb" -a.flags = 0x10 +a.reference_access_address_valid = 1 a.reference_access_address = 0x8e89bed6 +a.phy = 3 +a.type = 5 a.noise = -90 a.signal = -75 a.rf_channel = 6 a.access_address_offenses = 10 -assert raw(a) == b'\x06\xb5\xa6\n\xd6\xbe\x89\x8e\x10\x00\xd6\xbe\x89\x8e\x03\x0c\xaa\xaa\xaa\xaa\xaa\xaa\xbb\xbb\xbb\xbb\xbb\xbb\x07\xb2a' +assert raw(a) == b'\x06\xb5\xa6\n\xd6\xbe\x89\x8e\x90\xc2\xd6\xbe\x89\x8e\x03\x0c\xaa\xaa\xaa\xaa\xaa\xaa\xbb\xbb\xbb\xbb\xbb\xbb\x07\xb2a' a = BTLE_RF(raw(a)) assert a.noise == -90 assert a.signal == -75 -assert a.flags == "reference_access_address_valid" +assert a.phy == 3 +assert a.type == 5 +assert a.reference_access_address_valid == 1 assert a[BTLE_SCAN_REQ].ScanA == "aa:aa:aa:aa:aa:aa" + Specific tests after issue GH#1673