Topics

Data Length Extension on NRF52840 #ble #nrf52840 #hci


josh.lawless@...
 

Software/Hardware:

Board: NRF52840 PCA10056 programmed with Zephyr firmware
Host Device: Linux Ubuntu 16.04.1
Bluez 5.48 Source code
Bluetooth 5.0 Core Specification

Problem:

Attempting to use Bluetooth 4.2 feature, Data Length Extension, and set the notification size to 247 bytes but Max RX Octets is still set to 27 bytes.
The outcome is that I do not receive 247 byte notifications. I receive the default 27 byte notifications.

Workflow:

  1. Connect to Remote Bluetooth Device
  2. Exchange MTU
  3. Request Data Length Extension
  4. Enable Notifications
  5. Send command that will cause remote device to send notifications
  6. Notifications are 27 bytes in length

Research:

I'm using Bluez's hci_send_cmd in lib/hci.c to request the Data Length Extension feature using a HCI_LE_Set_Data_Length packet . At a lower level this will send a LL_LENGTH_REQ necessary for updating the data length. 

According to the Bluetooth Core Specification, (Vol 2, Part E 7.8.33 page 1304)
The LE_Set_Data_Length command allows the Host to suggest maximum transmission packet size and maximum packet transmission time (connMaxTxOctets and connMaxTxTime - see [Vol 6] Part B, Section 4.5.10) to be used for a given connection. The Controller may use smaller or larger values based on local information.

While sending the commands, I ran btmon to capture the Bluetooth packets below. Note that the MTU was successfully sent with the client at 247 byte length and the response of the remote device was also 247 bytes.
Furthermore, the LE Set Data Length command was also successful producing a LE Data Length Change event. The TX octets changed successfully, but the RX Octets remained at 27 bytes

TxOctets = 0x00FB (251 bytes)
< ACL Data TX: Handle 0 flags 0x00 dlen 7                              #3805 [hci1] 8157.585140
      ATT: Exchange MTU Request (0x02) len 2
        Client RX MTU: 247
> HCI Event: Number of Completed Packets (0x13) plen 5                 #3806 [hci1] 8157.606595
        Num handles: 1
        Handle: 0
        Count: 1
> HCI Event: Number of Completed Packets (0x13) plen 5                 #3807 [hci1] 8157.656582
        Num handles: 1
        Handle: 0
        Count: 1
> ACL Data RX: Handle 0 flags 0x02 dlen 7                              #3808 [hci1] 8157.706323
      ATT: Exchange MTU Response (0x03) len 2
        Server RX MTU: 247
@ RAW Open: luajit (privileged) version 2.22                        {0x000d} [hci1] 8157.716478
< HCI Command: LE Set Data Length (0x08|0x0022) plen 6                 #3809 [hci1] 8157.716970
        Handle: 0
        TX octets: 247
        TX time: 2120
@ RAW Close: luajit                                                 {0x000d} [hci1] 8157.717430
> HCI Event: Command Complete (0x0e) plen 6                            #3810 [hci1] 8157.717571
      LE Set Data Length (0x08|0x0022) ncmd 1
        Status: Success (0x00)
        Handle: 0
> HCI Event: LE Meta Event (0x3e) plen 11                              #3811 [hci1] 8157.856582
      LE Data Length Change (0x07)
        Handle: 0
        Max TX octets: 247
        Max TX time: 2088
        Max RX octets: 27
        Max RX time: 2088

Here's an example of two notifications received with data lines removed. Note that the length is 27

> ACL Data RX: Handle 0 flags 0x02 dlen 27                            #4182 [hci1] 13803.456102
      ATT: Handle Value Notification (0x1b) len 22
        Handle: 0x0010
> ACL Data RX: Handle 0 flags 0x02 dlen 27                            #4183 [hci1] 13803.456602
      ATT: Handle Value Notification (0x1b) len 22
        Handle: 0x0010

I have used the nRF Connect application on my Samsung S9 and connected to the same remote device. Using the settings, I clicked "Request MTU" and set the MTU to 251. Using the same defined workflow above and using Google's HCI Snoop log, I found similar packets above in the same order but with a different outcome.
Using the phone the Max RX Octets were successfully changed to 251 bytes!







Questions:
Am I missing a step to set the Max RX Octet value that appears on the LE Data Length Change event?
Is this an issue with the Zephyr firmware?


Chettimada, Vinayak Kariappa <vinayak.kariappa.chettimada@...>
 

Hi Josh,

Appreciate the excellent and detailed incidence report. My comments are inline.


On 12 Jul 2018, at 23:14, josh.lawless@... wrote:

Software/Hardware:

Board: NRF52840 PCA10056 programmed with Zephyr firmware
Host Device: Linux Ubuntu 16.04.1
Bluez 5.48 Source code
Bluetooth 5.0 Core Specification


Could you please provide the Zephyr repository git hash or release tag for the firmware you are using?

Problem:

Attempting to use Bluetooth 4.2 feature, Data Length Extension, and set the notification size to 247 bytes but Max RX Octets is still set to 27 bytes.
The outcome is that I do not receive 247 byte notifications. I receive the default 27 byte notifications.


Could you please confirm that Zephyr BLE controller is built using below mentioned options:
+CONFIG_BT_CTLR_TX_BUFFER_SIZE=251
+CONFIG_BT_RX_BUF_LEN=258
+CONFIG_BT_CTLR_DATA_LENGTH_MAX=251
 

Workflow:

  1. Connect to Remote Bluetooth Device
  2. Exchange MTU
  3. Request Data Length Extension
  4. Enable Notifications
  5. Send command that will cause remote device to send notifications
  6. Notifications are 27 bytes in length

Research:

I'm using Bluez's hci_send_cmd in lib/hci.c to request the Data Length Extension feature using a HCI_LE_Set_Data_Length packet . At a lower level this will send a LL_LENGTH_REQ necessary for updating the data length. 

According to the Bluetooth Core Specification, (Vol 2, Part E 7.8.33 page 1304)
The LE_Set_Data_Length command allows the Host to suggest maximum transmission packet size and maximum packet transmission time (connMaxTxOctets and connMaxTxTime - see [Vol 6] Part B, Section 4.5.10) to be used for a given connection. The Controller may use smaller or larger values based on local information.

While sending the commands, I ran btmon to capture the Bluetooth packets below. Note that the MTU was successfully sent with the client at 247 byte length and the response of the remote device was also 247 bytes.
Furthermore, the LE Set Data Length command was also successful producing a LE Data Length Change event. The TX octets changed successfully, but the RX Octets remained at 27 bytes

TxOctets = 0x00FB (251 bytes)
< ACL Data TX: Handle 0 flags 0x00 dlen 7                              #3805 [hci1] 8157.585140
      ATT: Exchange MTU Request (0x02) len 2
        Client RX MTU: 247
> HCI Event: Number of Completed Packets (0x13) plen 5                 #3806 [hci1] 8157.606595
        Num handles: 1
        Handle: 0
        Count: 1
> HCI Event: Number of Completed Packets (0x13) plen 5                 #3807 [hci1] 8157.656582
        Num handles: 1
        Handle: 0
        Count: 1
> ACL Data RX: Handle 0 flags 0x02 dlen 7                              #3808 [hci1] 8157.706323
      ATT: Exchange MTU Response (0x03) len 2
        Server RX MTU: 247
@ RAW Open: luajit (privileged) version 2.22                        {0x000d} [hci1] 8157.716478
< HCI Command: LE Set Data Length (0x08|0x0022) plen 6                 #3809 [hci1] 8157.716970
        Handle: 0
        TX octets: 247
        TX time: 2120
@ RAW Close: luajit                                                 {0x000d} [hci1] 8157.717430
> HCI Event: Command Complete (0x0e) plen 6                            #3810 [hci1] 8157.717571
      LE Set Data Length (0x08|0x0022) ncmd 1
        Status: Success (0x00)
        Handle: 0
> HCI Event: LE Meta Event (0x3e) plen 11                              #3811 [hci1] 8157.856582
      LE Data Length Change (0x07)
        Handle: 0
        Max TX octets: 247
        Max TX time: 2088
        Max RX octets: 27
        Max RX time: 2088


From my guess, without an on-air trace, either Zephyr BLE controller is not configured to support 251 byte PDU or the remote did not negotiate to Tx towards the controller any PDU larger than 27 bytes.
Moving on…

Here's an example of two notifications received with data lines removed. Note that the length is 27

> ACL Data RX: Handle 0 flags 0x02 dlen 27                            #4182 [hci1] 13803.456102
      ATT: Handle Value Notification (0x1b) len 22
        Handle: 0x0010
> ACL Data RX: Handle 0 flags 0x02 dlen 27                            #4183 [hci1] 13803.456602
      ATT: Handle Value Notification (0x1b) len 22
        Handle: 0x0010

I have used the nRF Connect application on my Samsung S9 and connected to the same remote device. Using the settings, I clicked "Request MTU" and set the MTU to 251. Using the same defined workflow above and using Google's HCI Snoop log, I found similar packets above in the same order but with a different outcome.
Using the phone the Max RX Octets were successfully changed to 251 bytes!
<2018_07_12 15_44_57_btsnoop_hci.log.png>


<2018_07_12 15_46_00_btsnoop_hci.log.png>

<2018_07_12 15_46_44_btsnoop_hci.log.png>

This confirms the remote device does indeed negotiate to Tx 251 byte PDUs to “a” central.


Questions:
Am I missing a step to set the Max RX Octet value that appears on the LE Data Length Change event?
Is this an issue with the Zephyr firmware?


Please confirm on the Kconfig options you have used for building the Zephyr BLE controller, we can analyse further based on the Zephyr revision and options used.



- Vinayak


George Ruinelli
 

@Josh

Can you give some insight, how you requested Data Length Extension?
I can not find any documentation how to do this.
I was able to enable to do it manually through the nRF Connect Tool, but need to do it directly in Zephyr.

Sincerely
George