Skip to content

Commit

Permalink
Fix broken class matching on receive
Browse files Browse the repository at this point in the history
Restructured match_prefixes to correctly match sequence number field
Added insurance that sequence number comes first to do so
Also caught the (macOS) case where adapter has no address (WIP)
Fixes adafruit#15
  • Loading branch information
alexwhittemore committed Jan 2, 2021
1 parent 82899ad commit c936f92
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 6 deletions.
23 changes: 17 additions & 6 deletions adafruit_ble_broadcastnet.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,13 +61,16 @@ def broadcast(measurement, *, broadcast_time=0.1, extended=False):
if not hasattr(os, "environ") or (
"GITHUB_ACTION" not in os.environ and "READTHEDOCS" not in os.environ
):
device_address = "{:02x}{:02x}{:02x}{:02x}{:02x}{:02x}".format( # pylint: disable=invalid-name
*reversed(
list(
_ble._adapter.address.address_bytes # pylint: disable=protected-access
if _ble._adapter.address:
device_address = "{:02x}{:02x}{:02x}{:02x}{:02x}{:02x}".format( # pylint: disable=invalid-name
*reversed(
list(
_ble._adapter.address.address_bytes # pylint: disable=protected-access
)
)
)
)
else:
device_address = "000000000000"
"""Device address as a string."""

_MANUFACTURING_DATA_ADT = const(0xFF)
Expand All @@ -79,7 +82,8 @@ class AdafruitSensorMeasurement(Advertisement):

# This prefix matches all
match_prefixes = (
struct.pack("<BBH", 3, _MANUFACTURING_DATA_ADT, _ADAFRUIT_COMPANY_ID),
# Matches the sequence number field header (length+ID)
struct.pack("<BHBH", _MANUFACTURING_DATA_ADT, _ADAFRUIT_COMPANY_ID, 0x03, 0x0003),
)

manufacturer_data = LazyObjectField(
Expand Down Expand Up @@ -174,6 +178,13 @@ def __str__(self):
if value is not None:
parts.append("{}={}".format(attr, str(value)))
return "<{} {} >".format(self.__class__.__name__, " ".join(parts))

def __bytes__(self):
"""The raw packet bytes."""
# Must reorder the ManufacturerData contents so the sequence number field is always first.
# Necessary to ensure that match_prefixes works right to reconstruct on the receiver.
self.data_dict[255].data.move_to_end(3, last=False)
return super().__bytes__()

def split(self, max_packet_size=31):
"""Split the measurement into multiple measurements with the given max_packet_size. Yields
Expand Down
14 changes: 14 additions & 0 deletions examples/ble_broadcastnet_scan_test.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
"""This example merely scans for broadcastnet packets as a quick check that something is sending them."""

from adafruit_ble.advertising.standard import ManufacturerDataField
import adafruit_ble
import adafruit_ble_broadcastnet

ble = adafruit_ble.BLERadio()

print("scanning")
# By providing Advertisement as well we include everything, not just specific advertisements.
for advert in ble.start_scan(
adafruit_ble_broadcastnet.AdafruitSensorMeasurement, interval=0.5
):
print(advert)

0 comments on commit c936f92

Please sign in to comment.