Maximum data size when sending data via BTLE on iOS

本秂侑毒 提交于 2019-12-21 04:04:10

问题


I am currently implementing an iOS application that uses CoreBluetooth to transfer data between 2 devices. For example, to send data from the central to the peripheral, I use this code:

NSData *data = [NSJSONSerialization dataWithJSONObject:dictionary options:NSJSONWritingPrettyPrinted error:nil];
NSLog(@"Writing data of length %d", [data length]);
[peripheral writeValue:data forCharacteristic:characteristic type:CBCharacteristicWriteWithResponse];

This works absolutely fine, but the thing is that I have read multiple times now that characteristics can transfer a maximum of 20 bytes at once. Also, when I look at Apple's BTLE Example Code they implement a mechanism that splits the data into chunks of 20 bytes. But the above code prints something like Writing data of length 124 - the data arrives fine at the other device, though.

So: Why is this working at all? And even more so, I am afraid that this could break at some point, especially when non-iOS devices come into play.


回答1:


The BLE standard requires 23 bytes as the minimum ATT_MTU (Attribute Protocol Maximum Transmission Unit) which all BLE devices must support. The maximum ATT_MTU is 255 bytes, however, and has been doubled again for BLE 4.2.

BLUETOOTH SPECIFICATION Version 4.2 [Vol 3, Part A]:

All L2CAP implementations shall support a minimum MTU of […] 23 octets over the LE-U logical link; however, some protocols and profiles explicitly require support for a larger MTU.

When establishing a connection, both devices will exchange their ATT_MTU size, and the smaller of both values is used. When Apple started with BLE, they would only support the minimum, but have since expanded the possible size. That is why your 124 bytes work, but the older documentation and sample code uses a much smaller ATT_MTU.




回答2:


I'm using iOS 7.1.1 and have also found that I can send as much as 132 bytes reliably from an iPhone to an iPad using BLE. I also heard that 20 bytes was the max but it sure doesn't seem like it is




回答3:


As a starting point the so-called ATT_MTU size determines the number of bytes that can be written. This value is exchanged/negotiating between the two devices. Unfortunately, this value doesn't seem to be exposed in Apple's CoreBluetooth interface :(

But I have just used a BLE sniffer and in my case it was 158 bytes. But then again this value can change over time...

If you write more data than ATT_MTU then the BlueTooth stack may use a so-called Prepare-Write procedure, but not all stacks supports that. Have not tested if Apple supports this...

:)




回答4:


On iOS 9+ you can use this method on each subscribed CBCentral to determine how much data to send per chunk:

[central maximumUpdateValueLength];



回答5:


When you write data to the characteristic of remote device by 



func writeValue(_ data: Data, for characteristic: CBCharacteristic, type: CBCharacteristicWriteType) https://developer.apple.com/documentation/corebluetooth/cbperipheral/1518747-writevalue 



you should use

func maximumWriteValueLength(for type: CBCharacteristicWriteType) -> Int https://developer.apple.com/documentation/corebluetooth/cbperipheral/1620312-maximumwritevaluelength



to figure out the size of chunks to split your data into.



来源:https://stackoverflow.com/questions/24349945/maximum-data-size-when-sending-data-via-btle-on-ios

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!