static void conn_params_negotiation(void) { // Start negotiation if the received connection parameters are not acceptable if (!is_conn_params_ok(&m_current_conn_params)) { #ifdef USE_APP_TIMER uint32_t err_code; #endif uint32_t timeout_ticks; if (m_change_param) { // Notify the application that the procedure has failed if (m_conn_params_config.evt_handler != NULL) { ble_conn_params_evt_t evt; evt.evt_type = BLE_CONN_PARAMS_EVT_FAILED; m_conn_params_config.evt_handler(&evt); } } else { if (m_update_count == 0) { // First connection parameter update timeout_ticks = m_conn_params_config.first_conn_params_update_delay; } else { timeout_ticks = m_conn_params_config.next_conn_params_update_delay; } #ifdef USE_APP_TIMER err_code = app_timer_start(m_conn_params_timer_id, timeout_ticks, NULL); if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) { m_conn_params_config.error_handler(err_code); } #else m_conn_params_timer.attach(update_timeout_handler, timeout_ticks / 32768); #endif } } else { // Notify the application that the procedure has succeded if (m_conn_params_config.evt_handler != NULL) { ble_conn_params_evt_t evt; evt.evt_type = BLE_CONN_PARAMS_EVT_SUCCEEDED; m_conn_params_config.evt_handler(&evt); } } m_change_param = false; }
static void update_timeout_handler(void * p_context) { UNUSED_PARAMETER(p_context); #else /* #if !USE_APP_TIMER */ static void update_timeout_handler(void) { m_conn_params_timer.detach(); /* this is supposed to be a single-shot timer callback */ #endif /* #if !USE_APP_TIMER */ if (m_conn_handle != BLE_CONN_HANDLE_INVALID) { // Check if we have reached the maximum number of attempts m_update_count++; if (m_update_count <= m_conn_params_config.max_conn_params_update_count) { uint32_t err_code; // Parameters are not ok, send connection parameters update request. err_code = sd_ble_gap_conn_param_update(m_conn_handle, &m_preferred_conn_params); if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) { m_conn_params_config.error_handler(err_code); } } else { m_update_count = 0; // Negotiation failed, disconnect automatically if this has been configured if (m_conn_params_config.disconnect_on_fail) { uint32_t err_code; err_code = sd_ble_gap_disconnect(m_conn_handle, BLE_HCI_CONN_INTERVAL_UNACCEPTABLE); if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) { m_conn_params_config.error_handler(err_code); } } // Notify the application that the procedure has failed if (m_conn_params_config.evt_handler != NULL) { ble_conn_params_evt_t evt; evt.evt_type = BLE_CONN_PARAMS_EVT_FAILED; m_conn_params_config.evt_handler(&evt); } } } }
uint32_t ble_conn_params_change_conn_params(ble_gap_conn_params_t * new_params) { uint32_t err_code; m_preferred_conn_params = *new_params; // Set the connection params in stack err_code = sd_ble_gap_ppcp_set(&m_preferred_conn_params); if (err_code == NRF_SUCCESS) { if (!is_conn_params_ok(&m_current_conn_params)) { m_change_param = true; err_code = sd_ble_gap_conn_param_update(m_conn_handle, &m_preferred_conn_params); m_update_count = 1; } else { // Notify the application that the procedure has succeded if (m_conn_params_config.evt_handler != NULL) { ble_conn_params_evt_t evt; evt.evt_type = BLE_CONN_PARAMS_EVT_SUCCEEDED; m_conn_params_config.evt_handler(&evt); } err_code = NRF_SUCCESS; } } return err_code; }
static void on_write(ble_evt_t * p_ble_evt) { ble_gatts_evt_write_t * p_evt_write = &p_ble_evt->evt.gatts_evt.params.write; // Check if this the correct CCCD if ( (p_evt_write->handle == m_conn_params_config.start_on_notify_cccd_handle) && (p_evt_write->len == 2) ) { // Check if this is a 'start notification' if (ble_srv_is_notification_enabled(p_evt_write->data)) { // Do connection parameter negotiation if necessary conn_params_negotiation(); } else { #ifdef USE_APP_TIMER uint32_t err_code; // Stop timer if running err_code = app_timer_stop(m_conn_params_timer_id); if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) { m_conn_params_config.error_handler(err_code); } #else /* #if !USE_APP_TIMER */ m_conn_params_timer.detach(); #endif /* #if !USE_APP_TIMER */ } } }
static void on_disconnect(ble_evt_t * p_ble_evt) { uint32_t err_code; m_conn_handle = BLE_CONN_HANDLE_INVALID; // Stop timer if running m_update_count = 0; // Connection parameters updates should happen during every connection err_code = app_timer_stop(m_conn_params_timer_id); if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) { m_conn_params_config.error_handler(err_code); } }