This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Storing system attributes manually to enable notifications

We would like to pre-bond our devices in production by writing bonding data into flash. Generating LTKs is easy enough. But we'd also like to store that notifications on peripheral were enabled, even though they never even connected before.

I'm aware of the sd_ble_gatts_sys_attr_set and that local gatt database is updated when using peer manager and enabling notifications through normal route. That way they get re-enabled on next connection. I tried inspecting pm_peer_data_local_gatt_db_t using pds_peer_data_read after normal bonding, but values don't make much sense to me. 

If someone could point me in right direction, like when does peer manager store the gatt databse, or the format of pm_peer_data_local_gatt_db_t::data would be appreciated.

Parents Reply Children
  • What is the reason you would like to pre-bond the devices? What benefits are you seeking from doing this, over doing the regular device service discovery and bonding upon the first connection?

    One reason for pre-bond is that devices come as a pair and should only connect to each other over their lifetime. Other is that in time of production we can test them and if you have more than 1 person trying to connect devices, you're bound to get cross connections.

    We also do regular service discovery and bonding upon first connection in case of device "reset" which a client can trigger. However that's not the usual case.

    This is unfortunately not possible, since the cccd have to be set by the GATT Client prior to notifications being sent.

    If the GATT client was a device we have no control over then it's indeed impossible, but I don't see how it's not possible if we have control over both devices. Isn't the client (our central in this case) just setting system attributes it saved with peer manager?

  • Hello again,

    Thank you for your patience with this. The summer holidays have begun here in Norway, and DevZone is therefore operating with reduced staff for the time being. Sorry for any inconvenience this might cause. 

    Darkenkade said:
    One reason for pre-bond is that devices come as a pair and should only connect to each other over their lifetime.

    I understand. Did you read the discussion in the ticket I linked about the security and logistics aspects of pre-bonded devices?

    Darkenkade said:
    Other is that in time of production we can test them and if you have more than 1 person trying to connect devices, you're bound to get cross connections.

    I am not sure I understand exactly what you mean by this. There are multiple ways to do the connection / bonding, if you are concerned that multiple centrals might try to initiate a connection when you open your peripheral device for connections. Does you peripheral have any I/O interfaces?

    Darkenkade said:
    If the GATT client was a device we have no control over then it's indeed impossible, but I don't see how it's not possible if we have control over both devices. Isn't the client (our central in this case) just setting system attributes it saved with peer manager?

    No, the actual CCCD value is stored in the SoftDevice, and is not accessible to the application layer. The .cccd value you see in the peer manager is just a copy of this, for use by the application layer.
    However, once service discovery has finished it only requires a single packet to set the CCCD for the characteristic, so this should not impede your process / communication between the devices.

    Best regards,
    Karl

  • Hello,

    No issues with waiting, I'm glad to receive any help at all. You guys are doing great work with your answers and helping the community. One of the best teams out there in terms of support so far.

    Did you read the discussion in the ticket I linked about the security and logistics aspects of pre-bonded devices?

    Yes I am aware of issues. I was considering just writing OOB data (some key) into flash at time of programming and try to connect with OOB enabled. But the code gets rather complex to handle that case, since it has to support re-pairing to a different central all-together.

    Does you peripheral have any I/O interfaces?

    Peripheral has only one button, which is not enough to differentiate if there's more than one of them.

    We'll probably settle on some scheme where we tell the central which address to pair/bond with, that way we can eliminate most issues.

    No, the actual CCCD value is stored in the SoftDevice, and is not accessible to the application layer.

    It makes sense how it's impossible then. Thank you for clarification. 

    This brings me to another problem, for which I might open another ticket or if you answer it here for me.

    I notice that if I blindly enable notifications, the peripheral will update the value stored in flash even if they are already enabled, which is why I made a workaround to check if notifications are already enabled by reading the peripheral CCCD value on central before enabling notifications.

    This works well, unless I want to re-pair devices. Then when sending notifications I get BLE_ERROR_GATTS_SYS_ATTR_MISSING, which I assume is because central reads old CCCD which is enabled, since we paired before. 

    Is there a way to enable notifications on re-pairing if either side has missing keys?

Related