BLE GattServer long write

Hi everybody!
I’m currently working based on the BLE_GattServer_CharacteristicWrite example using a nRF52DK board. I can write a single byte to a characteristic and also managed to change the characteristic to std::string and write a few bytes at once. However, I cannot find any documentation or examples on how to get long write to work, to write more than MTU bytes. Is there anything out there or does anybody know how to do this? Help would be greatly appreciated.

From my past experience working with BLE on iOS, this is handled on the sender’s side. Knowing your MTU, you need to cut your data in chunks of the right size and send them one by one.

If the integrity of the message is important, you’ll need to take care of lost/corrupted data. A starting sequence + size and a simple checksum at the end can greatly help.

I see. So this needs to be handled manually instead of being automated by mbed or other frameworks.
Seems like I missunderstood something.

So I think something like this could work:

  • WriteCharacteristic to write data to
  • NotifyCharacteristic to notify the client when the device is ready for the next chunk
  • (Optional) Another WriteCharacteristic that is used as some kind of “command” - for example this could be used to write how many chunks are to be expected.

Hmm I’m not sure what you mean.

To give you a concrete example: we have robot that is remote controlled by an iPad. The iPad can send commands to the robot and the robot has to execute them. We use only one service/characteristic.

I can send one command or multiple commands. My command frame always start with 2A 2B 2C 2D then I have the command length, the commands and finally a checksum on the whole command part. This way I make sure that before executing one or multiple commands received, they are well formed and that the robot will behave the way it is expected.

The frame can be very long, so I store that in a circular buffer then read the buffer until I find the start sequence, then read the length, then the commands and compute the checksum to compare it with the one sent.

This is necessary because we send a lot of commands. If you only send a string every once in a while, the solution can be simpler. But you need a way to say “this is the start and this is the end”.

That’s pretty clever, but as I only need to send a string once in a while I can probably get away with a bit of a simpler solution. Will have to think a bit about that, but I think you pointed me in the right direction, thanks a lot!

ATT_MTU is described here: GattClient - API references and tutorials | Mbed OS 6 Documentation

Here it notes that GattServer::EventHandler is also informed when the client requests a change.