Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: TYBLE16_simple_data_logger TYBLE16_MP3_Air
ConnectionParameters.h
00001 /* mbed Microcontroller Library 00002 * Copyright (c) 2018 ARM Limited 00003 * 00004 * Licensed under the Apache License, Version 2.0 (the "License"); 00005 * you may not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an "AS IS" BASIS, 00012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 00017 #ifndef MBED_EXTENDED_CONNECT_PARAMETERS_H__ 00018 #define MBED_EXTENDED_CONNECT_PARAMETERS_H__ 00019 00020 #include "ble/BLETypes.h" 00021 #include "mbed_assert.h" 00022 00023 namespace ble { 00024 00025 /** 00026 * @addtogroup ble 00027 * @{ 00028 * @addtogroup gap 00029 * @{ 00030 */ 00031 00032 /** 00033 * Parameters defining the connection initiation process. 00034 * 00035 * The connection initiation process is divided in two different phases. First, 00036 * the initiating device scans for the peer to which it should connect. Once it finds 00037 * the peer, it sends a connection request that contains the connection 00038 * parameters. 00039 * 00040 * @par Scan parameters 00041 * 00042 * The scan parameters are defined by two durations: the scan interval and the 00043 * scan window. The scan interval is the duration between two scan cycles, and the 00044 * scan window defines how long the device searches during a scan cycle. 00045 * 00046 * You can set the scan window and the scan interval at construction time or by 00047 * calling setScanParameters(). 00048 * 00049 * @par Connection parameters 00050 * 00051 * A Bluetooth connection is defined by three parameters: 00052 * - Connection interval: The time between two connection events. A minimum 00053 * and a maximum connection interval are requested to help the Bluetooth 00054 * subsystem deal with concurrent radio processing. 00055 * - Slave latency: Number of connection events that can be ignored by the 00056 * slave. 00057 * - Supervision timeout: Time after which the connection is considered lost 00058 * if the connected devices haven't exchanged a single packet. It is important 00059 * to note that even if the application doesn't send actual data, the Bluetooth 00060 * controller takes care of sending empty data packets to maintain the 00061 * connection. 00062 * 00063 * You can set these parameters at construction time or by calling the function 00064 * setConnectionParameters(). 00065 * 00066 * @par PHY 00067 * 00068 * Bluetooth 5 has introduced the support of different physical layer to either 00069 * increase the range or the throughput. You can configure multiple PHY 00070 * independently for scanning and connecting. 00071 * 00072 * Legacy connection happens on the 1M PHY (phy_t::LE_1M). It is the only PHY 00073 * that you can configure on legacy systems. 00074 * 00075 * The constructor, setScanParameters() and setConnectionParameters() accept 00076 * a phy_t parameter that defines to which PHY the parameters set applies. 00077 * 00078 * @par Other parameters: 00079 * 00080 * It is possible to define what type of address is used to establish the 00081 * connection and whether the whitelist should be used to find the peer 00082 * to connect to. 00083 * 00084 * @par Example: 00085 * 00086 * Thanks to the fluent API, you can compose the connection parameters at 00087 * instantiation point: 00088 * 00089 * @code 00090 * 00091 void do_connect(ble::Gap& gap, ble::target_peer_address_type_t addr_type, ble::address_t& address) 00092 { 00093 using namespace ble; 00094 00095 gap.connect( 00096 addr_type, 00097 address, 00098 ConnectionParameters() 00099 .setScanParameters( 00100 phy_t::LE_1M, 00101 scan_interval_t(millisecond_t(500)), 00102 scan_window_t(millisecond_t(250)) 00103 ) 00104 .setConnectionParameters( 00105 phy_t::LE_1M, 00106 conn_interval_t(millisecond_t(100)), 00107 conn_interval_t(millisecond_t(200)), 00108 slave_latency_t(0), 00109 supervision_timeout_t(millisecond_t(1000)) 00110 ) 00111 .setOwnAddressType(own_address_type_t::RANDOM) 00112 ); 00113 } 00114 * 00115 * @endcode 00116 * 00117 * @note It is not possible to configure phy_t::LE_2M for scanning. 00118 * 00119 * @see ble::Gap::connect() 00120 */ 00121 class ConnectionParameters { 00122 enum { 00123 LE_1M_INDEX = 0, 00124 LE_2M_INDEX = 1, 00125 LE_CODED_INDEX = 2, 00126 #if BLE_FEATURE_PHY_MANAGEMENT 00127 MAX_PARAM_PHYS = 3 00128 #else 00129 MAX_PARAM_PHYS = 1 00130 #endif // BLE_FEATURE_PHY_MANAGEMENT 00131 }; 00132 00133 public: 00134 /** 00135 * Create a ConnectionParameters object. 00136 * 00137 * @param phy The PHY being configured. 00138 * @param scanInterval Interval between two scans. 00139 * @param scanWindow Scan duration during a scan interval. 00140 * @param minConnectionInterval Minimum value of the connection interval. 00141 * @param maxConnectionInterval Maximum value of the connection interval. 00142 * @param slaveLatency Maximum number of packets the slave can drop. 00143 * @param connectionSupervisionTimeout Time after which the connection is 00144 * considered lost if no data has been exchanged. 00145 * @param minEventLength Minimum duration of a connection event. 00146 * @param maxEventLength Maximum duration of a connection event. 00147 */ 00148 ConnectionParameters( 00149 phy_t phy = phy_t::LE_1M, 00150 scan_interval_t scanInterval = scan_interval_t::min(), 00151 scan_window_t scanWindow = scan_window_t::min(), 00152 conn_interval_t minConnectionInterval = conn_interval_t(50), 00153 conn_interval_t maxConnectionInterval = conn_interval_t(100), 00154 slave_latency_t slaveLatency = slave_latency_t::min(), 00155 supervision_timeout_t connectionSupervisionTimeout = supervision_timeout_t(100), 00156 conn_event_length_t minEventLength = conn_event_length_t::min(), 00157 conn_event_length_t maxEventLength = conn_event_length_t::max() 00158 ); 00159 00160 /* setters */ 00161 00162 /** 00163 * Set the scan parameters for a given PHY. 00164 * 00165 * @param phy PHY being configured. 00166 * @param scanInterval Interval between two scans. 00167 * @param scanWindow Scan duration within a scan interval. 00168 * 00169 * @note It is useless to configure the 2M PHY because it is not used during 00170 * scanning. 00171 * 00172 * @return A reference to this. 00173 */ 00174 ConnectionParameters &setScanParameters( 00175 phy_t phy, 00176 scan_interval_t scanInterval, 00177 scan_window_t scanWindow 00178 ); 00179 00180 /** 00181 * Set the conenction parameters of a given PHY. 00182 * 00183 * @param phy The PHY being configured. 00184 * @param minConnectionInterval Minimum connection interval. 00185 * @param maxConnectionInterval Maximum connection interval. 00186 * @param slaveLatency Maximum number of packets the slave can drop. 00187 * @param connectionSupervisionTimeout Time after which the connection is 00188 * considered lost if no data has been exchanged. 00189 * @param minEventLength Minimum duration of a connection event. 00190 * @param maxEventLength Maximum duration of a connection event. 00191 * 00192 * @return A reference to this. 00193 */ 00194 ConnectionParameters &setConnectionParameters( 00195 phy_t phy, 00196 conn_interval_t minConnectionInterval, 00197 conn_interval_t maxConnectionInterval, 00198 slave_latency_t slaveLatency, 00199 supervision_timeout_t connectionSupervisionTimeout, 00200 conn_event_length_t minEventLength = conn_event_length_t::min(), 00201 conn_event_length_t maxEventLength = conn_event_length_t::max() 00202 ); 00203 00204 /** 00205 * Address type used by the local device to connect the peer. 00206 * @param ownAddress Type of address used to initiate the connection. 00207 * @return A reference to this. 00208 */ 00209 ConnectionParameters &setOwnAddressType(own_address_type_t ownAddress) 00210 { 00211 _ownAddressType = ownAddress; 00212 return *this; 00213 } 00214 00215 /** 00216 * Set if the whitelist should be used to find the peer. 00217 * 00218 * @param filterPolicy The initiator filter to apply. 00219 * 00220 * @return A reference to this. 00221 */ 00222 ConnectionParameters &setFilter(initiator_filter_policy_t filterPolicy) 00223 { 00224 #if BLE_FEATURE_WHITELIST 00225 _filterPolicy = filterPolicy; 00226 #endif // BLE_FEATURE_WHITELIST 00227 return *this; 00228 } 00229 00230 /** 00231 * Enable or disable PHYs. 00232 * 00233 * @param phy1M true to enable the 1M PHY and false to disable it. 00234 * @param phy2M true to enable the 2M PHY and false to disable it. 00235 * @param phyCoded true to enable the CODED PHY and false to disable it. 00236 * 00237 * @return A reference to this. 00238 */ 00239 ConnectionParameters &togglePhy(bool phy1M, bool phy2M, bool phyCoded) 00240 { 00241 #if BLE_FEATURE_PHY_MANAGEMENT 00242 handlePhyToggle(phy_t::LE_1M, phy1M); 00243 handlePhyToggle(phy_t::LE_2M, phy2M); 00244 handlePhyToggle(phy_t::LE_CODED, phyCoded); 00245 #endif // BLE_FEATURE_PHY_MANAGEMENT 00246 return *this; 00247 } 00248 00249 /** 00250 * Disable an individual PHY. 00251 * 00252 * @param phy The PHY to disable. 00253 * 00254 * @return A reference to this. 00255 */ 00256 ConnectionParameters &disablePhy(phy_t phy = phy_t::LE_1M) 00257 { 00258 #if BLE_FEATURE_PHY_MANAGEMENT 00259 handlePhyToggle(phy, false); 00260 #endif // BLE_FEATURE_PHY_MANAGEMENT 00261 return *this; 00262 } 00263 00264 /** 00265 * Enable an individual PHY. 00266 * 00267 * @param phy The PHY to enable. 00268 * 00269 * @return A reference to this. 00270 */ 00271 ConnectionParameters &enablePhy(phy_t phy = phy_t::LE_1M) 00272 { 00273 #if BLE_FEATURE_PHY_MANAGEMENT 00274 handlePhyToggle(phy, true); 00275 #endif // BLE_FEATURE_PHY_MANAGEMENT 00276 return *this; 00277 } 00278 00279 /* getters */ 00280 00281 /** 00282 * Return the local address type used. 00283 * 00284 * @return The local address type to use. 00285 */ 00286 own_address_type_t getOwnAddressType() const 00287 { 00288 return _ownAddressType; 00289 } 00290 00291 /** 00292 * Return the initiator policy. 00293 * 00294 * @return The initiator policy. 00295 */ 00296 initiator_filter_policy_t getFilter() const 00297 { 00298 #if BLE_FEATURE_WHITELIST 00299 return _filterPolicy; 00300 #else 00301 return initiator_filter_policy_t::NO_FILTER; 00302 #endif // BLE_FEATURE_WHITELIST 00303 } 00304 00305 /** 00306 * Return the number of PHY enabled. 00307 * @return The number of PHY enabled. 00308 */ 00309 uint8_t getNumberOfEnabledPhys() const 00310 { 00311 return ( 00312 _enabledPhy[LE_1M_INDEX] * 1 00313 #if BLE_FEATURE_PHY_MANAGEMENT 00314 + _enabledPhy[LE_2M_INDEX] * 1 00315 + _enabledPhy[LE_CODED_INDEX] * 1 00316 #endif // BLE_FEATURE_PHY_MANAGEMENT 00317 ); 00318 } 00319 00320 #if !defined(DOXYGEN_ONLY) 00321 00322 phy_set_t getPhySet() const 00323 { 00324 #if BLE_FEATURE_PHY_MANAGEMENT 00325 phy_set_t set( 00326 _enabledPhy[LE_1M_INDEX], 00327 _enabledPhy[LE_2M_INDEX], 00328 _enabledPhy[LE_CODED_INDEX] 00329 ); 00330 return set; 00331 #else 00332 return phy_set_t::PHY_SET_1M; 00333 #endif // BLE_FEATURE_PHY_MANAGEMENT 00334 } 00335 00336 00337 /* These return pointers to arrays of settings valid only across the number of active PHYs */ 00338 00339 const uint16_t *getScanIntervalArray() const 00340 { 00341 return &_scanInterval[getFirstEnabledIndex()]; 00342 } 00343 00344 const uint16_t *getScanWindowArray() const 00345 { 00346 return &_scanWindow[getFirstEnabledIndex()]; 00347 } 00348 00349 const uint16_t *getMinConnectionIntervalArray() const 00350 { 00351 return &_minConnectionInterval[getFirstEnabledIndex()]; 00352 } 00353 00354 const uint16_t *getMaxConnectionIntervalArray() const 00355 { 00356 return &_maxConnectionInterval[getFirstEnabledIndex()]; 00357 } 00358 00359 const uint16_t *getSlaveLatencyArray() const 00360 { 00361 return &_slaveLatency[getFirstEnabledIndex()]; 00362 } 00363 00364 const uint16_t *getConnectionSupervisionTimeoutArray() const 00365 { 00366 return &_connectionSupervisionTimeout[getFirstEnabledIndex()]; 00367 } 00368 00369 const uint16_t *getMinEventLengthArray() const 00370 { 00371 return &_minEventLength[getFirstEnabledIndex()]; 00372 } 00373 00374 const uint16_t *getMaxEventLengthArray() const 00375 { 00376 return &_maxEventLength[getFirstEnabledIndex()]; 00377 } 00378 00379 #endif 00380 00381 private: 00382 uint8_t getFirstEnabledIndex() const 00383 { 00384 #if BLE_FEATURE_PHY_MANAGEMENT 00385 if (_enabledPhy[LE_1M_INDEX]) { 00386 return LE_1M_INDEX; 00387 } else if (_enabledPhy[LE_2M_INDEX]) { 00388 return LE_2M_INDEX; 00389 } else if (_enabledPhy[LE_CODED_INDEX]) { 00390 return LE_CODED_INDEX; 00391 } 00392 /* This should never happen; it means you were trying to start a connection with a blank set 00393 * of parameters - you need to enable at least one PHY */ 00394 MBED_ASSERT("Trying to use connection parameters without any PHY defined."); 00395 #endif // BLE_FEATURE_PHY_MANAGEMENT 00396 return 0; 00397 } 00398 00399 /** Handle toggling PHYs on and off and return the correct index to use to set the configuration elements. 00400 * 00401 * @param phy Which PHY is being toggled. 00402 * @param enable On or Off. 00403 * @return The index to the array of settings. 00404 */ 00405 uint8_t handlePhyToggle(phy_t phy, bool enable) 00406 { 00407 uint8_t index = phyToIndex(phy); 00408 00409 #if BLE_FEATURE_PHY_MANAGEMENT 00410 bool was_swapped = isSwapped(); 00411 00412 _enabledPhy[index] = enable; 00413 00414 bool is_swapped = isSwapped(); 00415 00416 if (was_swapped != is_swapped) { 00417 swapCodedAnd2M(); 00418 } 00419 00420 if (is_swapped && index == LE_CODED_INDEX) { 00421 /* To keep the data contiguous, coded params are in place of the missing 2M params */ 00422 index = LE_2M_INDEX; 00423 } 00424 #endif // BLE_FEATURE_PHY_MANAGEMENT 00425 00426 return index; 00427 } 00428 00429 uint8_t phyToIndex(phy_t phy) const 00430 { 00431 uint8_t index; 00432 switch (phy.value()) { 00433 case phy_t::LE_1M: 00434 index = LE_1M_INDEX; 00435 break; 00436 #if BLE_FEATURE_PHY_MANAGEMENT 00437 case phy_t::LE_2M: 00438 index = LE_2M_INDEX; 00439 break; 00440 case phy_t::LE_CODED: 00441 index = LE_CODED_INDEX; 00442 break; 00443 #endif // BLE_FEATURE_PHY_MANAGEMENT 00444 default: 00445 index = LE_1M_INDEX; 00446 MBED_ASSERT("Illegal PHY"); 00447 break; 00448 } 00449 return index; 00450 } 00451 00452 #if BLE_FEATURE_PHY_MANAGEMENT 00453 bool isSwapped() const 00454 { 00455 return ( 00456 _enabledPhy[LE_1M_INDEX] && 00457 !_enabledPhy[LE_2M_INDEX] && 00458 _enabledPhy[LE_CODED_INDEX] 00459 ); 00460 } 00461 00462 /** Handle the swapping of 2M and CODED so that the array is ready for the pal call. */ 00463 void swapCodedAnd2M(); 00464 #endif // BLE_FEATURE_PHY_MANAGEMENT 00465 00466 private: 00467 initiator_filter_policy_t _filterPolicy; 00468 own_address_type_t _ownAddressType; 00469 00470 uint16_t _scanInterval[MAX_PARAM_PHYS]; /* 0.625 ms */ 00471 uint16_t _scanWindow[MAX_PARAM_PHYS]; /* 0.625 ms */ 00472 uint16_t _minConnectionInterval[MAX_PARAM_PHYS]; /* 1.25 ms */ 00473 uint16_t _maxConnectionInterval[MAX_PARAM_PHYS]; /* 1.25 ms */ 00474 uint16_t _slaveLatency[MAX_PARAM_PHYS]; /* events */ 00475 uint16_t _connectionSupervisionTimeout[MAX_PARAM_PHYS]; /* 10 ms */ 00476 uint16_t _minEventLength[MAX_PARAM_PHYS]; /* 0.625 ms */ 00477 uint16_t _maxEventLength[MAX_PARAM_PHYS]; /* 0.625 ms */ 00478 00479 bool _enabledPhy[MAX_PARAM_PHYS]; 00480 }; 00481 00482 /** 00483 * @} 00484 * @} 00485 */ 00486 00487 } // namespace ble 00488 00489 #endif /* ifndef MBED_EXTENDED_CONNECT_PARAMETERS_H__ */
Generated on Tue Jul 12 2022 13:54:13 by
