Android 6.0 Marsmallow BLE:连接参数

Android 6中的蓝牙低功耗连接参数pipe理似乎发生了变化。

我有一个BLE外围设备需要使用一些特定的连接参数(特别是连接间隔),我想使用BLE规范允许的最小连接间隔(即7.5ms)。

Android SDK不允许从BLE GAP Central(智能手机)端select它,所以正确的做法是让GAP外围设备在GAP连接之后发送一个L2CAP Connection Parameter Update Request

我请求的参数是:

  • 连续区间最小:7,5ms
  • conn间隔最大:7,5ms
  • 从属延迟:0
  • 监督超时时间:2000ms

这与我所testing的所有Android设备(从4.3到5.x)一致:在发送L2CAP Connection Parameter Update Request ,我的设备接收到一个带有0x0000(接受)的L2CAP Connection Parameter Update Response ,后面是一个LE Connection Update Complete event ,我可以看到所请求的连接参数已经被充分考虑。

现在,使用Nexus 9平板电脑或使用两台不同的Nexus 5设备(都安装了Android 6.0.1),我可以看到L2CAP Connection Parameter Update Request总是被拒绝(我收到一个带0x0001的L2CAP Connection Parameter Update Response (被拒绝) )。 然后,我收到一个LE Connection Update Complete event ,我可以看到请求的连接参数没有被考虑在内。

我一直试图在外设端使用两种不同的实现(一种是ST Microelectronics的BlueNRG,一种是北欧半导体的nRF52),两者的结果完全相同。

然后,经过更多的testing:我已经尝试了不同的参数集,改变conn interval max(我保持其他参数相同)。 这是我发现的:

  • conn interval = 18.75ms,更新请求被接受,时间间隔设置为18.75ms
  • conn interval = 17.50ms,更新请求被接受,时间间隔设置为15.00ms
  • conn interval = 15.00ms,更新请求被接受,时间间隔设置为15.00ms
  • conn interval = 13.75ms,更新请求被接受,间隔设置为11.25ms
  • conn interval = 11.25ms,更新请求被接受,时间间隔设置为11.25ms
  • 与任何其他conn间隔最大值低于11.25ms,我被拒绝。

所以观察到,Android 6的BLE堆栈处理连接参数的方式已经有了明显的改变。 但似乎没有任何forms的信息或文件来证实这一点。

我的观察得出的结论是,现在允许的最小连接间隔是11.25毫秒(实际上符合我的需要),而不是早期的Android版本7.5毫秒。 但通过实证发现,我想确保我不会错过其他约束/规则,或者如果这个最小值不是dynamic的,则取决于当前的电池电量。

相当于苹果公司的蓝牙devise指南 (参见3.6节),可以明确LE外设应该如何处理这个问题。

有没有人有相同的问题,或知道从谷歌更多有用的信息?

Solutions Collecting From Web of "Android 6.0 Marsmallow BLE:连接参数"

比较AOSP 6.0.1_r17中的GattService.java与AOSP 5.1.1_r14中的方法connectionParameterUpdate()。 在这两个实例中,调用一直到在bta_dm_api.c中的BTA_DmBleUpdateConnectionParams()中使用相同参数的Buedroid。

6.0:

  switch (connectionPriority) { case BluetoothGatt.CONNECTION_PRIORITY_HIGH: minInterval = 9; // 11.25ms maxInterval = 12; // 15ms break; case BluetoothGatt.CONNECTION_PRIORITY_LOW_POWER: minInterval = 80; // 100ms maxInterval = 100; // 125ms latency = 2; break; } 

5.1:

  switch (connectionPriority) { case BluetoothGatt.CONNECTION_PRIORITY_HIGH: minInterval = 6; // 7.5ms maxInterval = 8; // 10ms break; case BluetoothGatt.CONNECTION_PRIORITY_LOW_POWER: minInterval = 80; // 100ms maxInterval = 100; // 125ms latency = 2; break; } 

这可能是你的问题的答案的一部分。 尽pipeBLE允许低至7.5ms CI,但我无法推测为什么链路层不会根据外设的要求切换到较低的CI。 我不知道如果任何部分的android代码控制与外围设备的谈判结果。

虽然在Android 6中已经有了明显的一些,Google还没有提供任何有关连接参数变化的蓝牙LE堆栈变更的文档。

我的经验和你自己的一样,11.25ms是Android 6+中最快的连接间隔。

据我所知,为什么他们不发布文档是因为许多制造商把他们自己的BLE堆栈放入他们的手机(三星和HTC的BLE行为与香草Android不同)。

另外一个我曾经做过的观察导致了很多问题,Android 6+会在连接参数2到6次之前改变连接参数。

我观察到在请求连接参数更新间隔为800毫秒到1100毫秒之后,我看到初始间隔回到7.5毫秒,然后跳到48.75毫秒,然后跳到我请求的1098.75毫秒。 然后,我订阅了我的其中一个服务的通知,连接间隔再次跳回到7.5ms,然后回到1098.75ms。 此后,在连接期间稳定在1098.75ms。

这些testing是在Android 6.0.1的Nexus 6上运行的

显然,Android 6 BLE堆栈上发生了一些非常奇怪的事情。

谷歌的人在最近一次提交Bluedroid的时候犯了一个错误,把BTM_BLE_CONN_INT_MIN_LIMIT定义为0x0009 ,它给你1.25ms x 9 = 11.25ms。 为了符合标准,必须将其定义为0x0006

11.25毫秒是新的最小连接间隔。 他们不允许7.5毫秒的原因是因为如果你通过蓝牙串streamaudio同时audio可能变得波涛汹涌。