Skip to content

Commit 886e3cb

Browse files
committed
[thread-direct] add secure wake initiator and listener
- Remove legacy WED/P2P provisional headers - Remove `mle_p2p.cpp` (Thread Direct uses MAC-layer handshake) - Add Thread Direct public API (`thread_direct.h`) and platform API (`platform/thread_direct.h`) - `WakeupTxScheduler` handles wake initiator burst scheduling with wake key index 129 (network-derived) and 130-192 (guest keys) - Add `sub_mac_wl` for wake listener receive path, rename `sub_mac_wed.cpp` to `sub_mac_wl.cpp` - Add `DirectHandler` for WI/WL paths with stubs for upcoming implementation - Add `DirectPeer`/`DirectPeerTable` replacing legacy `peer`/`peer_table` - Changes to `MeshForwarder::Start` and `Mle::BecomeDetached` to respect rx-off-when-idle for Thread Direct devices - Add CLI support (`cli_td`) - Add Spinel/NCP stubs for Thread Direct properties
1 parent 318b4b0 commit 886e3cb

84 files changed

Lines changed: 4484 additions & 3296 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

etc/cmake/options.cmake

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -242,7 +242,7 @@ ot_option(OT_NETDIAG_CLIENT OPENTHREAD_CONFIG_TMF_NETDIAG_CLIENT_ENABLE "Network
242242
ot_option(OT_NETDIAG_VENDOR_INFO OPENTHREAD_CONFIG_NET_DIAG_VENDOR_INFO_SET_API_ENABLE "Allow setting vendor info at runtime")
243243
ot_option(OT_OPERATIONAL_DATASET_AUTO_INIT OPENTHREAD_CONFIG_OPERATIONAL_DATASET_AUTO_INIT "operational dataset auto init")
244244
ot_option(OT_OTNS OPENTHREAD_CONFIG_OTNS_ENABLE "OTNS")
245-
ot_option(OT_P2P OPENTHREAD_CONFIG_P2P_ENABLE "peer to peer")
245+
246246
ot_option(OT_PING_SENDER OPENTHREAD_CONFIG_PING_SENDER_ENABLE "ping sender" ${OT_APP_CLI})
247247
ot_option(OT_PLATFORM_BOOTLOADER_MODE OPENTHREAD_CONFIG_PLATFORM_BOOTLOADER_MODE_ENABLE "platform bootloader mode")
248248
ot_option(OT_PLATFORM_DNSSD OPENTHREAD_CONFIG_PLATFORM_DNSSD_ENABLE "platform dnssd")
@@ -266,13 +266,14 @@ ot_option(OT_TCP OPENTHREAD_CONFIG_TCP_ENABLE "TCP")
266266
ot_option(OT_TIME_SYNC OPENTHREAD_CONFIG_TIME_SYNC_ENABLE "time synchronization service")
267267
ot_option(OT_TREL OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE "TREL radio link for Thread over Infrastructure feature")
268268
ot_option(OT_TREL_MANAGE_DNSSD OPENTHREAD_CONFIG_TREL_MANAGE_DNSSD_ENABLE "TREL to manage DNSSD and peer discovery")
269+
ot_option(OT_THREAD_DIRECT_WAKE_INITIATOR OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE "Thread Direct wake initiator")
270+
ot_option(OT_THREAD_DIRECT_WAKE_LISTENER OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE "Thread Direct wake listener")
269271
ot_option(OT_TX_BEACON_PAYLOAD OPENTHREAD_CONFIG_MAC_OUTGOING_BEACON_PAYLOAD_ENABLE "tx beacon payload")
270272
ot_option(OT_TX_QUEUE_STATS OPENTHREAD_CONFIG_TX_QUEUE_STATISTICS_ENABLE "tx queue statistics")
271273
ot_option(OT_UDP_FORWARD OPENTHREAD_CONFIG_UDP_FORWARD_ENABLE "UDP forward")
272274
ot_option(OT_UPTIME OPENTHREAD_CONFIG_UPTIME_ENABLE "uptime")
273275
ot_option(OT_VERHOEFF_CHECKSUM OPENTHREAD_CONFIG_VERHOEFF_CHECKSUM_ENABLE "verhoeff checksum")
274-
ot_option(OT_WAKEUP_COORDINATOR OPENTHREAD_CONFIG_WAKEUP_COORDINATOR_ENABLE "wake-up coordinator")
275-
ot_option(OT_WAKEUP_END_DEVICE OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE "wake-up end device")
276+
276277
ot_option(OT_SPINEL_CP_RESET_FAIL_CALLBACK_ENABLE OPENTHREAD_SPINEL_CONFIG_COPROCESSOR_RESET_FAILURE_CALLBACK_ENABLE "CP reset failure callback")
277278

278279
option(OT_DOC "build OpenThread documentation")

examples/platforms/simulation/radio.c

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1161,6 +1161,33 @@ void otPlatRadioSetMacFrameCounter(otInstance *aInstance, uint32_t aMacFrameCoun
11611161
sRadioContext.mMacFrameCounter = aMacFrameCounter;
11621162
}
11631163

1164+
#if OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE || OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE
1165+
void otPlatRadioSetWakeKey(otInstance *aInstance, uint8_t aKeyIndex, const otMacKeyMaterial *aWakeKey)
1166+
{
1167+
OT_UNUSED_VARIABLE(aInstance);
1168+
OT_UNUSED_VARIABLE(aKeyIndex);
1169+
OT_UNUSED_VARIABLE(aWakeKey);
1170+
}
1171+
#endif
1172+
1173+
#if OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE
1174+
static uint32_t sWakeFrameCounter;
1175+
1176+
void otPlatRadioSetWakeFrameCounter(otInstance *aInstance, uint32_t aWakeFrameCounter)
1177+
{
1178+
OT_UNUSED_VARIABLE(aInstance);
1179+
1180+
sWakeFrameCounter = aWakeFrameCounter;
1181+
}
1182+
1183+
uint32_t otPlatRadioGetWakeFrameCounter(otInstance *aInstance)
1184+
{
1185+
OT_UNUSED_VARIABLE(aInstance);
1186+
1187+
return sWakeFrameCounter;
1188+
}
1189+
#endif
1190+
11641191
otError otPlatRadioSetChannelMaxTransmitPower(otInstance *aInstance, uint8_t aChannel, int8_t aMaxPower)
11651192
{
11661193
OT_UNUSED_VARIABLE(aInstance);

examples/platforms/utils/mac_frame.cpp

Lines changed: 21 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -318,11 +318,7 @@ otError otMacFrameProcessTransmitSecurity(otRadioFrame *aFrame, otRadioContext *
318318
uint32_t frameCounter;
319319
bool processKeyId;
320320

321-
processKeyId =
322-
#if OPENTHREAD_CONFIG_WAKEUP_COORDINATOR_ENABLE
323-
otMacFrameIsKeyIdMode2(aFrame) ||
324-
#endif
325-
otMacFrameIsKeyIdMode1(aFrame);
321+
processKeyId = otMacFrameIsKeyIdMode1(aFrame);
326322

327323
VerifyOrExit(otMacFrameIsSecurityEnabled(aFrame) && processKeyId && !aFrame->mInfo.mTxInfo.mIsSecurityProcessed);
328324

@@ -455,3 +451,23 @@ bool otMacFrameSrcAddrMatchCslReceiverPeer(const otRadioFrame *aFrame, const otR
455451
exit:
456452
return matches;
457453
}
454+
455+
#if OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE
456+
457+
bool otMacFrameIsTdWakeCommand(otRadioFrame *aFrame)
458+
{
459+
uint8_t keyId;
460+
461+
if (!otMacFrameIsCommand(aFrame) || otMacFrameIsAckRequested(aFrame) || !otMacFrameIsSecurityEnabled(aFrame) ||
462+
!otMacFrameIsKeyIdMode1(aFrame))
463+
{
464+
return false;
465+
}
466+
467+
keyId = otMacFrameGetKeyId(aFrame);
468+
469+
return keyId == OT_MAC_FRAME_WAKE_KEY_INDEX ||
470+
(keyId >= OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MIN && keyId <= OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MAX);
471+
}
472+
473+
#endif // OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE

examples/platforms/utils/mac_frame.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -401,6 +401,21 @@ otError otMacFrameProcessTransmitSecurity(otRadioFrame *aFrame, otRadioContext *
401401
*/
402402
bool otMacFrameSrcAddrMatchCslReceiverPeer(const otRadioFrame *aFrame, const otRadioContext *aRadioContext);
403403

404+
#if OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE
405+
/**
406+
* Tell if @p aFrame is a Thread Direct Wake Command frame.
407+
*
408+
* A TD Wake Command is a MAC Command with no ACK request and wake key index 129 or 130-192
409+
* in the Auxiliary Security Header (stamped by the stack before transmit).
410+
*
411+
* @param[in] aFrame A pointer to the frame.
412+
*
413+
* @retval true The frame is a TD Wake Command.
414+
* @retval false The frame is not a TD Wake Command.
415+
*/
416+
bool otMacFrameIsTdWakeCommand(otRadioFrame *aFrame);
417+
#endif
418+
404419
#ifdef __cplusplus
405420
} // extern "C"
406421
#endif

include/openthread/BUILD.gn

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -112,12 +112,11 @@ source_set("openthread") {
112112
"platform/radio.h",
113113
"platform/settings.h",
114114
"platform/spi-slave.h",
115+
"platform/thread_direct.h",
115116
"platform/time.h",
116117
"platform/toolchain.h",
117118
"platform/trel.h",
118119
"platform/udp.h",
119-
"provisional/link.h",
120-
"provisional/p2p.h",
121120
"radio_stats.h",
122121
"random_crypto.h",
123122
"random_noncrypto.h",
@@ -133,6 +132,7 @@ source_set("openthread") {
133132
"tcp.h",
134133
"tcp_ext.h",
135134
"thread.h",
135+
"thread_direct.h",
136136
"thread_ftd.h",
137137
"trel.h",
138138
"udp.h",

include/openthread/dataset.h

Lines changed: 16 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -207,7 +207,7 @@ typedef struct otOperationalDatasetComponents
207207
bool mIsPskcPresent; ///< TRUE if PSKc is present, FALSE otherwise.
208208
bool mIsSecurityPolicyPresent; ///< TRUE if Security Policy is present, FALSE otherwise.
209209
bool mIsChannelMaskPresent; ///< TRUE if Channel Mask is present, FALSE otherwise.
210-
bool mIsWakeupChannelPresent; ///< TRUE if Wake-up Channel is present, FALSE otherwise.
210+
bool mIsWakeupChannelPresent; ///< TRUE if Wake Channel is present, FALSE otherwise.
211211
} otOperationalDatasetComponents;
212212

213213
/**
@@ -227,20 +227,20 @@ typedef struct otTimestamp
227227
*/
228228
typedef struct otOperationalDataset
229229
{
230-
otTimestamp mActiveTimestamp; ///< Active Timestamp
231-
otTimestamp mPendingTimestamp; ///< Pending Timestamp
232-
otNetworkKey mNetworkKey; ///< Network Key
233-
otNetworkName mNetworkName; ///< Network Name
234-
otExtendedPanId mExtendedPanId; ///< Extended PAN ID
235-
otMeshLocalPrefix mMeshLocalPrefix; ///< Mesh Local Prefix
236-
uint32_t mDelay; ///< Delay Timer
237-
otPanId mPanId; ///< PAN ID
238-
uint16_t mChannel; ///< Channel
239-
uint16_t mWakeupChannel; ///< Wake-up Channel
240-
otPskc mPskc; ///< PSKc
241-
otSecurityPolicy mSecurityPolicy; ///< Security Policy
242-
otChannelMask mChannelMask; ///< Channel Mask
243-
otOperationalDatasetComponents mComponents; ///< Specifies which components are set in the Dataset.
230+
otTimestamp mActiveTimestamp; ///< Active Timestamp
231+
otTimestamp mPendingTimestamp; ///< Pending Timestamp
232+
otNetworkKey mNetworkKey; ///< Network Key
233+
otNetworkName mNetworkName; ///< Network Name
234+
otExtendedPanId mExtendedPanId; ///< Extended PAN ID
235+
otMeshLocalPrefix mMeshLocalPrefix; ///< Mesh Local Prefix
236+
uint32_t mDelay; ///< Delay Timer
237+
otPanId mPanId; ///< PAN ID
238+
uint16_t mChannel; ///< Channel
239+
uint16_t mWakeupChannel; ///< Wake Channel (always 20; see OPENTHREAD_CONFIG_THREAD_DIRECT_DEFAULT_WAKE_CHANNEL)
240+
otPskc mPskc; ///< PSKc
241+
otSecurityPolicy mSecurityPolicy; ///< Security Policy
242+
otChannelMask mChannelMask; ///< Channel Mask
243+
otOperationalDatasetComponents mComponents; ///< Specifies which components are set in the Dataset.
244244
} otOperationalDataset;
245245

246246
/**
@@ -303,7 +303,7 @@ typedef enum otMeshcopTlvType
303303
OT_MESHCOP_TLV_SCAN_DURATION = 56, ///< meshcop Scan Duration TLV
304304
OT_MESHCOP_TLV_ENERGY_LIST = 57, ///< meshcop Energy List TLV
305305
OT_MESHCOP_TLV_THREAD_DOMAIN_NAME = 59, ///< meshcop Thread Domain Name TLV
306-
OT_MESHCOP_TLV_WAKEUP_CHANNEL = 74, ///< meshcop Wake-up Channel TLV
306+
OT_MESHCOP_TLV_WAKEUP_CHANNEL = 74, ///< meshcop Wake Channel TLV (always 20 for Thread Direct)
307307
OT_MESHCOP_TLV_ADMITTER_STATE = 90, ///< meshcop Admitter State TLV
308308
OT_MESHCOP_TLV_ENROLLER_ID = 91, ///< meshcop Enroller ID TLV
309309
OT_MESHCOP_TLV_ENROLLER_MODE = 92, ///< meshcop Enroller Mode TLV

include/openthread/instance.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ extern "C" {
5252
*
5353
* @note This number versions both OpenThread platform and user APIs.
5454
*/
55-
#define OPENTHREAD_API_VERSION (603)
55+
#define OPENTHREAD_API_VERSION (604)
5656

5757
/**
5858
* @addtogroup api-instance

include/openthread/link.h

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1115,35 +1115,38 @@ otError otLinkSetRegion(otInstance *aInstance, uint16_t aRegionCode);
11151115
otError otLinkGetRegion(otInstance *aInstance, uint16_t *aRegionCode);
11161116

11171117
/**
1118-
* Gets the Wake-up channel.
1118+
* Gets the Thread Direct Wake Channel.
11191119
*
1120-
* Requires `OPENTHREAD_CONFIG_WAKEUP_COORDINATOR_ENABLE` or `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1120+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE` or
1121+
* `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
11211122
*
11221123
* @param[in] aInstance A pointer to an OpenThread instance.
11231124
*
1124-
* @returns The Wake-up channel.
1125+
* @returns The Wake Channel (always 20).
11251126
*/
11261127
uint8_t otLinkGetWakeupChannel(otInstance *aInstance);
11271128

11281129
/**
1129-
* Sets the Wake-up channel.
1130+
* Sets the Thread Direct Wake Channel.
11301131
*
1131-
* Requires `OPENTHREAD_CONFIG_WAKEUP_COORDINATOR_ENABLE` or `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1132+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_INITIATOR_ENABLE` or
1133+
* `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
1134+
*
1135+
* The Thread Direct feature mandates channel 20 (`OPENTHREAD_CONFIG_THREAD_DIRECT_DEFAULT_WAKE_CHANNEL`)
1136+
* as the sole Wake Channel. Any other value returns `OT_ERROR_INVALID_ARGS`.
11321137
*
11331138
* @param[in] aInstance A pointer to an OpenThread instance.
1134-
* @param[in] aChannel The Wake-up sample channel. Channel value should be `0` (Set Wake-up Channel unspecified,
1135-
* which means the device will use the PAN channel) or within the range [1, 10] (if 915-MHz
1136-
* supported) and [11, 26] (if 2.4 GHz supported).
1139+
* @param[in] aChannel The Wake Channel. Must equal 20.
11371140
*
1138-
* @retval OT_ERROR_NONE Successfully set the Wake-up channel.
1139-
* @retval OT_ERROR_INVALID_ARGS Invalid @p aChannel.
1141+
* @retval OT_ERROR_NONE Successfully set the Wake Channel.
1142+
* @retval OT_ERROR_INVALID_ARGS @p aChannel is not 20.
11401143
*/
11411144
otError otLinkSetWakeupChannel(otInstance *aInstance, uint8_t aChannel);
11421145

11431146
/**
11441147
* Enables or disables listening for wake-up frames.
11451148
*
1146-
* Requires `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1149+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
11471150
*
11481151
* @param[in] aInstance A pointer to an OpenThread instance.
11491152
* @param[in] aEnable true to enable listening for wake-up frames, or false otherwise.
@@ -1157,7 +1160,7 @@ otError otLinkSetWakeUpListenEnabled(otInstance *aInstance, bool aEnable);
11571160
/**
11581161
* Returns whether listening for wake-up frames is enabled.
11591162
*
1160-
* Requires `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1163+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
11611164
*
11621165
* @param[in] aInstance A pointer to an OpenThread instance.
11631166
*
@@ -1169,7 +1172,7 @@ bool otLinkIsWakeupListenEnabled(otInstance *aInstance);
11691172
/**
11701173
* Get the wake-up listen parameters.
11711174
*
1172-
* Requires `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1175+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
11731176
*
11741177
* @param[in] aInstance A pointer to an OpenThread instance.
11751178
* @param[out] aInterval A pointer to return the wake-up listen interval in microseconds.
@@ -1183,7 +1186,7 @@ void otLinkGetWakeupListenParameters(otInstance *aInstance, uint32_t *aInterval,
11831186
* The listen interval must be greater than the listen duration.
11841187
* The listen duration must be greater or equal than the minimum supported.
11851188
*
1186-
* Requires `OPENTHREAD_CONFIG_WAKEUP_END_DEVICE_ENABLE`.
1189+
* Requires `OPENTHREAD_CONFIG_THREAD_DIRECT_WAKE_LISTENER_ENABLE`.
11871190
*
11881191
* @param[in] aInstance A pointer to an OpenThread instance.
11891192
* @param[in] aInterval The wake-up listen interval in microseconds.

include/openthread/platform/radio.h

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -744,6 +744,65 @@ void otPlatRadioSetMacFrameCounter(otInstance *aInstance, uint32_t aMacFrameCoun
744744
*/
745745
void otPlatRadioSetMacFrameCounterIfLarger(otInstance *aInstance, uint32_t aMacFrameCounter);
746746

747+
/**
748+
* IEEE 802.15.4 key index reserved for the default Thread Direct Wake Key (network-derived).
749+
*
750+
* This value (129) is outside the range used for standard Thread MAC keys (1-128). It is
751+
* carried in the key index field of TD Wake Frames that use the network-derived wake key.
752+
*/
753+
#define OT_MAC_FRAME_WAKE_KEY_INDEX 129
754+
755+
/**
756+
* Lowest key index valid for a Thread Direct guest Wake Key.
757+
*/
758+
#define OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MIN 130
759+
760+
/**
761+
* Highest key index valid for a Thread Direct guest Wake Key.
762+
*/
763+
#define OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MAX 192
764+
765+
/**
766+
* Registers or removes a Thread Direct Wake Key at the given key index.
767+
*
768+
* Is used when radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability. When the platform
769+
* processes a TX frame whose key index matches `aKeyIndex`, it uses `aWakeKey` to perform
770+
* AES-CCM encryption rather than the standard Thread MAC key set registered via
771+
* `otPlatRadioSetMacKey`.
772+
*
773+
* `aKeyIndex` must be `OT_MAC_FRAME_WAKE_KEY_INDEX` (129) for the default network-derived
774+
* wake key, or in [`OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MIN`,
775+
* `OT_MAC_FRAME_GUEST_WAKE_KEY_INDEX_MAX`] (130-192) for a guest wake key.
776+
*
777+
* Passing `aWakeKey` as NULL removes any previously registered key at `aKeyIndex`.
778+
*
779+
* @param[in] aInstance A pointer to an OpenThread instance.
780+
* @param[in] aKeyIndex Key index (129 for default, 130-192 for guest keys).
781+
* @param[in] aWakeKey Key material to register, or NULL to remove.
782+
*/
783+
void otPlatRadioSetWakeKey(otInstance *aInstance, uint8_t aKeyIndex, const otMacKeyMaterial *aWakeKey);
784+
785+
/**
786+
* Sets the Thread Direct wake frame counter value.
787+
*
788+
* Is used when radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability.
789+
*
790+
* @param[in] aInstance A pointer to an OpenThread instance.
791+
* @param[in] aWakeFrameCounter The wake frame counter value.
792+
*/
793+
void otPlatRadioSetWakeFrameCounter(otInstance *aInstance, uint32_t aWakeFrameCounter);
794+
795+
/**
796+
* Gets the current Thread Direct wake frame counter value.
797+
*
798+
* Is used when radio provides `OT_RADIO_CAPS_TRANSMIT_SEC` capability.
799+
*
800+
* @param[in] aInstance A pointer to an OpenThread instance.
801+
*
802+
* @returns The current wake frame counter value.
803+
*/
804+
uint32_t otPlatRadioGetWakeFrameCounter(otInstance *aInstance);
805+
747806
/**
748807
* Get the current time in microseconds referenced to a continuous monotonic
749808
* local radio clock (64 bits width).

0 commit comments

Comments
 (0)