1 /* 2 * Copyright (c) 2016, The OpenThread Authors. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 3. Neither the name of the copyright holder nor the 13 * names of its contributors may be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 26 * POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29 /** 30 * @file 31 * @brief 32 * This file defines the radio interface for OpenThread. 33 * 34 */ 35 36 #ifndef OPENTHREAD_PLATFORM_RADIO_H_ 37 #define OPENTHREAD_PLATFORM_RADIO_H_ 38 39 #include <stdint.h> 40 41 #include <openthread/error.h> 42 #include <openthread/instance.h> 43 #include <openthread/platform/crypto.h> 44 45 #ifdef __cplusplus 46 extern "C" { 47 #endif 48 49 /** 50 * @addtogroup plat-radio 51 * 52 * @brief 53 * This module includes the platform abstraction for radio communication. 54 * 55 * @{ 56 * 57 */ 58 59 /** 60 * @defgroup radio-types Radio Types 61 * 62 * @brief 63 * This module includes the platform abstraction for a radio frame. 64 * 65 * @{ 66 * 67 */ 68 69 enum 70 { 71 OT_RADIO_FRAME_MAX_SIZE = 127, ///< aMaxPHYPacketSize (IEEE 802.15.4-2006) 72 OT_RADIO_FRAME_MIN_SIZE = 3, ///< Minimal size of frame FCS + CONTROL 73 74 OT_RADIO_SYMBOLS_PER_OCTET = 2, ///< 2.4 GHz IEEE 802.15.4-2006 75 OT_RADIO_BIT_RATE = 250000, ///< 2.4 GHz IEEE 802.15.4 (bits per second) 76 OT_RADIO_BITS_PER_OCTET = 8, ///< Number of bits per octet 77 78 // Per IEEE 802.15.4-2015, 12.3.3 Symbol rate: 79 // The O-QPSK PHY symbol rate shall be 25 ksymbol/s when operating in the 868 MHz band and 62.5 ksymbol/s when 80 // operating in the 780 MHz, 915 MHz, 2380 MHz, or 2450 MHz band 81 OT_RADIO_SYMBOL_RATE = 62500, ///< The O-QPSK PHY symbol rate when operating in the 780MHz, 915MHz, 2380MHz, 2450MHz 82 OT_RADIO_SYMBOL_TIME = 1000000 * 1 / OT_RADIO_SYMBOL_RATE, ///< Symbol duration time in unit of microseconds 83 OT_RADIO_TEN_SYMBOLS_TIME = 10 * OT_RADIO_SYMBOL_TIME, ///< Time for 10 symbols in unit of microseconds 84 85 OT_RADIO_LQI_NONE = 0, ///< LQI measurement not supported 86 OT_RADIO_RSSI_INVALID = 127, ///< Invalid or unknown RSSI value 87 OT_RADIO_POWER_INVALID = 127, ///< Invalid or unknown power value 88 }; 89 90 /** 91 * Defines the channel page. 92 * 93 */ 94 enum 95 { 96 OT_RADIO_CHANNEL_PAGE_0 = 0, ///< 2.4 GHz IEEE 802.15.4-2006 97 OT_RADIO_CHANNEL_PAGE_0_MASK = (1U << OT_RADIO_CHANNEL_PAGE_0), ///< 2.4 GHz IEEE 802.15.4-2006 98 OT_RADIO_CHANNEL_PAGE_2 = 2, ///< 915 MHz IEEE 802.15.4-2006 99 OT_RADIO_CHANNEL_PAGE_2_MASK = (1U << OT_RADIO_CHANNEL_PAGE_2), ///< 915 MHz IEEE 802.15.4-2006 100 }; 101 102 /** 103 * Defines the frequency band channel range. 104 * 105 */ 106 enum 107 { 108 OT_RADIO_915MHZ_OQPSK_CHANNEL_MIN = 1, ///< 915 MHz IEEE 802.15.4-2006 109 OT_RADIO_915MHZ_OQPSK_CHANNEL_MAX = 10, ///< 915 MHz IEEE 802.15.4-2006 110 OT_RADIO_915MHZ_OQPSK_CHANNEL_MASK = 0x3ff << OT_RADIO_915MHZ_OQPSK_CHANNEL_MIN, ///< 915 MHz IEEE 802.15.4-2006 111 OT_RADIO_2P4GHZ_OQPSK_CHANNEL_MIN = 11, ///< 2.4 GHz IEEE 802.15.4-2006 112 OT_RADIO_2P4GHZ_OQPSK_CHANNEL_MAX = 26, ///< 2.4 GHz IEEE 802.15.4-2006 113 OT_RADIO_2P4GHZ_OQPSK_CHANNEL_MASK = 0xffff << OT_RADIO_2P4GHZ_OQPSK_CHANNEL_MIN, ///< 2.4 GHz IEEE 802.15.4-2006 114 }; 115 116 /** 117 * Represents radio capabilities. 118 * 119 * The value is a bit-field indicating the capabilities supported by the radio. See `OT_RADIO_CAPS_*` definitions. 120 * 121 */ 122 typedef uint16_t otRadioCaps; 123 124 /** 125 * Defines constants that are used to indicate different radio capabilities. See `otRadioCaps`. 126 * 127 */ 128 enum 129 { 130 OT_RADIO_CAPS_NONE = 0, ///< Radio supports no capability. 131 OT_RADIO_CAPS_ACK_TIMEOUT = 1 << 0, ///< Radio supports AckTime event. 132 OT_RADIO_CAPS_ENERGY_SCAN = 1 << 1, ///< Radio supports Energy Scans. 133 OT_RADIO_CAPS_TRANSMIT_RETRIES = 1 << 2, ///< Radio supports tx retry logic with collision avoidance (CSMA). 134 OT_RADIO_CAPS_CSMA_BACKOFF = 1 << 3, ///< Radio supports CSMA backoff for frame transmission (but no retry). 135 OT_RADIO_CAPS_SLEEP_TO_TX = 1 << 4, ///< Radio supports direct transition from sleep to TX with CSMA. 136 OT_RADIO_CAPS_TRANSMIT_SEC = 1 << 5, ///< Radio supports tx security. 137 OT_RADIO_CAPS_TRANSMIT_TIMING = 1 << 6, ///< Radio supports tx at specific time. 138 OT_RADIO_CAPS_RECEIVE_TIMING = 1 << 7, ///< Radio supports rx at specific time. 139 OT_RADIO_CAPS_RX_ON_WHEN_IDLE = 1 << 8, ///< Radio supports RxOnWhenIdle handling. 140 }; 141 142 #define OT_PANID_BROADCAST 0xffff ///< IEEE 802.15.4 Broadcast PAN ID 143 144 /** 145 * Represents the IEEE 802.15.4 PAN ID. 146 * 147 */ 148 typedef uint16_t otPanId; 149 150 /** 151 * Represents the IEEE 802.15.4 Short Address. 152 * 153 */ 154 typedef uint16_t otShortAddress; 155 156 #define OT_EXT_ADDRESS_SIZE 8 ///< Size of an IEEE 802.15.4 Extended Address (bytes) 157 158 /** 159 * Defines constants about size of header IE in ACK. 160 * 161 */ 162 enum 163 { 164 OT_IE_HEADER_SIZE = 2, ///< Size of IE header in bytes. 165 OT_CSL_IE_SIZE = 4, ///< Size of CSL IE content in bytes. 166 OT_ACK_IE_MAX_SIZE = 16, ///< Max length for header IE in ACK. 167 OT_ENH_PROBING_IE_DATA_MAX_SIZE = 2, ///< Max length of Link Metrics data in Vendor-Specific IE. 168 }; 169 170 #define CSL_IE_HEADER_BYTES_LO 0x04 ///< Fixed CSL IE header first byte 171 #define CSL_IE_HEADER_BYTES_HI 0x0d ///< Fixed CSL IE header second byte 172 173 /** 174 * @struct otExtAddress 175 * 176 * Represents the IEEE 802.15.4 Extended Address. 177 * 178 */ 179 OT_TOOL_PACKED_BEGIN 180 struct otExtAddress 181 { 182 uint8_t m8[OT_EXT_ADDRESS_SIZE]; ///< IEEE 802.15.4 Extended Address bytes 183 } OT_TOOL_PACKED_END; 184 185 /** 186 * Represents the IEEE 802.15.4 Extended Address. 187 * 188 */ 189 typedef struct otExtAddress otExtAddress; 190 191 #define OT_MAC_KEY_SIZE 16 ///< Size of the MAC Key in bytes. 192 193 /** 194 * @struct otMacKey 195 * 196 * Represents a MAC Key. 197 * 198 */ 199 OT_TOOL_PACKED_BEGIN 200 struct otMacKey 201 { 202 uint8_t m8[OT_MAC_KEY_SIZE]; ///< MAC Key bytes. 203 } OT_TOOL_PACKED_END; 204 205 /** 206 * Represents a MAC Key. 207 * 208 */ 209 typedef struct otMacKey otMacKey; 210 211 /** 212 * Represents a MAC Key Ref used by PSA. 213 * 214 */ 215 typedef otCryptoKeyRef otMacKeyRef; 216 217 /** 218 * @struct otMacKeyMaterial 219 * 220 * Represents a MAC Key. 221 * 222 */ 223 typedef struct otMacKeyMaterial 224 { 225 union 226 { 227 otMacKeyRef mKeyRef; ///< Reference to the key stored. 228 otMacKey mKey; ///< Key stored as literal. 229 } mKeyMaterial; 230 } otMacKeyMaterial; 231 232 /** 233 * Defines constants about key types. 234 * 235 */ 236 typedef enum 237 { 238 OT_KEY_TYPE_LITERAL_KEY = 0, ///< Use Literal Keys. 239 OT_KEY_TYPE_KEY_REF = 1, ///< Use Reference to Key. 240 } otRadioKeyType; 241 242 /** 243 * Represents the IEEE 802.15.4 Header IE (Information Element) related information of a radio frame. 244 */ 245 typedef struct otRadioIeInfo 246 { 247 int64_t mNetworkTimeOffset; ///< The time offset to the Thread network time. 248 uint8_t mTimeIeOffset; ///< The Time IE offset from the start of PSDU. 249 uint8_t mTimeSyncSeq; ///< The Time sync sequence. 250 } otRadioIeInfo; 251 252 /** 253 * Represents an IEEE 802.15.4 radio frame. 254 */ 255 typedef struct otRadioFrame 256 { 257 uint8_t *mPsdu; ///< The PSDU. 258 259 uint16_t mLength; ///< Length of the PSDU. 260 uint8_t mChannel; ///< Channel used to transmit/receive the frame. 261 262 uint8_t mRadioType; ///< Radio link type - should be ignored by radio driver. 263 264 /** 265 * The union of transmit and receive information for a radio frame. 266 */ 267 union 268 { 269 /** 270 * Structure representing radio frame transmit information. 271 */ 272 struct 273 { 274 const otMacKeyMaterial *mAesKey; ///< The key material used for AES-CCM frame security. 275 otRadioIeInfo *mIeInfo; ///< The pointer to the Header IE(s) related information. 276 277 /** 278 * The base time in microseconds for scheduled transmissions 279 * relative to the local radio clock, see `otPlatRadioGetNow` and 280 * `mTxDelay`. 281 */ 282 uint32_t mTxDelayBaseTime; 283 284 /** 285 * The delay time in microseconds for this transmission referenced 286 * to `mTxDelayBaseTime`. 287 * 288 * Note: `mTxDelayBaseTime` + `mTxDelay` SHALL point to the point in 289 * time when the end of the SFD will be present at the local 290 * antenna, relative to the local radio clock. 291 */ 292 uint32_t mTxDelay; 293 294 uint8_t mMaxCsmaBackoffs; ///< Maximum number of backoffs attempts before declaring CCA failure. 295 uint8_t mMaxFrameRetries; ///< Maximum number of retries allowed after a transmission failure. 296 297 /** 298 * The RX channel after frame TX is done (after all frame retries - ack received, or timeout, or abort). 299 * 300 * Radio platforms can choose to fully ignore this. OT stack will make sure to call `otPlatRadioReceive()` 301 * with the desired RX channel after a frame TX is done and signaled in `otPlatRadioTxDone()` callback. 302 * Radio platforms that don't provide `OT_RADIO_CAPS_TRANSMIT_RETRIES` must always ignore this. 303 * 304 * This is intended for situations where there may be delay in interactions between OT stack and radio, as 305 * an example this is used in RCP/host architecture to make sure RCP switches to PAN channel more quickly. 306 * In particular, this can help with CSL tx to a sleepy child, where the child may use a different channel 307 * for CSL than the PAN channel. After frame tx, we want the radio/RCP to go back to the PAN channel 308 * quickly to ensure that parent does not miss tx from child afterwards, e.g., child responding to the 309 * earlier CSL transmitted frame from parent using PAN channel while radio still staying on CSL channel. 310 * 311 * The switch to the RX channel MUST happen after the frame TX is fully done, i.e., after all retries and 312 * when ack is received (when "Ack Request" flag is set on the TX frame) or ack timeout. Note that ack is 313 * expected on the same channel that frame is sent on. 314 * 315 */ 316 uint8_t mRxChannelAfterTxDone; 317 318 /** 319 * Indicates whether frame counter and CSL IEs are properly updated in the header. 320 * 321 * If the platform layer does not provide `OT_RADIO_CAPS_TRANSMIT_SEC` capability, it can ignore this flag. 322 * 323 * If the platform provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability, then platform is expected to handle tx 324 * security processing and assignment of frame counter. In this case the following behavior is expected: 325 * 326 * When `mIsHeaderUpdated` is set, it indicates that OpenThread core has already set the frame counter and 327 * CSL IEs (if security is enabled) in the prepared frame. The counter is ensured to match the counter value 328 * from the previous attempts of the same frame. The platform should not assign or change the frame counter 329 * (but may still need to perform security processing depending on `mIsSecurityProcessed` flag). 330 * 331 * If `mIsHeaderUpdated` is not set, then the frame counter and key CSL IE not set in the frame by 332 * OpenThread core and it is the responsibility of the radio platform to assign them. The platform 333 * must update the frame header (assign counter and CSL IE values) before sending the frame over the air, 334 * however if the the transmission gets aborted and the frame is never sent over the air (e.g., channel 335 * access error) the platform may choose to not update the header. If the platform updates the header, 336 * it must also set this flag before passing the frame back from the `otPlatRadioTxDone()` callback. 337 * 338 */ 339 bool mIsHeaderUpdated : 1; 340 bool mIsARetx : 1; ///< Indicates whether the frame is a retransmission or not. 341 bool mCsmaCaEnabled : 1; ///< Set to true to enable CSMA-CA for this packet, false otherwise. 342 bool mCslPresent : 1; ///< Set to true if CSL header IE is present. 343 bool mIsSecurityProcessed : 1; ///< True if SubMac should skip the AES processing of this frame. 344 } mTxInfo; 345 346 /** 347 * Structure representing radio frame receive information. 348 */ 349 struct 350 { 351 /** 352 * The time of the local radio clock in microseconds when the end of 353 * the SFD was present at the local antenna. 354 */ 355 uint64_t mTimestamp; 356 357 uint32_t mAckFrameCounter; ///< ACK security frame counter (applicable when `mAckedWithSecEnhAck` is set). 358 uint8_t mAckKeyId; ///< ACK security key index (applicable when `mAckedWithSecEnhAck` is set). 359 int8_t mRssi; ///< Received signal strength indicator in dBm for received frames. 360 uint8_t mLqi; ///< Link Quality Indicator for received frames. 361 362 // Flags 363 bool mAckedWithFramePending : 1; ///< This indicates if this frame was acknowledged with frame pending set. 364 bool mAckedWithSecEnhAck : 1; ///< This indicates if this frame was acknowledged with secured enhance ACK. 365 } mRxInfo; 366 } mInfo; 367 } otRadioFrame; 368 369 /** 370 * Represents the state of a radio. 371 * Initially, a radio is in the Disabled state. 372 */ 373 typedef enum otRadioState 374 { 375 OT_RADIO_STATE_DISABLED = 0, 376 OT_RADIO_STATE_SLEEP = 1, 377 OT_RADIO_STATE_RECEIVE = 2, 378 OT_RADIO_STATE_TRANSMIT = 3, 379 OT_RADIO_STATE_INVALID = 255, 380 } otRadioState; 381 382 /** 383 * The following are valid radio state transitions: 384 * 385 * (Radio ON) 386 * +----------+ Enable() +-------+ Receive() +---------+ Transmit() +----------+ 387 * | |----------->| |----------->| |-------------->| | 388 * | Disabled | | Sleep | | Receive | | Transmit | 389 * | |<-----------| |<-----------| |<--------------| | 390 * +----------+ Disable() +-------+ Sleep() +---------+ Receive() +----------+ 391 * (Radio OFF) or 392 * signal TransmitDone 393 * 394 * During the IEEE 802.15.4 data request command the transition Sleep->Receive->Transmit 395 * can be shortened to direct transition from Sleep to Transmit if the platform supports 396 * the OT_RADIO_CAPS_SLEEP_TO_TX capability. 397 */ 398 399 /** 400 * Represents radio coexistence metrics. 401 */ 402 typedef struct otRadioCoexMetrics 403 { 404 uint32_t mNumGrantGlitch; ///< Number of grant glitches. 405 uint32_t mNumTxRequest; ///< Number of tx requests. 406 uint32_t mNumTxGrantImmediate; ///< Number of tx requests while grant was active. 407 uint32_t mNumTxGrantWait; ///< Number of tx requests while grant was inactive. 408 uint32_t mNumTxGrantWaitActivated; ///< Number of tx requests while grant was inactive that were ultimately granted. 409 uint32_t mNumTxGrantWaitTimeout; ///< Number of tx requests while grant was inactive that timed out. 410 uint32_t mNumTxGrantDeactivatedDuringRequest; ///< Number of tx that were in progress when grant was deactivated. 411 uint32_t mNumTxDelayedGrant; ///< Number of tx requests that were not granted within 50us. 412 uint32_t mAvgTxRequestToGrantTime; ///< Average time in usec from tx request to grant. 413 uint32_t mNumRxRequest; ///< Number of rx requests. 414 uint32_t mNumRxGrantImmediate; ///< Number of rx requests while grant was active. 415 uint32_t mNumRxGrantWait; ///< Number of rx requests while grant was inactive. 416 uint32_t mNumRxGrantWaitActivated; ///< Number of rx requests while grant was inactive that were ultimately granted. 417 uint32_t mNumRxGrantWaitTimeout; ///< Number of rx requests while grant was inactive that timed out. 418 uint32_t mNumRxGrantDeactivatedDuringRequest; ///< Number of rx that were in progress when grant was deactivated. 419 uint32_t mNumRxDelayedGrant; ///< Number of rx requests that were not granted within 50us. 420 uint32_t mAvgRxRequestToGrantTime; ///< Average time in usec from rx request to grant. 421 uint32_t mNumRxGrantNone; ///< Number of rx requests that completed without receiving grant. 422 bool mStopped; ///< Stats collection stopped due to saturation. 423 } otRadioCoexMetrics; 424 425 /** 426 * Represents what metrics are specified to query. 427 * 428 */ 429 typedef struct otLinkMetrics 430 { 431 bool mPduCount : 1; ///< Pdu count. 432 bool mLqi : 1; ///< Link Quality Indicator. 433 bool mLinkMargin : 1; ///< Link Margin. 434 bool mRssi : 1; ///< Received Signal Strength Indicator. 435 bool mReserved : 1; ///< Reserved, this is for reference device. 436 } otLinkMetrics; 437 438 /** 439 * @} 440 * 441 */ 442 443 /** 444 * @defgroup radio-config Radio Configuration 445 * 446 * @brief 447 * This module includes the platform abstraction for radio configuration. 448 * 449 * @{ 450 * 451 */ 452 453 /** 454 * Get the radio capabilities. 455 * 456 * @param[in] aInstance The OpenThread instance structure. 457 * 458 * @returns The radio capability bit vector (see `OT_RADIO_CAP_*` definitions). 459 * 460 */ 461 otRadioCaps otPlatRadioGetCaps(otInstance *aInstance); 462 463 /** 464 * Get the radio version string. 465 * 466 * This is an optional radio driver platform function. If not provided by platform radio driver, OpenThread uses 467 * the OpenThread version instead (@sa otGetVersionString()). 468 * 469 * @param[in] aInstance The OpenThread instance structure. 470 * 471 * @returns A pointer to the OpenThread radio version. 472 * 473 */ 474 const char *otPlatRadioGetVersionString(otInstance *aInstance); 475 476 /** 477 * Get the radio receive sensitivity value. 478 * 479 * @param[in] aInstance The OpenThread instance structure. 480 * 481 * @returns The radio receive sensitivity value in dBm. 482 * 483 */ 484 int8_t otPlatRadioGetReceiveSensitivity(otInstance *aInstance); 485 486 /** 487 * Gets the factory-assigned IEEE EUI-64 for this interface. 488 * 489 * @param[in] aInstance The OpenThread instance structure. 490 * @param[out] aIeeeEui64 A pointer to the factory-assigned IEEE EUI-64. 491 * 492 */ 493 void otPlatRadioGetIeeeEui64(otInstance *aInstance, uint8_t *aIeeeEui64); 494 495 /** 496 * Set the PAN ID for address filtering. 497 * 498 * @param[in] aInstance The OpenThread instance structure. 499 * @param[in] aPanId The IEEE 802.15.4 PAN ID. 500 * 501 */ 502 void otPlatRadioSetPanId(otInstance *aInstance, otPanId aPanId); 503 504 /** 505 * Set the Extended Address for address filtering. 506 * 507 * @param[in] aInstance The OpenThread instance structure. 508 * @param[in] aExtAddress A pointer to the IEEE 802.15.4 Extended Address stored in little-endian byte order. 509 * 510 * 511 */ 512 void otPlatRadioSetExtendedAddress(otInstance *aInstance, const otExtAddress *aExtAddress); 513 514 /** 515 * Set the Short Address for address filtering. 516 * 517 * @param[in] aInstance The OpenThread instance structure. 518 * @param[in] aShortAddress The IEEE 802.15.4 Short Address. 519 * 520 */ 521 void otPlatRadioSetShortAddress(otInstance *aInstance, otShortAddress aShortAddress); 522 523 /** 524 * Get the radio's transmit power in dBm. 525 * 526 * @note The transmit power returned will be no larger than the power specified in the max power table for 527 * the current channel. 528 * 529 * @param[in] aInstance The OpenThread instance structure. 530 * @param[out] aPower The transmit power in dBm. 531 * 532 * @retval OT_ERROR_NONE Successfully retrieved the transmit power. 533 * @retval OT_ERROR_INVALID_ARGS @p aPower was NULL. 534 * @retval OT_ERROR_NOT_IMPLEMENTED Transmit power configuration via dBm is not implemented. 535 * 536 */ 537 otError otPlatRadioGetTransmitPower(otInstance *aInstance, int8_t *aPower); 538 539 /** 540 * Set the radio's transmit power in dBm. 541 * 542 * @note The real transmit power will be no larger than the power specified in the max power table for 543 * the current channel. 544 * 545 * @param[in] aInstance The OpenThread instance structure. 546 * @param[in] aPower The transmit power in dBm. 547 * 548 * @retval OT_ERROR_NONE Successfully set the transmit power. 549 * @retval OT_ERROR_NOT_IMPLEMENTED Transmit power configuration via dBm is not implemented. 550 * 551 */ 552 otError otPlatRadioSetTransmitPower(otInstance *aInstance, int8_t aPower); 553 554 /** 555 * Get the radio's CCA ED threshold in dBm measured at antenna connector per IEEE 802.15.4 - 2015 section 10.1.4. 556 * 557 * @param[in] aInstance The OpenThread instance structure. 558 * @param[out] aThreshold The CCA ED threshold in dBm. 559 * 560 * @retval OT_ERROR_NONE Successfully retrieved the CCA ED threshold. 561 * @retval OT_ERROR_INVALID_ARGS @p aThreshold was NULL. 562 * @retval OT_ERROR_NOT_IMPLEMENTED CCA ED threshold configuration via dBm is not implemented. 563 * 564 */ 565 otError otPlatRadioGetCcaEnergyDetectThreshold(otInstance *aInstance, int8_t *aThreshold); 566 567 /** 568 * Set the radio's CCA ED threshold in dBm measured at antenna connector per IEEE 802.15.4 - 2015 section 10.1.4. 569 * 570 * @param[in] aInstance The OpenThread instance structure. 571 * @param[in] aThreshold The CCA ED threshold in dBm. 572 * 573 * @retval OT_ERROR_NONE Successfully set the transmit power. 574 * @retval OT_ERROR_INVALID_ARGS Given threshold is out of range. 575 * @retval OT_ERROR_NOT_IMPLEMENTED CCA ED threshold configuration via dBm is not implemented. 576 * 577 */ 578 otError otPlatRadioSetCcaEnergyDetectThreshold(otInstance *aInstance, int8_t aThreshold); 579 580 /** 581 * Gets the external FEM's Rx LNA gain in dBm. 582 * 583 * @param[in] aInstance The OpenThread instance structure. 584 * @param[out] aGain The external FEM's Rx LNA gain in dBm. 585 * 586 * @retval OT_ERROR_NONE Successfully retrieved the external FEM's LNA gain. 587 * @retval OT_ERROR_INVALID_ARGS @p aGain was NULL. 588 * @retval OT_ERROR_NOT_IMPLEMENTED External FEM's LNA setting is not implemented. 589 * 590 */ 591 otError otPlatRadioGetFemLnaGain(otInstance *aInstance, int8_t *aGain); 592 593 /** 594 * Sets the external FEM's Rx LNA gain in dBm. 595 * 596 * @param[in] aInstance The OpenThread instance structure. 597 * @param[in] aGain The external FEM's Rx LNA gain in dBm. 598 * 599 * @retval OT_ERROR_NONE Successfully set the external FEM's LNA gain. 600 * @retval OT_ERROR_NOT_IMPLEMENTED External FEM's LNA gain setting is not implemented. 601 * 602 */ 603 otError otPlatRadioSetFemLnaGain(otInstance *aInstance, int8_t aGain); 604 605 /** 606 * Get the status of promiscuous mode. 607 * 608 * @param[in] aInstance The OpenThread instance structure. 609 * 610 * @retval TRUE Promiscuous mode is enabled. 611 * @retval FALSE Promiscuous mode is disabled. 612 * 613 */ 614 bool otPlatRadioGetPromiscuous(otInstance *aInstance); 615 616 /** 617 * Enable or disable promiscuous mode. 618 * 619 * @param[in] aInstance The OpenThread instance structure. 620 * @param[in] aEnable TRUE to enable or FALSE to disable promiscuous mode. 621 * 622 */ 623 void otPlatRadioSetPromiscuous(otInstance *aInstance, bool aEnable); 624 625 /** 626 * Sets the rx-on-when-idle state to the radio platform. 627 * 628 * There are a few situations that the radio can enter sleep state if the device is in rx-off-when-idle state but 629 * it's hard and costly for the SubMac to identify these situations and instruct the radio to enter sleep: 630 * 631 * - Finalization of a regular frame reception task, provided that: 632 * - The frame is received without errors and passes the filtering and it's not an spurious ACK. 633 * - ACK is not requested or transmission of ACK is not possible due to internal conditions. 634 * - Finalization of a frame transmission or transmission of an ACK frame, when ACK is not requested in the transmitted 635 * frame. 636 * - Finalization of the reception operation of a requested ACK due to: 637 * - ACK timeout expiration. 638 * - Reception of an invalid ACK or not an ACK frame. 639 * - Reception of the proper ACK, unless the transmitted frame was a Data Request Command and the frame pending bit 640 * on the received ACK is set to true. In this case the radio platform implementation SHOULD keep the receiver on 641 * until a determined timeout which triggers an idle period start.`OPENTHREAD_CONFIG_MAC_DATA_POLL_TIMEOUT` can be 642 * taken as a reference for this. 643 * - Finalization of a stand alone CCA task. 644 * - Finalization of a CCA operation with busy result during CSMA/CA procedure. 645 * - Finalization of an Energy Detection task. 646 * - Finalization of a radio reception window scheduled with `otPlatRadioReceiveAt`. 647 * 648 * If a platform supports `OT_RADIO_CAPS_RX_ON_WHEN_IDLE` it must also support `OT_RADIO_CAPS_CSMA_BACKOFF` and handle 649 * idle periods after CCA as described above. 650 * 651 * Upon the transition of the "RxOnWhenIdle" flag from TRUE to FALSE, the radio platform should enter sleep mode. 652 * If the radio is currently in receive mode, it should enter sleep mode immediately. Otherwise, it should enter sleep 653 * mode after the current operation is completed. 654 * 655 * @param[in] aInstance The OpenThread instance structure. 656 * @param[in] aEnable TRUE to keep radio in Receive state, FALSE to put to Sleep state during idle periods. 657 * 658 */ 659 void otPlatRadioSetRxOnWhenIdle(otInstance *aInstance, bool aEnable); 660 661 /** 662 * Update MAC keys and key index 663 * 664 * Is used when radio provides OT_RADIO_CAPS_TRANSMIT_SEC capability. 665 * 666 * @param[in] aInstance A pointer to an OpenThread instance. 667 * @param[in] aKeyIdMode The key ID mode. 668 * @param[in] aKeyId Current MAC key index. 669 * @param[in] aPrevKey A pointer to the previous MAC key. 670 * @param[in] aCurrKey A pointer to the current MAC key. 671 * @param[in] aNextKey A pointer to the next MAC key. 672 * @param[in] aKeyType Key Type used. 673 * 674 */ 675 void otPlatRadioSetMacKey(otInstance *aInstance, 676 uint8_t aKeyIdMode, 677 uint8_t aKeyId, 678 const otMacKeyMaterial *aPrevKey, 679 const otMacKeyMaterial *aCurrKey, 680 const otMacKeyMaterial *aNextKey, 681 otRadioKeyType aKeyType); 682 683 /** 684 * Sets the current MAC frame counter value. 685 * 686 * Is used when radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability. 687 * 688 * @param[in] aInstance A pointer to an OpenThread instance. 689 * @param[in] aMacFrameCounter The MAC frame counter value. 690 * 691 */ 692 void otPlatRadioSetMacFrameCounter(otInstance *aInstance, uint32_t aMacFrameCounter); 693 694 /** 695 * Sets the current MAC frame counter value only if the new given value is larger than the current value. 696 * 697 * Is used when radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability. 698 * 699 * @param[in] aInstance A pointer to an OpenThread instance. 700 * @param[in] aMacFrameCounter The MAC frame counter value. 701 * 702 */ 703 void otPlatRadioSetMacFrameCounterIfLarger(otInstance *aInstance, uint32_t aMacFrameCounter); 704 705 /** 706 * Get the current time in microseconds referenced to a continuous monotonic 707 * local radio clock (64 bits width). 708 * 709 * The radio clock SHALL NOT wrap during the device's uptime. Implementations 710 * SHALL therefore identify and compensate for internal counter overflows. The 711 * clock does not have a defined epoch and it SHALL NOT introduce any continuous 712 * or discontinuous adjustments (e.g. leap seconds). Implementations SHALL 713 * compensate for any sleep times of the device. 714 * 715 * Implementations MAY choose to discipline the radio clock and compensate for 716 * sleep times by any means (e.g. by combining a high precision/low power RTC 717 * with a high resolution counter) as long as the exposed combined clock 718 * provides continuous monotonic microsecond resolution ticks within the 719 * accuracy limits announced by @ref otPlatRadioGetCslAccuracy. 720 * 721 * @param[in] aInstance A pointer to an OpenThread instance. 722 * 723 * @returns The current time in microseconds. UINT64_MAX when platform does not 724 * support or radio time is not ready. 725 * 726 */ 727 uint64_t otPlatRadioGetNow(otInstance *aInstance); 728 729 /** 730 * Get the bus speed in bits/second between the host and the radio chip. 731 * 732 * @param[in] aInstance A pointer to an OpenThread instance. 733 * 734 * @returns The bus speed in bits/second between the host and the radio chip. 735 * Return 0 when the MAC and above layer and Radio layer resides on the same chip. 736 * 737 */ 738 uint32_t otPlatRadioGetBusSpeed(otInstance *aInstance); 739 740 /** 741 * @} 742 * 743 */ 744 745 /** 746 * @defgroup radio-operation Radio Operation 747 * 748 * @brief 749 * This module includes the platform abstraction for radio operations. 750 * 751 * @{ 752 * 753 */ 754 755 /** 756 * Get current state of the radio. 757 * 758 * Is not required by OpenThread. It may be used for debugging and/or application-specific purposes. 759 * 760 * @note This function may be not implemented. It does not affect OpenThread. 761 * 762 * @param[in] aInstance The OpenThread instance structure. 763 * 764 * @return Current state of the radio. 765 * 766 */ 767 otRadioState otPlatRadioGetState(otInstance *aInstance); 768 769 /** 770 * Enable the radio. 771 * 772 * @param[in] aInstance The OpenThread instance structure. 773 * 774 * @retval OT_ERROR_NONE Successfully enabled. 775 * @retval OT_ERROR_FAILED The radio could not be enabled. 776 * 777 */ 778 otError otPlatRadioEnable(otInstance *aInstance); 779 780 /** 781 * Disable the radio. 782 * 783 * @param[in] aInstance The OpenThread instance structure. 784 * 785 * @retval OT_ERROR_NONE Successfully transitioned to Disabled. 786 * @retval OT_ERROR_INVALID_STATE The radio was not in sleep state. 787 * 788 */ 789 otError otPlatRadioDisable(otInstance *aInstance); 790 791 /** 792 * Check whether radio is enabled or not. 793 * 794 * @param[in] aInstance The OpenThread instance structure. 795 * 796 * @returns TRUE if the radio is enabled, FALSE otherwise. 797 * 798 */ 799 bool otPlatRadioIsEnabled(otInstance *aInstance); 800 801 /** 802 * Transition the radio from Receive to Sleep (turn off the radio). 803 * 804 * @param[in] aInstance The OpenThread instance structure. 805 * 806 * @retval OT_ERROR_NONE Successfully transitioned to Sleep. 807 * @retval OT_ERROR_BUSY The radio was transmitting. 808 * @retval OT_ERROR_INVALID_STATE The radio was disabled. 809 * 810 */ 811 otError otPlatRadioSleep(otInstance *aInstance); 812 813 /** 814 * Transition the radio from Sleep to Receive (turn on the radio). 815 * 816 * @param[in] aInstance The OpenThread instance structure. 817 * @param[in] aChannel The channel to use for receiving. 818 * 819 * @retval OT_ERROR_NONE Successfully transitioned to Receive. 820 * @retval OT_ERROR_INVALID_STATE The radio was disabled or transmitting. 821 * 822 */ 823 otError otPlatRadioReceive(otInstance *aInstance, uint8_t aChannel); 824 825 /** 826 * Schedule a radio reception window at a specific time and duration. 827 * 828 * @param[in] aChannel The radio channel on which to receive. 829 * @param[in] aStart The receive window start time relative to the local 830 * radio clock, see `otPlatRadioGetNow`. The radio 831 * receiver SHALL be on and ready to receive the first 832 * symbol of a frame's SHR at the window start time. 833 * @param[in] aDuration The receive window duration, in microseconds, as 834 * measured by the local radio clock. The radio SHOULD be 835 * turned off (or switched to TX mode if an ACK frame 836 * needs to be sent) after that duration unless it is 837 * still actively receiving a frame. In the latter case 838 * the radio SHALL be kept in reception mode until frame 839 * reception has either succeeded or failed. 840 * 841 * @retval OT_ERROR_NONE Successfully scheduled receive window. 842 * @retval OT_ERROR_FAILED The receive window could not be scheduled. 843 */ 844 otError otPlatRadioReceiveAt(otInstance *aInstance, uint8_t aChannel, uint32_t aStart, uint32_t aDuration); 845 846 /** 847 * The radio driver calls this method to notify OpenThread of a received frame. 848 * 849 * @param[in] aInstance The OpenThread instance structure. 850 * @param[in] aFrame A pointer to the received frame or NULL if the receive operation failed. 851 * @param[in] aError OT_ERROR_NONE when successfully received a frame, 852 * OT_ERROR_ABORT when reception was aborted and a frame was not received, 853 * OT_ERROR_NO_BUFS when a frame could not be received due to lack of rx buffer space. 854 * 855 */ 856 extern void otPlatRadioReceiveDone(otInstance *aInstance, otRadioFrame *aFrame, otError aError); 857 858 /** 859 * The radio driver calls this method to notify OpenThread diagnostics module of a received frame. 860 * 861 * Is used when diagnostics is enabled. 862 * 863 * @param[in] aInstance The OpenThread instance structure. 864 * @param[in] aFrame A pointer to the received frame or NULL if the receive operation failed. 865 * @param[in] aError OT_ERROR_NONE when successfully received a frame, 866 * OT_ERROR_ABORT when reception was aborted and a frame was not received, 867 * OT_ERROR_NO_BUFS when a frame could not be received due to lack of rx buffer space. 868 * 869 */ 870 extern void otPlatDiagRadioReceiveDone(otInstance *aInstance, otRadioFrame *aFrame, otError aError); 871 872 /** 873 * Get the radio transmit frame buffer. 874 * 875 * OpenThread forms the IEEE 802.15.4 frame in this buffer then calls `otPlatRadioTransmit()` to request transmission. 876 * 877 * @param[in] aInstance The OpenThread instance structure. 878 * 879 * @returns A pointer to the transmit frame buffer. 880 * 881 */ 882 otRadioFrame *otPlatRadioGetTransmitBuffer(otInstance *aInstance); 883 884 /** 885 * Begin the transmit sequence on the radio. 886 * 887 * The caller must form the IEEE 802.15.4 frame in the buffer provided by `otPlatRadioGetTransmitBuffer()` before 888 * requesting transmission. The channel and transmit power are also included in the otRadioFrame structure. 889 * 890 * The transmit sequence consists of: 891 * 1. Transitioning the radio to Transmit from one of the following states: 892 * - Receive if RX is on when the device is idle or OT_RADIO_CAPS_SLEEP_TO_TX is not supported 893 * - Sleep if RX is off when the device is idle and OT_RADIO_CAPS_SLEEP_TO_TX is supported. 894 * 2. Transmits the psdu on the given channel and at the given transmit power. 895 * 896 * @param[in] aInstance The OpenThread instance structure. 897 * @param[in] aFrame A pointer to the frame to be transmitted. 898 * 899 * @retval OT_ERROR_NONE Successfully transitioned to Transmit. 900 * @retval OT_ERROR_INVALID_STATE The radio was not in the Receive state. 901 * 902 */ 903 otError otPlatRadioTransmit(otInstance *aInstance, otRadioFrame *aFrame); 904 905 /** 906 * The radio driver calls this method to notify OpenThread that the transmission has started. 907 * 908 * @note This function should be called by the same thread that executes all of the other OpenThread code. It should 909 * not be called by ISR or any other task. 910 * 911 * @param[in] aInstance A pointer to the OpenThread instance structure. 912 * @param[in] aFrame A pointer to the frame that is being transmitted. 913 * 914 */ 915 extern void otPlatRadioTxStarted(otInstance *aInstance, otRadioFrame *aFrame); 916 917 /** 918 * The radio driver calls this function to notify OpenThread that the transmit operation has completed, 919 * providing both the transmitted frame and, if applicable, the received ack frame. 920 * 921 * When radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability, radio platform layer updates @p aFrame 922 * with the security frame counter and key index values maintained by the radio. 923 * 924 * @param[in] aInstance The OpenThread instance structure. 925 * @param[in] aFrame A pointer to the frame that was transmitted. 926 * @param[in] aAckFrame A pointer to the ACK frame, NULL if no ACK was received. 927 * @param[in] aError OT_ERROR_NONE when the frame was transmitted, 928 * OT_ERROR_NO_ACK when the frame was transmitted but no ACK was received, 929 * OT_ERROR_CHANNEL_ACCESS_FAILURE tx could not take place due to activity on the channel, 930 * OT_ERROR_ABORT when transmission was aborted for other reasons. 931 * 932 */ 933 extern void otPlatRadioTxDone(otInstance *aInstance, otRadioFrame *aFrame, otRadioFrame *aAckFrame, otError aError); 934 935 /** 936 * The radio driver calls this method to notify OpenThread diagnostics module that the transmission has completed. 937 * 938 * Is used when diagnostics is enabled. 939 * 940 * @param[in] aInstance The OpenThread instance structure. 941 * @param[in] aFrame A pointer to the frame that was transmitted. 942 * @param[in] aError OT_ERROR_NONE when the frame was transmitted, 943 * OT_ERROR_CHANNEL_ACCESS_FAILURE tx could not take place due to activity on the channel, 944 * OT_ERROR_ABORT when transmission was aborted for other reasons. 945 * 946 */ 947 extern void otPlatDiagRadioTransmitDone(otInstance *aInstance, otRadioFrame *aFrame, otError aError); 948 949 /** 950 * Get the most recent RSSI measurement. 951 * 952 * @param[in] aInstance The OpenThread instance structure. 953 * 954 * @returns The RSSI in dBm when it is valid. 127 when RSSI is invalid. 955 * 956 */ 957 int8_t otPlatRadioGetRssi(otInstance *aInstance); 958 959 /** 960 * Begin the energy scan sequence on the radio. 961 * 962 * Is used when radio provides OT_RADIO_CAPS_ENERGY_SCAN capability. 963 * 964 * @param[in] aInstance The OpenThread instance structure. 965 * @param[in] aScanChannel The channel to perform the energy scan on. 966 * @param[in] aScanDuration The duration, in milliseconds, for the channel to be scanned. 967 * 968 * @retval OT_ERROR_NONE Successfully started scanning the channel. 969 * @retval OT_ERROR_BUSY The radio is performing energy scanning. 970 * @retval OT_ERROR_NOT_IMPLEMENTED The radio doesn't support energy scanning. 971 * 972 */ 973 otError otPlatRadioEnergyScan(otInstance *aInstance, uint8_t aScanChannel, uint16_t aScanDuration); 974 975 /** 976 * The radio driver calls this method to notify OpenThread that the energy scan is complete. 977 * 978 * Is used when radio provides OT_RADIO_CAPS_ENERGY_SCAN capability. 979 * 980 * @param[in] aInstance The OpenThread instance structure. 981 * @param[in] aEnergyScanMaxRssi The maximum RSSI encountered on the scanned channel. 982 * 983 */ 984 extern void otPlatRadioEnergyScanDone(otInstance *aInstance, int8_t aEnergyScanMaxRssi); 985 986 /** 987 * Enable/Disable source address match feature. 988 * 989 * The source address match feature controls how the radio layer decides the "frame pending" bit for acks sent in 990 * response to data request commands from children. 991 * 992 * If disabled, the radio layer must set the "frame pending" on all acks to data request commands. 993 * 994 * If enabled, the radio layer uses the source address match table to determine whether to set or clear the "frame 995 * pending" bit in an ack to a data request command. 996 * 997 * The source address match table provides the list of children for which there is a pending frame. Either a short 998 * address or an extended/long address can be added to the source address match table. 999 * 1000 * @param[in] aInstance The OpenThread instance structure. 1001 * @param[in] aEnable Enable/disable source address match feature. 1002 * 1003 */ 1004 void otPlatRadioEnableSrcMatch(otInstance *aInstance, bool aEnable); 1005 1006 /** 1007 * Add a short address to the source address match table. 1008 * 1009 * @param[in] aInstance The OpenThread instance structure. 1010 * @param[in] aShortAddress The short address to be added. 1011 * 1012 * @retval OT_ERROR_NONE Successfully added short address to the source match table. 1013 * @retval OT_ERROR_NO_BUFS No available entry in the source match table. 1014 * 1015 */ 1016 otError otPlatRadioAddSrcMatchShortEntry(otInstance *aInstance, otShortAddress aShortAddress); 1017 1018 /** 1019 * Add an extended address to the source address match table. 1020 * 1021 * @param[in] aInstance The OpenThread instance structure. 1022 * @param[in] aExtAddress The extended address to be added stored in little-endian byte order. 1023 * 1024 * @retval OT_ERROR_NONE Successfully added extended address to the source match table. 1025 * @retval OT_ERROR_NO_BUFS No available entry in the source match table. 1026 * 1027 */ 1028 otError otPlatRadioAddSrcMatchExtEntry(otInstance *aInstance, const otExtAddress *aExtAddress); 1029 1030 /** 1031 * Remove a short address from the source address match table. 1032 * 1033 * @param[in] aInstance The OpenThread instance structure. 1034 * @param[in] aShortAddress The short address to be removed. 1035 * 1036 * @retval OT_ERROR_NONE Successfully removed short address from the source match table. 1037 * @retval OT_ERROR_NO_ADDRESS The short address is not in source address match table. 1038 * 1039 */ 1040 otError otPlatRadioClearSrcMatchShortEntry(otInstance *aInstance, otShortAddress aShortAddress); 1041 1042 /** 1043 * Remove an extended address from the source address match table. 1044 * 1045 * @param[in] aInstance The OpenThread instance structure. 1046 * @param[in] aExtAddress The extended address to be removed stored in little-endian byte order. 1047 * 1048 * @retval OT_ERROR_NONE Successfully removed the extended address from the source match table. 1049 * @retval OT_ERROR_NO_ADDRESS The extended address is not in source address match table. 1050 * 1051 */ 1052 otError otPlatRadioClearSrcMatchExtEntry(otInstance *aInstance, const otExtAddress *aExtAddress); 1053 1054 /** 1055 * Clear all short addresses from the source address match table. 1056 * 1057 * @param[in] aInstance The OpenThread instance structure. 1058 * 1059 */ 1060 void otPlatRadioClearSrcMatchShortEntries(otInstance *aInstance); 1061 1062 /** 1063 * Clear all the extended/long addresses from source address match table. 1064 * 1065 * @param[in] aInstance The OpenThread instance structure. 1066 * 1067 */ 1068 void otPlatRadioClearSrcMatchExtEntries(otInstance *aInstance); 1069 1070 /** 1071 * Get the radio supported channel mask that the device is allowed to be on. 1072 * 1073 * @param[in] aInstance The OpenThread instance structure. 1074 * 1075 * @returns The radio supported channel mask. 1076 * 1077 */ 1078 uint32_t otPlatRadioGetSupportedChannelMask(otInstance *aInstance); 1079 1080 /** 1081 * Gets the radio preferred channel mask that the device prefers to form on. 1082 * 1083 * @param[in] aInstance The OpenThread instance structure. 1084 * 1085 * @returns The radio preferred channel mask. 1086 * 1087 */ 1088 uint32_t otPlatRadioGetPreferredChannelMask(otInstance *aInstance); 1089 1090 /** 1091 * Enable the radio coex. 1092 * 1093 * Is used when feature OPENTHREAD_CONFIG_PLATFORM_RADIO_COEX_ENABLE is enabled. 1094 * 1095 * @param[in] aInstance The OpenThread instance structure. 1096 * @param[in] aEnabled TRUE to enable the radio coex, FALSE otherwise. 1097 * 1098 * @retval OT_ERROR_NONE Successfully enabled. 1099 * @retval OT_ERROR_FAILED The radio coex could not be enabled. 1100 * 1101 */ 1102 otError otPlatRadioSetCoexEnabled(otInstance *aInstance, bool aEnabled); 1103 1104 /** 1105 * Check whether radio coex is enabled or not. 1106 * 1107 * Is used when feature OPENTHREAD_CONFIG_PLATFORM_RADIO_COEX_ENABLE is enabled. 1108 * 1109 * @param[in] aInstance The OpenThread instance structure. 1110 * 1111 * @returns TRUE if the radio coex is enabled, FALSE otherwise. 1112 * 1113 */ 1114 bool otPlatRadioIsCoexEnabled(otInstance *aInstance); 1115 1116 /** 1117 * Get the radio coexistence metrics. 1118 * 1119 * Is used when feature OPENTHREAD_CONFIG_PLATFORM_RADIO_COEX_ENABLE is enabled. 1120 * 1121 * @param[in] aInstance The OpenThread instance structure. 1122 * @param[out] aCoexMetrics A pointer to the coexistence metrics structure. 1123 * 1124 * @retval OT_ERROR_NONE Successfully retrieved the coex metrics. 1125 * @retval OT_ERROR_INVALID_ARGS @p aCoexMetrics was NULL. 1126 */ 1127 otError otPlatRadioGetCoexMetrics(otInstance *aInstance, otRadioCoexMetrics *aCoexMetrics); 1128 1129 /** 1130 * Enable or disable CSL receiver. 1131 * 1132 * @param[in] aInstance The OpenThread instance structure. 1133 * @param[in] aCslPeriod CSL period, 0 for disabling CSL. CSL period is in unit of 10 symbols. 1134 * @param[in] aShortAddr The short source address of CSL receiver's peer. 1135 * @param[in] aExtAddr The extended source address of CSL receiver's peer. 1136 * 1137 * @note Platforms should use CSL peer addresses to include CSL IE when generating enhanced acks. 1138 * 1139 * @retval OT_ERROR_NOT_IMPLEMENTED Radio driver doesn't support CSL. 1140 * @retval OT_ERROR_FAILED Other platform specific errors. 1141 * @retval OT_ERROR_NONE Successfully enabled or disabled CSL. 1142 * 1143 */ 1144 otError otPlatRadioEnableCsl(otInstance *aInstance, 1145 uint32_t aCslPeriod, 1146 otShortAddress aShortAddr, 1147 const otExtAddress *aExtAddr); 1148 1149 /** 1150 * Reset CSL receiver in the platform. 1151 * 1152 * @note Defaults to `otPlatRadioEnableCsl(aInstance,0, Mac::kShortAddrInvalid, nullptr);` 1153 * 1154 * @param[in] aInstance The OpenThread instance structure. 1155 * 1156 * @retval OT_ERROR_NOT_IMPLEMENTED Radio driver doesn't support CSL. 1157 * @retval OT_ERROR_FAILED Other platform specific errors. 1158 * @retval OT_ERROR_NONE Successfully disabled CSL. 1159 * 1160 */ 1161 otError otPlatRadioResetCsl(otInstance *aInstance); 1162 1163 /** 1164 * Update CSL sample time in radio driver. 1165 * 1166 * Sample time is stored in radio driver as a copy to calculate phase when 1167 * sending ACK with CSL IE. The CSL sample (window) of the CSL receiver extends 1168 * before and after the sample time. The CSL sample time marks a timestamp in 1169 * the CSL sample window when a frame should be received in "ideal conditions" 1170 * if there would be no inaccuracy/clock-drift. 1171 * 1172 * @param[in] aInstance The OpenThread instance structure. 1173 * @param[in] aCslSampleTime The next sample time, in microseconds. It is 1174 * the time when the first symbol of the MHR of 1175 * the frame is expected. 1176 */ 1177 void otPlatRadioUpdateCslSampleTime(otInstance *aInstance, uint32_t aCslSampleTime); 1178 1179 /** 1180 * Get the current estimated worst case accuracy (maximum ± deviation from the 1181 * nominal frequency) of the local radio clock in units of PPM. This is the 1182 * clock used to schedule CSL operations. 1183 * 1184 * @note Implementations MAY estimate this value based on current operating 1185 * conditions (e.g. temperature). 1186 * 1187 * In case the implementation does not estimate the current value but returns a 1188 * fixed value, this value MUST be the worst-case accuracy over all possible 1189 * foreseen operating conditions (temperature, pressure, etc) of the 1190 * implementation. 1191 * 1192 * @param[in] aInstance A pointer to an OpenThread instance. 1193 * 1194 * @returns The current CSL rx/tx scheduling drift, in PPM. 1195 * 1196 */ 1197 uint8_t otPlatRadioGetCslAccuracy(otInstance *aInstance); 1198 1199 /** 1200 * The fixed uncertainty (i.e. random jitter) of the arrival time of CSL 1201 * transmissions received by this device in units of 10 microseconds. 1202 * 1203 * This designates the worst case constant positive or negative deviation of 1204 * the actual arrival time of a transmission from the transmission time 1205 * calculated relative to the local radio clock independent of elapsed time. In 1206 * addition to uncertainty accumulated over elapsed time, the CSL channel sample 1207 * ("RX window") must be extended by twice this deviation such that an actual 1208 * transmission is guaranteed to be detected by the local receiver in the 1209 * presence of random arrival time jitter. 1210 * 1211 * @param[in] aInstance A pointer to an OpenThread instance. 1212 * 1213 * @returns The CSL Uncertainty in units of 10 us. 1214 * 1215 */ 1216 uint8_t otPlatRadioGetCslUncertainty(otInstance *aInstance); 1217 1218 /** 1219 * Set the max transmit power for a specific channel. 1220 * 1221 * @param[in] aInstance The OpenThread instance structure. 1222 * @param[in] aChannel The radio channel. 1223 * @param[in] aMaxPower The max power in dBm, passing OT_RADIO_RSSI_INVALID will disable this channel. 1224 * 1225 * @retval OT_ERROR_NOT_IMPLEMENTED The feature is not implemented 1226 * @retval OT_ERROR_INVALID_ARGS The specified channel is not valid. 1227 * @retval OT_ERROR_FAILED Other platform specific errors. 1228 * @retval OT_ERROR_NONE Successfully set max transmit power. 1229 * 1230 */ 1231 otError otPlatRadioSetChannelMaxTransmitPower(otInstance *aInstance, uint8_t aChannel, int8_t aMaxPower); 1232 1233 /** 1234 * Set the region code. 1235 * 1236 * The radio region format is the 2-bytes ascii representation of the 1237 * ISO 3166 alpha-2 code. 1238 * 1239 * @param[in] aInstance The OpenThread instance structure. 1240 * @param[in] aRegionCode The radio region code. The `aRegionCode >> 8` is first ascii char 1241 * and the `aRegionCode & 0xff` is the second ascii char. 1242 * 1243 * @retval OT_ERROR_FAILED Other platform specific errors. 1244 * @retval OT_ERROR_NONE Successfully set region code. 1245 * @retval OT_ERROR_NOT_IMPLEMENTED The feature is not implemented. 1246 * 1247 */ 1248 otError otPlatRadioSetRegion(otInstance *aInstance, uint16_t aRegionCode); 1249 1250 /** 1251 * Get the region code. 1252 * 1253 * The radio region format is the 2-bytes ascii representation of the 1254 * ISO 3166 alpha-2 code. 1255 1256 * @param[in] aInstance The OpenThread instance structure. 1257 * @param[out] aRegionCode The radio region. 1258 * 1259 * @retval OT_ERROR_INVALID_ARGS @p aRegionCode is nullptr. 1260 * @retval OT_ERROR_FAILED Other platform specific errors. 1261 * @retval OT_ERROR_NONE Successfully got region code. 1262 * @retval OT_ERROR_NOT_IMPLEMENTED The feature is not implemented. 1263 * 1264 */ 1265 otError otPlatRadioGetRegion(otInstance *aInstance, uint16_t *aRegionCode); 1266 1267 /** 1268 * Enable/disable or update Enhanced-ACK Based Probing in radio for a specific Initiator. 1269 * 1270 * After Enhanced-ACK Based Probing is configured by a specific Probing Initiator, the Enhanced-ACK sent to that 1271 * node should include Vendor-Specific IE containing Link Metrics data. This method informs the radio to start/stop to 1272 * collect Link Metrics data and include Vendor-Specific IE that containing the data in Enhanced-ACK sent to that 1273 * Probing Initiator. 1274 * 1275 * @param[in] aInstance The OpenThread instance structure. 1276 * @param[in] aLinkMetrics This parameter specifies what metrics to query. Per spec 4.11.3.4.4.6, at most 2 metrics 1277 * can be specified. The probing would be disabled if @p `aLinkMetrics` is bitwise 0. 1278 * @param[in] aShortAddress The short address of the Probing Initiator. 1279 * @param[in] aExtAddress The extended source address of the Probing Initiator. @p aExtAddr MUST NOT be `NULL`. 1280 * 1281 * @retval OT_ERROR_NONE Successfully configured the Enhanced-ACK Based Probing. 1282 * @retval OT_ERROR_INVALID_ARGS @p aExtAddress is `NULL`. 1283 * @retval OT_ERROR_NOT_FOUND The Initiator indicated by @p aShortAddress is not found when trying to clear. 1284 * @retval OT_ERROR_NO_BUFS No more Initiator can be supported. 1285 * @retval OT_ERROR_NOT_IMPLEMENTED The feature is not implemented. 1286 * 1287 */ 1288 otError otPlatRadioConfigureEnhAckProbing(otInstance *aInstance, 1289 otLinkMetrics aLinkMetrics, 1290 otShortAddress aShortAddress, 1291 const otExtAddress *aExtAddress); 1292 1293 /** 1294 * Add a calibrated power of the specified channel to the power calibration table. 1295 * 1296 * @note This API is an optional radio platform API. It's up to the platform layer to implement it. 1297 * 1298 * The @p aActualPower is the actual measured output power when the parameters of the radio hardware modules 1299 * are set to the @p aRawPowerSetting. 1300 * 1301 * The raw power setting is an opaque byte array. OpenThread doesn't define the format of the raw power setting. 1302 * Its format is radio hardware related and it should be defined by the developers in the platform radio driver. 1303 * For example, if the radio hardware contains both the radio chip and the FEM chip, the raw power setting can be 1304 * a combination of the radio power register and the FEM gain value. 1305 * 1306 * @param[in] aInstance The OpenThread instance structure. 1307 * @param[in] aChannel The radio channel. 1308 * @param[in] aActualPower The actual power in 0.01dBm. 1309 * @param[in] aRawPowerSetting A pointer to the raw power setting byte array. 1310 * @param[in] aRawPowerSettingLength The length of the @p aRawPowerSetting. 1311 * 1312 * @retval OT_ERROR_NONE Successfully added the calibrated power to the power calibration table. 1313 * @retval OT_ERROR_NO_BUFS No available entry in the power calibration table. 1314 * @retval OT_ERROR_INVALID_ARGS The @p aChannel, @p aActualPower or @p aRawPowerSetting is invalid or the 1315 * @p aActualPower already exists in the power calibration table. 1316 * @retval OT_ERROR_NOT_IMPLEMENTED This feature is not implemented. 1317 * 1318 */ 1319 otError otPlatRadioAddCalibratedPower(otInstance *aInstance, 1320 uint8_t aChannel, 1321 int16_t aActualPower, 1322 const uint8_t *aRawPowerSetting, 1323 uint16_t aRawPowerSettingLength); 1324 1325 /** 1326 * Clear all calibrated powers from the power calibration table. 1327 * 1328 * @note This API is an optional radio platform API. It's up to the platform layer to implement it. 1329 * 1330 * @param[in] aInstance The OpenThread instance structure. 1331 * 1332 * @retval OT_ERROR_NONE Successfully cleared all calibrated powers from the power calibration table. 1333 * @retval OT_ERROR_NOT_IMPLEMENTED This feature is not implemented. 1334 * 1335 */ 1336 otError otPlatRadioClearCalibratedPowers(otInstance *aInstance); 1337 1338 /** 1339 * Set the target power for the given channel. 1340 * 1341 * @note This API is an optional radio platform API. It's up to the platform layer to implement it. 1342 * If this API is implemented, the function `otPlatRadioSetTransmitPower()` should be disabled. 1343 * 1344 * The radio driver should set the actual output power to be less than or equal to the target power and as close 1345 * as possible to the target power. 1346 * 1347 * @param[in] aInstance The OpenThread instance structure. 1348 * @param[in] aChannel The radio channel. 1349 * @param[in] aTargetPower The target power in 0.01dBm. Passing `INT16_MAX` will disable this channel to use the 1350 * target power. 1351 * 1352 * @retval OT_ERROR_NONE Successfully set the target power. 1353 * @retval OT_ERROR_INVALID_ARGS The @p aChannel or @p aTargetPower is invalid. 1354 * @retval OT_ERROR_NOT_IMPLEMENTED The feature is not implemented. 1355 * 1356 */ 1357 otError otPlatRadioSetChannelTargetPower(otInstance *aInstance, uint8_t aChannel, int16_t aTargetPower); 1358 1359 /** 1360 * Get the raw power setting for the given channel. 1361 * 1362 * @note OpenThread `src/core/utils` implements a default implementation of the API `otPlatRadioAddCalibratedPower()`, 1363 * `otPlatRadioClearCalibratedPowers()` and `otPlatRadioSetChannelTargetPower()`. This API is provided by 1364 * the default implementation to get the raw power setting for the given channel. If the platform doesn't 1365 * use the default implementation, it can ignore this API. 1366 * 1367 * Platform radio layer should parse the raw power setting based on the radio layer defined format and set the 1368 * parameters of each radio hardware module. 1369 * 1370 * @param[in] aInstance The OpenThread instance structure. 1371 * @param[in] aChannel The radio channel. 1372 * @param[out] aRawPowerSetting A pointer to the raw power setting byte array. 1373 * @param[in,out] aRawPowerSettingLength On input, a pointer to the size of @p aRawPowerSetting. 1374 * On output, a pointer to the length of the raw power setting data. 1375 * 1376 * @retval OT_ERROR_NONE Successfully got the target power. 1377 * @retval OT_ERROR_INVALID_ARGS The @p aChannel is invalid, @p aRawPowerSetting or @p aRawPowerSettingLength is NULL 1378 * or @aRawPowerSettingLength is too short. 1379 * @retval OT_ERROR_NOT_FOUND The raw power setting for the @p aChannel was not found. 1380 * 1381 */ 1382 extern otError otPlatRadioGetRawPowerSetting(otInstance *aInstance, 1383 uint8_t aChannel, 1384 uint8_t *aRawPowerSetting, 1385 uint16_t *aRawPowerSettingLength); 1386 1387 /** 1388 * @} 1389 * 1390 */ 1391 1392 /** 1393 * @} 1394 * 1395 */ 1396 1397 #ifdef __cplusplus 1398 } // end of extern "C" 1399 #endif 1400 1401 #endif // OPENTHREAD_PLATFORM_RADIO_H_ 1402