Patched version of nrf51822 FOTA compatible driver, with GPTIO disabled, as it clashed with the mbed definitions...
Fork of nRF51822 by
ble_conn_params.cpp
00001 /* Copyright (c) 2012 Nordic Semiconductor. All Rights Reserved. 00002 * 00003 * The information contained herein is property of Nordic Semiconductor ASA. 00004 * Terms and conditions of usage are described in detail in NORDIC 00005 * SEMICONDUCTOR STANDARD SOFTWARE LICENSE AGREEMENT. 00006 * 00007 * Licensees are granted free, non-transferable use of the information. NO 00008 * WARRANTY of ANY KIND is provided. This heading must NOT be removed from 00009 * the file. 00010 * 00011 */ 00012 00013 #include "ble_conn_params.h " 00014 #include <stdlib.h> 00015 #include "nordic_common.h" 00016 #include "ble_hci.h" 00017 #include "ble_srv_common.h " 00018 #include "app_util.h " 00019 00020 #ifdef USE_APP_TIMER 00021 #include "app_timer.h" 00022 #else 00023 #include "mbed.h" 00024 #endif 00025 00026 static ble_conn_params_init_t m_conn_params_config; /**< Configuration as specified by the application. */ 00027 static ble_gap_conn_params_t m_preferred_conn_params; /**< Connection parameters preferred by the application. */ 00028 static uint8_t m_update_count; /**< Number of Connection Parameter Update messages that has currently been sent. */ 00029 static uint16_t m_conn_handle; /**< Current connection handle. */ 00030 static ble_gap_conn_params_t m_current_conn_params; /**< Connection parameters received in the most recent Connect event. */ 00031 #ifdef USE_APP_TIMER 00032 static app_timer_id_t m_conn_params_timer_id; /**< Connection parameters timer. */ 00033 #else 00034 static Ticker m_conn_params_timer; 00035 #endif 00036 00037 static bool m_change_param = false; 00038 00039 static bool is_conn_params_ok(ble_gap_conn_params_t * p_conn_params) 00040 { 00041 // Check if interval is within the acceptable range. 00042 // NOTE: Using max_conn_interval in the received event data because this contains 00043 // the client's connection interval. 00044 if ( 00045 (p_conn_params->max_conn_interval >= m_preferred_conn_params.min_conn_interval) 00046 && 00047 (p_conn_params->max_conn_interval <= m_preferred_conn_params.max_conn_interval) 00048 ) 00049 { 00050 return true; 00051 } 00052 else 00053 { 00054 return false; 00055 } 00056 } 00057 00058 00059 #ifdef USE_APP_TIMER 00060 static void update_timeout_handler(void * p_context) 00061 { 00062 UNUSED_PARAMETER(p_context); 00063 00064 #else /* #if !USE_APP_TIMER */ 00065 static void update_timeout_handler(void) 00066 { 00067 m_conn_params_timer.detach(); /* this is supposed to be a single-shot timer callback */ 00068 #endif /* #if !USE_APP_TIMER */ 00069 if (m_conn_handle != BLE_CONN_HANDLE_INVALID) 00070 { 00071 // Check if we have reached the maximum number of attempts 00072 m_update_count++; 00073 if (m_update_count <= m_conn_params_config.max_conn_params_update_count) 00074 { 00075 uint32_t err_code; 00076 00077 // Parameters are not ok, send connection parameters update request. 00078 err_code = sd_ble_gap_conn_param_update(m_conn_handle, &m_preferred_conn_params); 00079 if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) 00080 { 00081 m_conn_params_config.error_handler(err_code); 00082 } 00083 } 00084 else 00085 { 00086 m_update_count = 0; 00087 00088 // Negotiation failed, disconnect automatically if this has been configured 00089 if (m_conn_params_config.disconnect_on_fail) 00090 { 00091 uint32_t err_code; 00092 00093 err_code = sd_ble_gap_disconnect(m_conn_handle, BLE_HCI_CONN_INTERVAL_UNACCEPTABLE); 00094 if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) 00095 { 00096 m_conn_params_config.error_handler(err_code); 00097 } 00098 } 00099 00100 // Notify the application that the procedure has failed 00101 if (m_conn_params_config.evt_handler != NULL) 00102 { 00103 ble_conn_params_evt_t evt; 00104 00105 evt.evt_type = BLE_CONN_PARAMS_EVT_FAILED; 00106 m_conn_params_config.evt_handler(&evt); 00107 } 00108 } 00109 } 00110 } 00111 00112 00113 uint32_t ble_conn_params_init(const ble_conn_params_init_t * p_init) 00114 { 00115 uint32_t err_code; 00116 00117 m_conn_params_config = *p_init; 00118 m_change_param = false; 00119 if (p_init->p_conn_params != NULL) 00120 { 00121 m_preferred_conn_params = *p_init->p_conn_params; 00122 00123 // Set the connection params in stack 00124 err_code = sd_ble_gap_ppcp_set(&m_preferred_conn_params); 00125 if (err_code != NRF_SUCCESS) 00126 { 00127 return err_code; 00128 } 00129 } 00130 else 00131 { 00132 // Fetch the connection params from stack 00133 err_code = sd_ble_gap_ppcp_get(&m_preferred_conn_params); 00134 if (err_code != NRF_SUCCESS) 00135 { 00136 return err_code; 00137 } 00138 } 00139 00140 m_conn_handle = BLE_CONN_HANDLE_INVALID; 00141 m_update_count = 0; 00142 00143 #ifdef USE_APP_TIMER 00144 return app_timer_create(&m_conn_params_timer_id, 00145 APP_TIMER_MODE_SINGLE_SHOT, 00146 update_timeout_handler); 00147 #else 00148 return NRF_SUCCESS; 00149 #endif 00150 } 00151 00152 00153 uint32_t ble_conn_params_stop(void) 00154 { 00155 #ifdef USE_APP_TIMER 00156 return app_timer_stop(m_conn_params_timer_id); 00157 #else /* #if !USE_APP_TIMER */ 00158 m_conn_params_timer.detach(); 00159 return NRF_SUCCESS; 00160 #endif /* #if !USE_APP_TIMER */ 00161 } 00162 00163 00164 static void conn_params_negotiation(void) 00165 { 00166 // Start negotiation if the received connection parameters are not acceptable 00167 if (!is_conn_params_ok(&m_current_conn_params)) 00168 { 00169 #ifdef USE_APP_TIMER 00170 uint32_t err_code; 00171 #endif 00172 uint32_t timeout_ticks; 00173 00174 if (m_change_param) 00175 { 00176 // Notify the application that the procedure has failed 00177 if (m_conn_params_config.evt_handler != NULL) 00178 { 00179 ble_conn_params_evt_t evt; 00180 00181 evt.evt_type = BLE_CONN_PARAMS_EVT_FAILED; 00182 m_conn_params_config.evt_handler(&evt); 00183 } 00184 } 00185 else 00186 { 00187 if (m_update_count == 0) 00188 { 00189 // First connection parameter update 00190 timeout_ticks = m_conn_params_config.first_conn_params_update_delay; 00191 } 00192 else 00193 { 00194 timeout_ticks = m_conn_params_config.next_conn_params_update_delay; 00195 } 00196 00197 #ifdef USE_APP_TIMER 00198 err_code = app_timer_start(m_conn_params_timer_id, timeout_ticks, NULL); 00199 if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) 00200 { 00201 m_conn_params_config.error_handler(err_code); 00202 } 00203 #else 00204 m_conn_params_timer.attach(update_timeout_handler, timeout_ticks / 32768); 00205 #endif 00206 } 00207 } 00208 else 00209 { 00210 // Notify the application that the procedure has succeded 00211 if (m_conn_params_config.evt_handler != NULL) 00212 { 00213 ble_conn_params_evt_t evt; 00214 00215 evt.evt_type = BLE_CONN_PARAMS_EVT_SUCCEEDED; 00216 m_conn_params_config.evt_handler(&evt); 00217 } 00218 } 00219 m_change_param = false; 00220 } 00221 00222 00223 static void on_connect(ble_evt_t * p_ble_evt) 00224 { 00225 // Save connection parameters 00226 m_conn_handle = p_ble_evt->evt.gap_evt.conn_handle; 00227 m_current_conn_params = p_ble_evt->evt.gap_evt.params.connected.conn_params; 00228 m_update_count = 0; // Connection parameter negotiation should re-start every connection 00229 00230 // Check if we shall handle negotiation on connect 00231 if (m_conn_params_config.start_on_notify_cccd_handle == BLE_GATT_HANDLE_INVALID) 00232 { 00233 conn_params_negotiation(); 00234 } 00235 } 00236 00237 00238 static void on_disconnect(ble_evt_t * p_ble_evt) 00239 { 00240 #ifdef USE_APP_TIMER 00241 uint32_t err_code; 00242 #endif 00243 00244 m_conn_handle = BLE_CONN_HANDLE_INVALID; 00245 00246 // Stop timer if running 00247 m_update_count = 0; // Connection parameters updates should happen during every connection 00248 00249 #ifdef USE_APP_TIMER 00250 err_code = app_timer_stop(m_conn_params_timer_id); 00251 if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) 00252 { 00253 m_conn_params_config.error_handler(err_code); 00254 } 00255 #else 00256 m_conn_params_timer.detach(); 00257 #endif 00258 } 00259 00260 00261 static void on_write(ble_evt_t * p_ble_evt) 00262 { 00263 ble_gatts_evt_write_t * p_evt_write = &p_ble_evt->evt.gatts_evt.params.write; 00264 00265 // Check if this the correct CCCD 00266 if ( 00267 (p_evt_write->handle == m_conn_params_config.start_on_notify_cccd_handle) 00268 && 00269 (p_evt_write->len == 2) 00270 ) 00271 { 00272 // Check if this is a 'start notification' 00273 if (ble_srv_is_notification_enabled(p_evt_write->data)) 00274 { 00275 // Do connection parameter negotiation if necessary 00276 conn_params_negotiation(); 00277 } 00278 else 00279 { 00280 #ifdef USE_APP_TIMER 00281 uint32_t err_code; 00282 00283 // Stop timer if running 00284 err_code = app_timer_stop(m_conn_params_timer_id); 00285 if ((err_code != NRF_SUCCESS) && (m_conn_params_config.error_handler != NULL)) 00286 { 00287 m_conn_params_config.error_handler(err_code); 00288 } 00289 #else /* #if !USE_APP_TIMER */ 00290 m_conn_params_timer.detach(); 00291 #endif /* #if !USE_APP_TIMER */ 00292 } 00293 } 00294 } 00295 00296 00297 static void on_conn_params_update(ble_evt_t * p_ble_evt) 00298 { 00299 // Copy the parameters 00300 m_current_conn_params = p_ble_evt->evt.gap_evt.params.conn_param_update.conn_params; 00301 00302 conn_params_negotiation(); 00303 } 00304 00305 00306 void ble_conn_params_on_ble_evt(ble_evt_t * p_ble_evt) 00307 { 00308 switch (p_ble_evt->header.evt_id) 00309 { 00310 case BLE_GAP_EVT_CONNECTED: 00311 on_connect(p_ble_evt); 00312 break; 00313 00314 case BLE_GAP_EVT_DISCONNECTED: 00315 on_disconnect(p_ble_evt); 00316 break; 00317 00318 case BLE_GATTS_EVT_WRITE: 00319 on_write(p_ble_evt); 00320 break; 00321 00322 case BLE_GAP_EVT_CONN_PARAM_UPDATE: 00323 on_conn_params_update(p_ble_evt); 00324 break; 00325 00326 default: 00327 // No implementation needed. 00328 break; 00329 } 00330 } 00331 00332 uint32_t ble_conn_params_change_conn_params(ble_gap_conn_params_t *new_params) 00333 { 00334 uint32_t err_code; 00335 00336 m_preferred_conn_params = *new_params; 00337 // Set the connection params in stack 00338 err_code = sd_ble_gap_ppcp_set(&m_preferred_conn_params); 00339 if (err_code == NRF_SUCCESS) 00340 { 00341 if (!is_conn_params_ok(&m_current_conn_params)) 00342 { 00343 m_change_param = true; 00344 err_code = sd_ble_gap_conn_param_update(m_conn_handle, &m_preferred_conn_params); 00345 m_update_count = 1; 00346 } 00347 else 00348 { 00349 // Notify the application that the procedure has succeded 00350 if (m_conn_params_config.evt_handler != NULL) 00351 { 00352 ble_conn_params_evt_t evt; 00353 00354 evt.evt_type = BLE_CONN_PARAMS_EVT_SUCCEEDED; 00355 m_conn_params_config.evt_handler(&evt); 00356 } 00357 err_code = NRF_SUCCESS; 00358 } 00359 } 00360 return err_code; 00361 }
Generated on Tue Jul 12 2022 17:56:12 by 1.7.2