[Aioble] Update Parameters request from Central not answered by Peripheral.
Checks
-
I agree to follow the MicroPython Code of Conduct to ensure a safe and respectful space for everyone.
-
I've searched for existing issues matching this bug, and didn't find any.
Port, board and/or hardware
Raspberry PI Pico W
MicroPython version
MicroPython v1.22.2 on 2024-02-22; Raspberry Pi Pico W with RP2040
Reproduction
- Create a client on MicroPython side with Aioble and set it into advertisting mode. E.g:
ADVERTISE_INTERVAL_US = const(250000)
BLUETOOTH_APPEARANCE = const(512)
EVENT_SERVICE_UUID = bluetooth.UUID("ANY SERVICE UUID HERE")
event_service = aioble.Service(EVENT_SERVICE_UUID)
async def advertise():
while True:
async with await aioble.advertise(
ADVERTISE_INTERVAL_US,
name="WarnTag",
services=[EVENT_SERVICE_UUID],
appearance=BLUETOOTH_APPEARANCE,
) as connection:
await connection.disconnected()
- At the same time, create a Central GATT Client using Bleak with python and connect it to the known Raspberry PI Pico W adress
async with BleakClient(ADRESS) as client:
print("Connection established")
Expected behaviour
Expected behavior:
The Python Client does not freeze. The communication is established and both, the server periphal and the client central side continue in their program flow.
Observed behaviour
In Windows 10, everything works perfectly.
In Windows 11, the central GATT client using bleak freezes when calling
async with BleakClient(ADRESS) as client:
print("Connection established")
As was already analyzed in https://github.com/hbldh/bleak/issues/1262, it seems that the following difference between Windows 10 and Windows 11 is happening:
Windows 10 does not request a connection parameters update.
Windows 11 DOES request a connection parameters update.
It seems that the Micropython connection is not answering the connection parameters update, leading to a freeze on the client side.
In the issue created on the bleak repo, you can also see Wireshark Measurements to see the communication between the central GATT client and the peripheral GATT server (using aioble).
https://github.com/hbldh/bleak/issues/1262#issuecomment-2040980754
Additional Information
No, I've provided everything above.
[Aioble] Update Parameters request from Central not answered by Peripheral.
Hello,
see
https://github.com/hbldh/bleak/issues/1262
If you just want the measurements: https://github.com/hbldh/bleak/issues/1262#issuecomment-2040980754
On Windows 10, no "Sent LE Connection Update" is sent by the Central GATT Client. In that case, everything works fine.
On Windows 11, a "Sent LE Connection Update" is sent by the Central GATT Client. In that case, the connection breaks down.
The link above has Wireshark Bluetooth logs attached from the computer side, which uses Bleak to create a Central GATT Client. I run Aioble on the Peripheral device side as Peripheral GATT Server.
The problem in the link above is, that Bleak crashes in Windows 11 while it works perfectly fine in Windows 10. Our suspicion is, that the Peripheral does not handle the "Sent LE Connection Update" correctly.
On the Aioble side, I also get an error (in the time where the Bleak client freezes on Windows 11):
Traceback (most recent call last):
File "<stdin>", line 167, in <module>
File "asyncio/core.py", line 1, in run
File "asyncio/core.py", line 1, in run_until_complete
File "asyncio/core.py", line 1, in run_until_complete
File "<stdin>", line 164, in main
File "asyncio/funcs.py", line 1, in gather
File "asyncio/core.py", line 1, in run_until_complete
File "<stdin>", line 88, in advertise
File "aioble/device.py", line 295, in aexit
File "aioble/device.py", line 216, in disconnect
File "aioble/device.py", line 232, in disconnected
File "aioble/device.py", line 232, in disconnected
File "asyncio/core.py", line 1, in run_until_complete
File "aioble/device.py", line 198, in device_task
File "asyncio/event.py", line 1, in wait
CancelledError:
The error does not even referr to a line of code that I have written, so it must happen during the
await connection.disconnected()
stage after I have initiated the connection via
async with await aioble.advertise(...) as connection:
...
await connection.disconnected()
The same code (on both sides, same server code and same client code) runs perfectly on Windows 10. And the only difference that we see in the Wireshark logs (see link above) is that under Windows 11 a Sent LE Connection Update is sent by the client.
To be more clear, apparently Windows 11 now requires peripherals to support the "Connection Parameter Update procedure" (e.g. Bluetooth core spec 5.3, vol 3, part C, sec 9.3.9) and is hanging because it never gets a response from an RPi Pico running MicroPtython.
This is a low level procedure that should be handled by BTStack already. So if it isn't I'm guessing there is an issue with pumping BTStack events in the MicroPython code somewhere or a bug in BTStack where it doesn't respond to this request under specific conditions.
In any case, this is a core MicroPython issue, not micropython-lib.
Duplicated, issue tracked via
https://github.com/micropython/micropython/issues/14268