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

sd_ble_gattc_read returning 0 (zero)

Hi,

We are developing an application on a nRF52840 using the nrf SDK (16.0) which should connect to a nRF52832 device, read characteristics of two different custom services, and disconnect again. For one service this works perfectly, however when reading a specific 4 byte timestamp characteristic we are experiencing some issues. In more than 50% of our attempts we are reading a zero value, in all other cases we receive the expected value. When we verify on the nrf connect android application, the correct value is always read successfully. Below you can find some code snippets related to the issue. Any feedback on where to start looking would be greatly appreciated!

  • Read request:

ret_code_t ble_config_c_read_timestamp(ble_config_c_t *p_ble_config_c)
{
    ret_code_t err_code;
    nrf_ble_gq_req_t config_c_req;

    VERIFY_PARAM_NOT_NULL(p_ble_config_c);

    if ((p_ble_config_c->conn_handle == BLE_CONN_HANDLE_INVALID) ||
        (p_ble_config_c->peer_config_db.timestamp_value_handle == BLE_GATT_HANDLE_INVALID))
    {
        return NRF_ERROR_INVALID_STATE;
    }

    memset(&config_c_req, 0, sizeof(config_c_req));
    config_c_req.type = NRF_BLE_GQ_REQ_GATTC_READ;
    config_c_req.error_handler.cb = gatt_error_handler;
    config_c_req.error_handler.p_ctx = p_ble_config_c;
    config_c_req.params.gattc_read.handle = p_ble_config_c->peer_config_db.timestamp_value_handle;

    err_code = nrf_ble_gq_item_add(p_ble_config_c->p_gatt_queue, &config_c_req, p_ble_config_c->conn_handle);
    return err_code;
}

  • Read response:

void ble_config_c_on_ble_evt(ble_evt_t const *p_ble_evt, void *p_context)
{
    ble_config_c_t *p_ble_config_c = (ble_config_c_t *)p_context;

    if ((p_ble_config_c == NULL) || (p_ble_evt == NULL))
    {
        return;
    }

    switch (p_ble_evt->header.evt_id)
    {

    case BLE_GATTC_EVT_READ_RSP:
        on_read_rsp(p_ble_config_c, p_ble_evt);
        break;

    default:
        break;
    }
}

static void on_read_rsp(ble_config_c_t *p_ble_config_c, ble_evt_t const *p_ble_evt)
{
    ble_gattc_evt_read_rsp_t const *p_response = &p_ble_evt->evt.gattc_evt.params.read_rsp;
    ble_config_c_evt_t ble_config_c_evt;

    // Check if the event is on the link for this instance and the event handler is present.
    if ((p_ble_config_c->evt_handler == NULL) ||
        (p_ble_config_c->conn_handle != p_ble_evt->evt.gattc_evt.conn_handle))
    {
        return;
    }

    if (p_ble_evt->evt.gattc_evt.gatt_status == BLE_GATT_STATUS_SUCCESS)
    {
        if (p_response->handle == p_ble_config_c->peer_config_db.timestamp_value_handle)
        {
            ble_config_c_evt.evt_type = BLE_CONFIG_C_EVT_TIMESTAMP_READ;
            ble_config_c_evt.conn_handle = p_ble_config_c->conn_handle;
            NRF_LOG_INFO("Received config data %lu of length %u", * (uint32_t *) p_response->data, p_response->len);

            memcpy(&(ble_config_c_evt.timestamp), p_response->data, 4);

            p_ble_config_c->evt_handler(p_ble_config_c, &ble_config_c_evt);
        }
    }
}

Related