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

Incorrect custom service being updated by ble_cus_custom_value_update()

Hi in the code below I successfully register multiple custom services (m_cus and m_cus2) using NRF_SDH_BLE_OBSERVERS().  In my original code when notifications is turned on for custom characteristic of m_cus the characteristic value would increment every second. However, now I notice that the characteristic value for m_cus no longer increments every second when notifications is turned on. If I turn on the notifications for the characteristic of m_cus2, strangely it will increment. 

#main.c
BLE_CUS_DEF(m_cus, 0); 
BLE_CUS_DEF(m_cus2, 1);  

static void notification_timeout_handler(void * p_context)
{
    UNUSED_PARAMETER(p_context);
    ret_code_t err_code;
    
    // Increment the value of m_custom_value before notifying it.
    m_custom_value++;
 
    if(notif_bool == 1){
       err_code = ble_cus_custom_value_update(&m_cus, m_custom_value);
       APP_ERROR_CHECK(err_code);
    }
}

//ble_cus.h
#define BLE_CUS_DEF(_name, _cnt)                                                                      \
static ble_cus_t _name[_cnt];                          \
NRF_SDH_BLE_OBSERVERS(_name ## _obs,                                                                 \
                     BLE_HRS_BLE_OBSERVER_PRIO,                                                     \
                     ble_cus_on_ble_evt, &_name, _cnt)

I further check the definition for ble_cus_custom_value_update() and it is supposed to only modify the characteristic value for the custom service passed into parameter 'p_cus'. In the 'notification_timeout_handler' code above, the event handler code only passes in m_cus into the 'p_cus' parameter of ble_cus_custom_value_update(). 

sd_ble_gatts_value_set(p_cus->conn_handle,
p_cus->custom_value_handles.value_handle,
&gatts_value);

sd_ble_gatts_hvx(p_cus->conn_handle, &hvx_params);

If m_cus has a different conn_handle and custom_value_handles.value_handle, then m_cus2 the custom characteristic value updates should not be mixed up between different custom services/characteristics.

However, right now the most confusing issue is why m_cus2 is getting its custom characteristic value incremented after notifications are turned on, when this behavior was supposed to be for m_cus only.  Any suggestions? Thank you.

Project files and code attached below. 

ble_app_template_nordic_fds.zip

Parents
  • Hi Thoric_fish, 

    Firstly which SDK version are you using?

    I see that you have defined BLE_CUS_DEF the following way

     

    #define BLE_CUS_DEF(_name, _cnt)                                                                      \
    static ble_cus_t _name[_cnt];                          \
    NRF_SDH_BLE_OBSERVERS(_name ## _obs,                                                                 \
                         BLE_HRS_BLE_OBSERVER_PRIO,                                                     \
                         ble_cus_on_ble_evt, &_name, _cnt)
    

    I would argue that there is no need to add BLE_CUS_DEF twice in main.c when you're using NRF_SDH_BLE_OBSERVERS and not NRF_SDH_BLE_OBSERVER. Now, you're infact declaring 4 ble_cus structs as well as registering 4 observers instead of two. 

    However, right now the most confusing issue is why m_cus2 is getting its custom characteristic value incremented after notifications are turned on, when this behavior was supposed to be for m_cus only.  Any suggestions?

    I agree that  since ble_cus_custom_value_update(ble_cus_t * p_cusuint8_t custom_value) takes a pointer to a ble_cus_t structure, then the sd_ble_gatts_value_set() and sd_ble_gatts_hvx() calls should refer to the handle passed with the p_cus pointer. 

    Which handle is used when you're calling ble_cus_custom_value_update()? Just add a NRF_LOG_INFO() line that prints the p_cus->custom_value_handles.value_handle.

    Best regards

    Bjørn

  • Hi Bjørn,

    I am using SDK v15. I will try to find the handle for ble_cus_custom_value_update(). 

    I would argue that there is no need to add BLE_CUS_DEF twice in main.c when you're using NRF_SDH_BLE_OBSERVERS and not NRF_SDH_BLE_OBSERVER. Now, you're infact declaring 4 ble_cus structs as well as registering 4 observers instead of two. 



    So what is the proper way to declare and register 'mcus2' (the second instance of the custom service ble_cus_s struct), if there is no need to call BLE_CUS_DEF twice in main.c? 

  • Call BLE_CUS_DEF once with cnt set to 2 ( which ever number of custom services youre populating the gatt table with) so that it defines an array of ble_cus_s structures. Then refer to the first instance as &mcus[0] and the second as &mcus[2] etc.  

  • Hi Bjørn,

    So when I call BLE_CUS_DEF in main.c, I should now pass mcus into the first parameter of the BLE_CUS_DEF(mcus, 2) call? Then I can use mcus[0] and mcus[1] as the two instances

Reply Children
Related