drivers: nrf_802154: Update the IEEE 802.15.4 component
This commit updates the nRF 802.15.4 radio driver to feature the latest changes. sdk-nrf-802154 commit: 9307dc01053c7f4ddb3081984a72a6d454ec8681 Signed-off-by: Jedrzej Ciupis <jedrzej.ciupis@nordicsemi.no>
This commit is contained in:
parent
fc301b9758
commit
9bd5891e3c
|
@ -64,8 +64,8 @@ else ()
|
|||
endif ()
|
||||
|
||||
if (SL_OPENSOURCE OR NRF53_SERIES)
|
||||
target_compile_definitions(nrf-802154-driver
|
||||
PUBLIC
|
||||
target_compile_definitions(nrf-802154-driver-interface
|
||||
INTERFACE
|
||||
# Disable Frame Timestamps
|
||||
NRF_802154_FRAME_TIMESTAMP_ENABLED=0
|
||||
# Disable DTRX
|
||||
|
@ -74,8 +74,8 @@ if (SL_OPENSOURCE OR NRF53_SERIES)
|
|||
NRF_802154_IFS_ENABLED=0
|
||||
)
|
||||
else()
|
||||
target_compile_definitions(nrf-802154-driver
|
||||
PUBLIC
|
||||
target_compile_definitions(nrf-802154-driver-interface
|
||||
INTERFACE
|
||||
# Enable Frame Timestamps
|
||||
NRF_802154_FRAME_TIMESTAMP_ENABLED=1
|
||||
# Enable DTRX
|
||||
|
|
|
@ -56,7 +56,25 @@ extern "C" {
|
|||
/**
|
||||
* @brief Timestamp value indicating that the timestamp is inaccurate.
|
||||
*/
|
||||
#define NRF_802154_NO_TIMESTAMP 0
|
||||
#define NRF_802154_NO_TIMESTAMP 0
|
||||
|
||||
/**
|
||||
* @brief Invalid delayed timeslot identifier.
|
||||
*/
|
||||
#define NRF_802154_RESERVED_INVALID_ID UINT32_MAX
|
||||
|
||||
/**
|
||||
* @brief Reception window identifier reserved for immediate reception.
|
||||
*/
|
||||
#define NRF_802154_RESERVED_IMM_RX_WINDOW_ID (UINT32_MAX - 1)
|
||||
|
||||
/**
|
||||
* @brief Upper bound for delayed reception window identifiers used by the application.
|
||||
*
|
||||
* All integers ranging from 0 to @ref NRF_802154_RESERVED_DRX_ID_UPPER_BOUND (inclusive)
|
||||
* can be used by the application as identifiers of delayed reception windows.
|
||||
*/
|
||||
#define NRF_802154_RESERVED_DRX_ID_UPPER_BOUND (UINT32_MAX - 4)
|
||||
|
||||
/**
|
||||
* @brief Initializes the 802.15.4 driver.
|
||||
|
@ -452,11 +470,19 @@ bool nrf_802154_receive(void);
|
|||
*
|
||||
* A scheduled reception can be cancelled by a call to @ref nrf_802154_receive_at_cancel.
|
||||
*
|
||||
* @param[in] t0 Base of delay time - absolute time used by the Timer Scheduler,
|
||||
* in microseconds (us).
|
||||
* @param[in] dt Delta of delay time from @p t0, in microseconds (us).
|
||||
* @param[in] timeout Reception timeout (counted from @p t0 + @p dt), in microseconds (us).
|
||||
* @param[in] channel Radio channel on which the frame is to be received.
|
||||
* @note The identifier @p id must be unique. It must not have the same value as identifiers
|
||||
* of other delayed timeslots active at the moment, so that it can be mapped unambiguously
|
||||
* to an active delayed operation if the request is successful. In particular, none of the reserved
|
||||
* identifiers can be used.
|
||||
*
|
||||
* @param[in] t0 Base of delay time - absolute time used by the Timer Scheduler,
|
||||
* in microseconds (us).
|
||||
* @param[in] dt Delta of delay time from @p t0, in microseconds (us).
|
||||
* @param[in] timeout Reception timeout (counted from @p t0 + @p dt), in microseconds (us).
|
||||
* @param[in] channel Radio channel on which the frame is to be received.
|
||||
* @param[in] id Identifier of the scheduled reception window. If the reception has been
|
||||
* scheduled successfully, the value of this parameter can be used in
|
||||
* @ref nrf_802154_receive_at_cancel to cancel it.
|
||||
*
|
||||
* @retval true The reception procedure was scheduled.
|
||||
* @retval false The driver could not schedule the reception procedure.
|
||||
|
@ -464,7 +490,8 @@ bool nrf_802154_receive(void);
|
|||
bool nrf_802154_receive_at(uint32_t t0,
|
||||
uint32_t dt,
|
||||
uint32_t timeout,
|
||||
uint8_t channel);
|
||||
uint8_t channel,
|
||||
uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Cancels a delayed reception scheduled by a call to @ref nrf_802154_receive_at.
|
||||
|
@ -473,10 +500,14 @@ bool nrf_802154_receive_at(uint32_t t0,
|
|||
* entering the receive window. If the receive window has been scheduled and has already started,
|
||||
* the radio remains in the receive state, but a window timeout will not be reported.
|
||||
*
|
||||
* @param[in] id Identifier of the delayed reception window to be cancelled. If the provided
|
||||
* value does not refer to any scheduled or active receive window, the function
|
||||
* returns false.
|
||||
*
|
||||
* @retval true The delayed reception was scheduled and successfully cancelled.
|
||||
* @retval false No delayed reception was scheduled.
|
||||
*/
|
||||
bool nrf_802154_receive_at_cancel(void);
|
||||
bool nrf_802154_receive_at_cancel(uint32_t id);
|
||||
|
||||
#if NRF_802154_USE_RAW_API
|
||||
/**
|
||||
|
@ -806,8 +837,13 @@ extern void nrf_802154_received_timestamp(uint8_t * p_data,
|
|||
* @brief Notifies that the reception of a frame failed.
|
||||
*
|
||||
* @param[in] error Error code that indicates the reason of the failure.
|
||||
* @param[in] id Identifier of reception window the error occurred in.
|
||||
* If the error is related to a delayed reception window requested through
|
||||
* @ref nrf_802154_receive_at, the value of @p id equals the identifier
|
||||
* of the scheduled reception window. Otherwise, the value of @p id equals
|
||||
* @ref NRF_802154_RESERVED_IMM_RX_WINDOW_ID.
|
||||
*/
|
||||
extern void nrf_802154_receive_failed(nrf_802154_rx_error_t error);
|
||||
extern void nrf_802154_receive_failed(nrf_802154_rx_error_t error, uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Notifies that transmitting a frame has started.
|
||||
|
|
|
@ -43,126 +43,129 @@
|
|||
#include <stdint.h>
|
||||
#include "nrf_802154_config.h"
|
||||
|
||||
#define ACK_HEADER_WITH_PENDING 0x12 ///< The first byte of an ACK frame containing a pending bit.
|
||||
#define ACK_HEADER_WITHOUT_PENDING 0x02 ///< The first byte of an ACK frame without a pending bit.
|
||||
#define ACK_HEADER_WITH_PENDING 0x12 ///< The first byte of an ACK frame containing a pending bit.
|
||||
#define ACK_HEADER_WITHOUT_PENDING 0x02 ///< The first byte of an ACK frame without a pending bit.
|
||||
|
||||
#define ACK_REQUEST_OFFSET 1 ///< Byte containing the ACK request bit (+1 for the frame length byte).
|
||||
#define ACK_REQUEST_BIT (1 << 5) ///< ACK request bit.
|
||||
#define ACK_REQUEST_OFFSET 1 ///< Byte containing the ACK request bit (+1 for the frame length byte).
|
||||
#define ACK_REQUEST_BIT (1 << 5) ///< ACK request bit.
|
||||
|
||||
#define DEST_ADDR_TYPE_OFFSET 2 ///< Byte containing the destination address type (+1 for the frame length byte).
|
||||
#define DEST_ADDR_TYPE_MASK 0x0c ///< Mask of bits containing the destination address type.
|
||||
#define DEST_ADDR_TYPE_EXTENDED 0x0c ///< Bits containing the extended destination address type.
|
||||
#define DEST_ADDR_TYPE_NONE 0x00 ///< Bits containing a not-present destination address type.
|
||||
#define DEST_ADDR_TYPE_SHORT 0x08 ///< Bits containing the short destination address type.
|
||||
#define DEST_ADDR_OFFSET 6 ///< Offset of the destination address in the Data frame (+1 for the frame length byte).
|
||||
#define DEST_ADDR_TYPE_OFFSET 2 ///< Byte containing the destination address type (+1 for the frame length byte).
|
||||
#define DEST_ADDR_TYPE_MASK 0x0c ///< Mask of bits containing the destination address type.
|
||||
#define DEST_ADDR_TYPE_EXTENDED 0x0c ///< Bits containing the extended destination address type.
|
||||
#define DEST_ADDR_TYPE_NONE 0x00 ///< Bits containing a not-present destination address type.
|
||||
#define DEST_ADDR_TYPE_SHORT 0x08 ///< Bits containing the short destination address type.
|
||||
#define DEST_ADDR_OFFSET 6 ///< Offset of the destination address in the Data frame (+1 for the frame length byte).
|
||||
|
||||
#define DSN_OFFSET 3 ///< Byte containing the DSN value (+1 for the frame length byte).
|
||||
#define DSN_SUPPRESS_OFFSET 2 ///< Byte containing the DSN suppression field.
|
||||
#define DSN_SUPPRESS_BIT 0x01 ///< Bits containing the DSN suppression field.
|
||||
#define DSN_OFFSET 3 ///< Byte containing the DSN value (+1 for the frame length byte).
|
||||
#define DSN_SUPPRESS_OFFSET 2 ///< Byte containing the DSN suppression field.
|
||||
#define DSN_SUPPRESS_BIT 0x01 ///< Bits containing the DSN suppression field.
|
||||
|
||||
#define FRAME_COUNTER_SUPPRESS_BIT 0x20 ///< Bit containing the Frame Counter Suppression field.
|
||||
#define FRAME_COUNTER_SUPPRESS_BIT 0x20 ///< Bit containing the Frame Counter Suppression field.
|
||||
|
||||
#define FRAME_PENDING_OFFSET 1 ///< Byte containing a pending bit (+1 for the frame length byte).
|
||||
#define FRAME_PENDING_BIT (1 << 4) ///< Pending bit.
|
||||
#define FRAME_PENDING_OFFSET 1 ///< Byte containing a pending bit (+1 for the frame length byte).
|
||||
#define FRAME_PENDING_BIT (1 << 4) ///< Pending bit.
|
||||
|
||||
#define FRAME_TYPE_OFFSET 1 ///< Byte containing the frame type bits (+1 for the frame length byte).
|
||||
#define FRAME_TYPE_MASK 0x07 ///< Mask of bits containing the frame type.
|
||||
#define FRAME_TYPE_ACK 0x02 ///< Bits containing the ACK frame type.
|
||||
#define FRAME_TYPE_BEACON 0x00 ///< Bits containing the Beacon frame type.
|
||||
#define FRAME_TYPE_COMMAND 0x03 ///< Bits containing the Command frame type.
|
||||
#define FRAME_TYPE_DATA 0x01 ///< Bits containing the Data frame type.
|
||||
#define FRAME_TYPE_EXTENDED 0x07 ///< Bits containing the Extended frame type.
|
||||
#define FRAME_TYPE_FRAGMENT 0x06 ///< Bits containing the Fragment or the Frak frame type.
|
||||
#define FRAME_TYPE_MULTIPURPOSE 0x05 ///< Bits containing the Multipurpose frame type.
|
||||
#define FRAME_TYPE_OFFSET 1 ///< Byte containing the frame type bits (+1 for the frame length byte).
|
||||
#define FRAME_TYPE_MASK 0x07 ///< Mask of bits containing the frame type.
|
||||
#define FRAME_TYPE_ACK 0x02 ///< Bits containing the ACK frame type.
|
||||
#define FRAME_TYPE_BEACON 0x00 ///< Bits containing the Beacon frame type.
|
||||
#define FRAME_TYPE_COMMAND 0x03 ///< Bits containing the Command frame type.
|
||||
#define FRAME_TYPE_DATA 0x01 ///< Bits containing the Data frame type.
|
||||
#define FRAME_TYPE_EXTENDED 0x07 ///< Bits containing the Extended frame type.
|
||||
#define FRAME_TYPE_FRAGMENT 0x06 ///< Bits containing the Fragment or the Frak frame type.
|
||||
#define FRAME_TYPE_MULTIPURPOSE 0x05 ///< Bits containing the Multipurpose frame type.
|
||||
|
||||
#define FRAME_VERSION_OFFSET 2 ///< Byte containing the frame version bits (+1 for the frame length byte).
|
||||
#define FRAME_VERSION_MASK 0x30 ///< Mask of bits containing the frame version.
|
||||
#define FRAME_VERSION_0 0x00 ///< Bits containing the frame version 0b00.
|
||||
#define FRAME_VERSION_1 0x10 ///< Bits containing the frame version 0b01.
|
||||
#define FRAME_VERSION_2 0x20 ///< Bits containing the frame version 0b10.
|
||||
#define FRAME_VERSION_3 0x30 ///< Bits containing the frame version 0b11.
|
||||
#define FRAME_VERSION_OFFSET 2 ///< Byte containing the frame version bits (+1 for the frame length byte).
|
||||
#define FRAME_VERSION_MASK 0x30 ///< Mask of bits containing the frame version.
|
||||
#define FRAME_VERSION_0 0x00 ///< Bits containing the frame version 0b00.
|
||||
#define FRAME_VERSION_1 0x10 ///< Bits containing the frame version 0b01.
|
||||
#define FRAME_VERSION_2 0x20 ///< Bits containing the frame version 0b10.
|
||||
#define FRAME_VERSION_3 0x30 ///< Bits containing the frame version 0b11.
|
||||
|
||||
#define IE_HEADER_LENGTH_MASK 0x3f ///< Mask of bits containing the length of an IE header content.
|
||||
#define IE_PRESENT_OFFSET 2 ///< Byte containing the IE Present bit.
|
||||
#define IE_PRESENT_BIT 0x02 ///< Bits containing the IE Present field.
|
||||
#define IE_HEADER_LENGTH_MASK 0x3f ///< Mask of bits containing the length of an IE header content.
|
||||
#define IE_PRESENT_OFFSET 2 ///< Byte containing the IE Present bit.
|
||||
#define IE_PRESENT_BIT 0x02 ///< Bits containing the IE Present field.
|
||||
|
||||
#define KEY_ID_MODE_MASK 0x18 ///< Mask of bits containing Key Identifier Mode in the Security Control field.
|
||||
#define KEY_ID_MODE_0 0 ///< Bits containing the 0x00 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_1 0x08 ///< Bits containing the 0x01 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_2 0x10 ///< Bits containing the 0x10 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_3 0x18 ///< Bits containing the 0x11 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_MASK 0x18 ///< Mask of bits containing Key Identifier Mode in the Security Control field.
|
||||
#define KEY_ID_MODE_0 0 ///< Bits containing the 0x00 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_1 0x08 ///< Bits containing the 0x01 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_2 0x10 ///< Bits containing the 0x10 Key Identifier Mode.
|
||||
#define KEY_ID_MODE_3 0x18 ///< Bits containing the 0x11 Key Identifier Mode.
|
||||
|
||||
#define MAC_CMD_ASSOC_REQ 0x01 ///< Command frame identifier for MAC Association request.
|
||||
#define MAC_CMD_ASSOC_RESP 0x02 ///< Command frame identifier for MAC Association response.
|
||||
#define MAC_CMD_DISASSOC_NOTIFY 0x03 ///< Command frame identifier for MAC Disaccociation notification.
|
||||
#define MAC_CMD_DATA_REQ 0x04 ///< Command frame identifier for MAC Data Requests.
|
||||
#define MAC_CMD_PANID_CONFLICT 0x05 ///< Command frame identifier for MAC PAN ID conflict notification.
|
||||
#define MAC_CMD_ORPHAN_NOTIFY 0x06 ///< Command frame identifier for MAC Orphan notification.
|
||||
#define MAC_CMD_BEACON_REQ 0x07 ///< Command frame identifier for MAC Beacon.
|
||||
#define MAC_CMD_COORD_REALIGN 0x08 ///< Command frame identifier for MAC Coordinator realignment.
|
||||
#define MAC_CMD_GTS_REQUEST 0x09 ///< Command frame identifier for MAC GTS request.
|
||||
#define MAC_CMD_ASSOC_REQ 0x01 ///< Command frame identifier for MAC Association request.
|
||||
#define MAC_CMD_ASSOC_RESP 0x02 ///< Command frame identifier for MAC Association response.
|
||||
#define MAC_CMD_DISASSOC_NOTIFY 0x03 ///< Command frame identifier for MAC Disaccociation notification.
|
||||
#define MAC_CMD_DATA_REQ 0x04 ///< Command frame identifier for MAC Data Requests.
|
||||
#define MAC_CMD_PANID_CONFLICT 0x05 ///< Command frame identifier for MAC PAN ID conflict notification.
|
||||
#define MAC_CMD_ORPHAN_NOTIFY 0x06 ///< Command frame identifier for MAC Orphan notification.
|
||||
#define MAC_CMD_BEACON_REQ 0x07 ///< Command frame identifier for MAC Beacon.
|
||||
#define MAC_CMD_COORD_REALIGN 0x08 ///< Command frame identifier for MAC Coordinator realignment.
|
||||
#define MAC_CMD_GTS_REQUEST 0x09 ///< Command frame identifier for MAC GTS request.
|
||||
|
||||
#define PAN_ID_COMPR_OFFSET 1 ///< Byte containing the PAN ID compression bit (+1 for the frame length byte).
|
||||
#define PAN_ID_COMPR_MASK 0x40 ///< PAN ID compression bit.
|
||||
#define PAN_ID_COMPR_OFFSET 1 ///< Byte containing the PAN ID compression bit (+1 for the frame length byte).
|
||||
#define PAN_ID_COMPR_MASK 0x40 ///< PAN ID compression bit.
|
||||
|
||||
#define PAN_ID_OFFSET 4 ///< Offset of PAN ID in the Data frame (+1 for the frame length byte).
|
||||
#define PAN_ID_OFFSET 4 ///< Offset of PAN ID in the Data frame (+1 for the frame length byte).
|
||||
|
||||
#define PHR_OFFSET 0 ///< Offset of the PHY header in a frame.
|
||||
#define PHR_OFFSET 0 ///< Offset of the PHY header in a frame.
|
||||
|
||||
#define SECURITY_ENABLED_OFFSET 1 ///< Byte containing the Security Enabled bit.
|
||||
#define SECURITY_ENABLED_BIT 0x08 ///< Bits containing the Security Enabled field.
|
||||
#define SECURITY_LEVEL_MASK 0x07 ///< Mask of bits containing the Security level field.
|
||||
#define SECURITY_LEVEL_MIC_32 0x01 ///< Bits containing the 32-bit Message Integrity Code (0b001).
|
||||
#define SECURITY_LEVEL_MIC_64 0x02 ///< Bits containing the 64-bit Message Integrity Code (0b010).
|
||||
#define SECURITY_LEVEL_MIC_128 0x03 ///< Bits containing the 128-bit Message Integrity Code (0b011).
|
||||
#define SECURITY_LEVEL_ENC_MIC_32 0x05 ///< Bits containing the 32-bit Encrypted Message Integrity Code (0b101).
|
||||
#define SECURITY_LEVEL_ENC_MIC_64 0x06 ///< Bits containing the 64-bit Encrypted Message Integrity Code (0b110).
|
||||
#define SECURITY_LEVEL_ENC_MIC_128 0x07 ///< Bits containing the 128-bit Encrypted Message Integrity Code (0b111).
|
||||
#define SECURITY_ENABLED_OFFSET 1 ///< Byte containing the Security Enabled bit.
|
||||
#define SECURITY_ENABLED_BIT 0x08 ///< Bits containing the Security Enabled field.
|
||||
#define SECURITY_LEVEL_MASK 0x07 ///< Mask of bits containing the Security level field.
|
||||
#define SECURITY_LEVEL_MIC_32 0x01 ///< Bits containing the 32-bit Message Integrity Code (0b001).
|
||||
#define SECURITY_LEVEL_MIC_64 0x02 ///< Bits containing the 64-bit Message Integrity Code (0b010).
|
||||
#define SECURITY_LEVEL_MIC_128 0x03 ///< Bits containing the 128-bit Message Integrity Code (0b011).
|
||||
#define SECURITY_LEVEL_ENC_MIC_32 0x05 ///< Bits containing the 32-bit Encrypted Message Integrity Code (0b101).
|
||||
#define SECURITY_LEVEL_ENC_MIC_64 0x06 ///< Bits containing the 64-bit Encrypted Message Integrity Code (0b110).
|
||||
#define SECURITY_LEVEL_ENC_MIC_128 0x07 ///< Bits containing the 128-bit Encrypted Message Integrity Code (0b111).
|
||||
|
||||
#define SRC_ADDR_TYPE_EXTENDED 0xc0 ///< Bits containing the extended source address type.
|
||||
#define SRC_ADDR_TYPE_NONE 0x00 ///< Bits containing a not-present source address type.
|
||||
#define SRC_ADDR_TYPE_MASK 0xc0 ///< Mask of bits containing the source address type.
|
||||
#define SRC_ADDR_TYPE_OFFSET 2 ///< Byte containing the source address type (+1 for the frame length byte).
|
||||
#define SRC_ADDR_TYPE_SHORT 0x80 ///< Bits containing the short source address type.
|
||||
#define SRC_ADDR_TYPE_EXTENDED 0xc0 ///< Bits containing the extended source address type.
|
||||
#define SRC_ADDR_TYPE_NONE 0x00 ///< Bits containing a not-present source address type.
|
||||
#define SRC_ADDR_TYPE_MASK 0xc0 ///< Mask of bits containing the source address type.
|
||||
#define SRC_ADDR_TYPE_OFFSET 2 ///< Byte containing the source address type (+1 for the frame length byte).
|
||||
#define SRC_ADDR_TYPE_SHORT 0x80 ///< Bits containing the short source address type.
|
||||
|
||||
#define SRC_ADDR_OFFSET_SHORT_DST 8 ///< Offset of the source address in the Data frame if the destination address is short.
|
||||
#define SRC_ADDR_OFFSET_EXTENDED_DST 14 ///< Offset of the source address in the Data frame if the destination address is extended.
|
||||
#define SRC_ADDR_OFFSET_SHORT_DST 8 ///< Offset of the source address in the Data frame if the destination address is short.
|
||||
#define SRC_ADDR_OFFSET_EXTENDED_DST 14 ///< Offset of the source address in the Data frame if the destination address is extended.
|
||||
|
||||
#define DSN_SIZE 1 ///< Size of the Sequence Number field.
|
||||
#define FCF_SIZE 2 ///< Size of the FCF field.
|
||||
#define FCS_SIZE 2 ///< Size of the FCS field.
|
||||
#define FRAME_COUNTER_SIZE 4 ///< Size of the Frame Counter field.
|
||||
#define IE_HEADER_SIZE 4 ///< Size of the obligatory IE Header field elements, including the header termination.
|
||||
#define IMM_ACK_LENGTH 5 ///< Length of the ACK frame.
|
||||
#define KEY_ID_MODE_1_SIZE 1 ///< Size of the 0x01 Key Identifier Mode field.
|
||||
#define KEY_ID_MODE_2_SIZE 5 ///< Size of the 0x10 Key Identifier Mode field.
|
||||
#define KEY_ID_MODE_3_SIZE 9 ///< Size of the 0x11 Key Identifier Mode field.
|
||||
#define MAX_PACKET_SIZE 127 ///< Maximum size of the radio packet.
|
||||
#define MIC_32_SIZE 4 ///< Size of MIC with the MIC-32 and ENC-MIC-32 security attributes.
|
||||
#define MIC_64_SIZE 8 ///< Size of MIC with the MIC-64 and ENC-MIC-64 security attributes.
|
||||
#define MIC_128_SIZE 16 ///< Size of MIC with the MIC-128 and ENC-MIC-128 security attributes.
|
||||
#define PAN_ID_SIZE 2 ///< Size of the PAN ID.
|
||||
#define PHR_SIZE 1 ///< Size of the PHR field.
|
||||
#define SECURITY_CONTROL_SIZE 1 ///< Size of the Security Control field.
|
||||
#define DSN_SIZE 1 ///< Size of the Sequence Number field.
|
||||
#define FCF_SIZE 2 ///< Size of the FCF field.
|
||||
#define FCS_SIZE 2 ///< Size of the FCS field.
|
||||
#define FRAME_COUNTER_SIZE 4 ///< Size of the Frame Counter field.
|
||||
#define IE_HEADER_SIZE 4 ///< Size of the obligatory IE Header field elements, including the header termination.
|
||||
#define IMM_ACK_LENGTH 5 ///< Length of the ACK frame.
|
||||
#define KEY_ID_MODE_1_SIZE 1 ///< Size of the 0x01 Key Identifier Mode field.
|
||||
#define KEY_ID_MODE_2_SIZE 5 ///< Size of the 0x10 Key Identifier Mode field.
|
||||
#define KEY_ID_MODE_3_SIZE 9 ///< Size of the 0x11 Key Identifier Mode field.
|
||||
#define MAX_PACKET_SIZE 127 ///< Maximum size of the radio packet.
|
||||
#define MIC_32_SIZE 4 ///< Size of MIC with the MIC-32 and ENC-MIC-32 security attributes.
|
||||
#define MIC_64_SIZE 8 ///< Size of MIC with the MIC-64 and ENC-MIC-64 security attributes.
|
||||
#define MIC_128_SIZE 16 ///< Size of MIC with the MIC-128 and ENC-MIC-128 security attributes.
|
||||
#define PAN_ID_SIZE 2 ///< Size of the PAN ID.
|
||||
#define PHR_SIZE 1 ///< Size of the PHR field.
|
||||
#define SECURITY_CONTROL_SIZE 1 ///< Size of the Security Control field.
|
||||
|
||||
#define EXTENDED_ADDRESS_SIZE 8 ///< Size of the Extended Mac Address.
|
||||
#define SHORT_ADDRESS_SIZE 2 ///< Size of the Short Mac Address.
|
||||
#define EXTENDED_ADDRESS_SIZE 8 ///< Size of the Extended Mac Address.
|
||||
#define SHORT_ADDRESS_SIZE 2 ///< Size of the Short Mac Address.
|
||||
|
||||
#define TURNAROUND_TIME 192UL ///< RX-to-TX or TX-to-RX turnaround time (aTurnaroundTime), in microseconds (us).
|
||||
#define CCA_TIME 128UL ///< Time required to perform CCA detection (aCcaTime), in microseconds (us).
|
||||
#define UNIT_BACKOFF_PERIOD (TURNAROUND_TIME + CCA_TIME) ///< Number of symbols in the basic time period used by CSMA-CA algorithm (aUnitBackoffPeriod), in (us).
|
||||
#define TURNAROUND_TIME 192UL ///< RX-to-TX or TX-to-RX turnaround time (aTurnaroundTime), in microseconds (us).
|
||||
#define CCA_TIME 128UL ///< Time required to perform CCA detection (aCcaTime), in microseconds (us).
|
||||
#define UNIT_BACKOFF_PERIOD (TURNAROUND_TIME + CCA_TIME) ///< Number of symbols in the basic time period used by CSMA-CA algorithm (aUnitBackoffPeriod), in (us).
|
||||
|
||||
#define PHY_US_PER_SYMBOL 16 ///< Duration of a single symbol in microseconds (us).
|
||||
#define PHY_SYMBOLS_PER_OCTET 2 ///< Number of symbols in a single byte (octet).
|
||||
#define PHY_SHR_SYMBOLS 10 ///< Number of symbols in the Synchronization Header (SHR).
|
||||
#define PHY_US_PER_SYMBOL 16 ///< Duration of a single symbol in microseconds (us).
|
||||
#define PHY_SYMBOLS_PER_OCTET 2 ///< Number of symbols in a single byte (octet).
|
||||
#define PHY_SHR_SYMBOLS 10 ///< Number of symbols in the Synchronization Header (SHR).
|
||||
|
||||
#define ED_RESULT_MAX 0xff ///< Maximal ED result.
|
||||
#define ED_RESULT_MAX 0xff ///< Maximal ED result.
|
||||
|
||||
#define BROADCAST_ADDRESS ((uint8_t[SHORT_ADDRESS_SIZE]) {0xff, 0xff}) ///< Broadcast short address.
|
||||
#define BROADCAST_ADDRESS ((uint8_t[SHORT_ADDRESS_SIZE]) {0xff, 0xff}) ///< Broadcast short address.
|
||||
|
||||
#define MIN_SIFS_PERIOD_US 192 ///< Minimum Short IFS period default value in us.
|
||||
#define MIN_LIFS_PERIOD_US 640 ///< Minimum Long IFS period default value in us.
|
||||
#define MAX_SIFS_FRAME_SIZE 18 ///< Maximum frame length which can be followed by the Short Interframe Space.
|
||||
#define MIN_SIFS_PERIOD_US 192 ///< Minimum Short IFS period default value in us.
|
||||
#define MIN_LIFS_PERIOD_US 640 ///< Minimum Long IFS period default value in us.
|
||||
#define MAX_SIFS_FRAME_SIZE 18 ///< Maximum frame length which can be followed by the Short Interframe Space.
|
||||
|
||||
#define NRF_802154_RESERVED_CSMACA_ID (UINT32_MAX - 2) ///< Delayed timeslot identifier reserved for CSMA/CA procedure.
|
||||
#define NRF_802154_RESERVED_DTX_ID (UINT32_MAX - 3) ///< Delayed timeslot identifier reserved for delayed transmissions.
|
||||
|
||||
typedef enum
|
||||
{
|
||||
|
|
|
@ -80,7 +80,8 @@ static void timeout_timer_fired(void * p_context)
|
|||
if (nrf_802154_request_receive(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_ACK_TIMEOUT,
|
||||
notify_tx_error,
|
||||
false))
|
||||
false,
|
||||
NRF_802154_RESERVED_IMM_RX_WINDOW_ID))
|
||||
{
|
||||
m_procedure_is_active = false;
|
||||
}
|
||||
|
|
|
@ -96,12 +96,15 @@ static bool procedure_is_running(void)
|
|||
*/
|
||||
static void procedure_stop(void)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
if (procedure_is_running())
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
nrf_802154_rsch_delayed_timeslot_cancel(RSCH_DLY_CSMACA);
|
||||
m_is_running = false;
|
||||
nrf_802154_rsch_delayed_timeslot_cancel(NRF_802154_RESERVED_CSMACA_ID);
|
||||
m_is_running = false;
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
}
|
||||
|
||||
static void priority_leverage(void)
|
||||
|
@ -116,7 +119,8 @@ static void priority_leverage(void)
|
|||
if (first_transmit_attempt && coex_requires_boosted_prio)
|
||||
{
|
||||
// It should always be possible to update this timeslot's priority here
|
||||
if (!nrf_802154_rsch_delayed_timeslot_priority_update(RSCH_DLY_CSMACA, RSCH_PRIO_TX))
|
||||
if (!nrf_802154_rsch_delayed_timeslot_priority_update(NRF_802154_RESERVED_CSMACA_ID,
|
||||
RSCH_PRIO_TX))
|
||||
{
|
||||
assert(false);
|
||||
}
|
||||
|
@ -157,6 +161,7 @@ static void notify_busy_channel(bool result)
|
|||
*/
|
||||
static void frame_transmit(rsch_dly_ts_id_t dly_ts_id)
|
||||
{
|
||||
assert(dly_ts_id == NRF_802154_RESERVED_CSMACA_ID);
|
||||
(void)dly_ts_id;
|
||||
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
@ -192,9 +197,10 @@ static void random_backoff_start(void)
|
|||
{
|
||||
.t0 = nrf_802154_timer_sched_time_get(),
|
||||
.dt = backoff_periods * UNIT_BACKOFF_PERIOD,
|
||||
.id = RSCH_DLY_CSMACA,
|
||||
.op = RSCH_DLY_TS_OP_CSMACA,
|
||||
.type = RSCH_DLY_TS_TYPE_RELAXED,
|
||||
.started_callback = frame_transmit,
|
||||
.id = NRF_802154_RESERVED_CSMACA_ID,
|
||||
};
|
||||
|
||||
switch (nrf_802154_pib_coex_tx_request_mode_get())
|
||||
|
@ -219,6 +225,14 @@ static void random_backoff_start(void)
|
|||
break;
|
||||
}
|
||||
|
||||
if (m_nb != 0)
|
||||
{
|
||||
// Since CSMA/CA always requests delayed timeslot of type RSCH_DLY_TS_TYPE_RELAXED,
|
||||
// it must be cancelled explicitly, so that the slot is released and available
|
||||
// for the upcoming request.
|
||||
nrf_802154_rsch_delayed_timeslot_cancel(NRF_802154_RESERVED_CSMACA_ID);
|
||||
}
|
||||
|
||||
// Delayed timeslot with these parameters should always be scheduled
|
||||
if (!nrf_802154_rsch_delayed_timeslot_request(&backoff_ts_param))
|
||||
{
|
||||
|
|
|
@ -53,7 +53,9 @@
|
|||
#include "nrf_802154_notification.h"
|
||||
#include "nrf_802154_pib.h"
|
||||
#include "nrf_802154_procedures_duration.h"
|
||||
#include "nrf_802154_queue.h"
|
||||
#include "nrf_802154_request.h"
|
||||
#include "nrf_802154_utils.h"
|
||||
#include "rsch/nrf_802154_rsch.h"
|
||||
#include "timer/nrf_802154_timer_sched.h"
|
||||
|
||||
|
@ -88,110 +90,293 @@ typedef struct
|
|||
} delayed_rx_frame_data_t;
|
||||
|
||||
/**
|
||||
* @brief TX delayed operation configuration.
|
||||
* @brief RX delayed operation data.
|
||||
*/
|
||||
static const uint8_t * mp_tx_data; ///< Pointer to a buffer containing PHR and PSDU of the frame requested to be transmitted.
|
||||
static bool m_tx_cca; ///< If CCA should be performed prior to transmission.
|
||||
static uint8_t m_tx_channel; ///< Channel number on which transmission should be performed.
|
||||
typedef struct
|
||||
{
|
||||
nrf_802154_timer_t timeout_timer; ///< Timer for delayed RX timeout handling.
|
||||
volatile delayed_rx_frame_data_t extension_frame; ///< Data of frame that caused extension of RX window.
|
||||
uint8_t channel; ///< Channel number on which reception should be performed.
|
||||
} dly_rx_data_t;
|
||||
|
||||
/**
|
||||
* @brief RX delayed operation configuration.
|
||||
* @brief TX delayed operation data.
|
||||
*/
|
||||
static nrf_802154_timer_t m_timeout_timer; ///< Timer for delayed RX timeout handling.
|
||||
static uint8_t m_rx_channel; ///< Channel number on which reception should be performed.
|
||||
typedef struct
|
||||
{
|
||||
const uint8_t * p_data; ///< Pointer to a buffer containing PHR and PSDU of the frame requested to be transmitted.
|
||||
bool cca; ///< If CCA should be performed prior to transmission.
|
||||
uint8_t channel; ///< Channel number on which transmission should be performed.
|
||||
} dly_tx_data_t;
|
||||
|
||||
/**
|
||||
* @brief State of delayed operations.
|
||||
* @brief Delayed operation data.
|
||||
*/
|
||||
static volatile delayed_trx_op_state_t m_dly_op_state[RSCH_DLY_TS_NUM];
|
||||
typedef struct
|
||||
{
|
||||
volatile delayed_trx_op_state_t state; ///< State of the delayed timeslot.
|
||||
rsch_dly_ts_id_t id; ///< Identifier of the delayed timeslot.
|
||||
rsch_dly_ts_op_t op; ///< Type of delayed operation to be performed.
|
||||
|
||||
union
|
||||
{
|
||||
dly_tx_data_t tx; ///< Data specific for delayed transmission.
|
||||
dly_rx_data_t rx; ///< Data specific for delayed reception.
|
||||
};
|
||||
} dly_op_data_t;
|
||||
|
||||
/**
|
||||
* @brief RX delayed operation frame data.
|
||||
* @brief Array of slots for RX delayed operations.
|
||||
*/
|
||||
static volatile delayed_rx_frame_data_t m_dly_rx_frame;
|
||||
static dly_op_data_t m_dly_rx_data[NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS];
|
||||
|
||||
/**
|
||||
* @brief Array of slots for TX delayed operations.
|
||||
*/
|
||||
static dly_op_data_t m_dly_tx_data[NRF_802154_RSCH_DLY_TS_OP_DTX_SLOTS];
|
||||
|
||||
/**
|
||||
* @brief Queue of RX delayed operations IDs to be processed.
|
||||
*/
|
||||
static nrf_802154_queue_t m_dly_rx_id_q;
|
||||
|
||||
/**
|
||||
* @brief Storage for RX delayed operations ID queue.
|
||||
*/
|
||||
static dly_op_data_t * m_dly_rx_id_q_mem[NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS];
|
||||
|
||||
/**
|
||||
* @brief Search for a RX delayed operation with given ID.
|
||||
*
|
||||
* @param[in] id Identifier to search for.
|
||||
*
|
||||
* @return Pointer to matching slot.
|
||||
*/
|
||||
static dly_op_data_t * dly_rx_data_by_id_search(rsch_dly_ts_id_t id)
|
||||
{
|
||||
dly_op_data_t * p_dly_op_data = NULL;
|
||||
|
||||
for (uint32_t i = 0; i < sizeof(m_dly_rx_data) / sizeof(m_dly_rx_data[0]); i++)
|
||||
{
|
||||
if (m_dly_rx_data[i].id == id)
|
||||
{
|
||||
// Slot with a matching identifier found
|
||||
if ((p_dly_op_data == NULL))
|
||||
{
|
||||
// It's the first matching slot found
|
||||
p_dly_op_data = &m_dly_rx_data[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
// There's already been a matching slot. We expect all active slots to have unique
|
||||
// IDs and all inactive slots to have their IDs set to NRF_802154_RESERVED_INVALID_ID.
|
||||
// If we ended up here then either we're searching for invalid ID or the IDs assigned
|
||||
// to active slots aren't unique. Either way - assert.
|
||||
assert(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return p_dly_op_data;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Search for a TX delayed operation with given ID.
|
||||
*
|
||||
* @param[in] id Identifier to search for.
|
||||
*
|
||||
* @return Pointer to matching slot.
|
||||
*/
|
||||
static dly_op_data_t * dly_tx_data_by_id_search(rsch_dly_ts_id_t id)
|
||||
{
|
||||
// Note that this function only supports a single slot.
|
||||
assert(id == m_dly_tx_data[0].id);
|
||||
|
||||
return &m_dly_tx_data[0];
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check if there are any slots available.
|
||||
*
|
||||
* @param[in] p_dly_op_data_pool Pool of slots to check.
|
||||
* @param[in] pool_len Total number of elements in the pool.
|
||||
*
|
||||
* @retval true The pool contains free slots.
|
||||
* @retval false There are no available slots in the pool.
|
||||
*/
|
||||
static bool is_dly_ts_slot_available(const dly_op_data_t * p_dly_op_data_pool, uint32_t pool_len)
|
||||
{
|
||||
for (uint32_t i = 0; i < pool_len; i++)
|
||||
{
|
||||
if (p_dly_op_data_pool[i].id == NRF_802154_RESERVED_INVALID_ID)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Retrieve an available slot from a pool.
|
||||
*
|
||||
* @param[inout] p_dly_op_data_pool Pool of slots to allocate from.
|
||||
* @param[in] pool_len Number of elements in the pool.
|
||||
*
|
||||
* @return Pointer to an available slot.
|
||||
*/
|
||||
static dly_op_data_t * available_dly_ts_slot_from_pool_get(
|
||||
dly_op_data_t * p_dly_op_data_pool, uint32_t pool_len)
|
||||
{
|
||||
for (uint32_t i = 0; i < pool_len; i++)
|
||||
{
|
||||
if (p_dly_op_data_pool[i].id == NRF_802154_RESERVED_INVALID_ID)
|
||||
{
|
||||
return &p_dly_op_data_pool[i];
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get a slot for TX delayed operation.
|
||||
*
|
||||
* @return Pointer to a slot.
|
||||
*/
|
||||
static dly_op_data_t * available_dly_tx_slot_get(void)
|
||||
{
|
||||
return available_dly_ts_slot_from_pool_get(
|
||||
m_dly_tx_data,
|
||||
sizeof(m_dly_tx_data) / sizeof(m_dly_tx_data[0]));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get a slot for RX delayed operation.
|
||||
*
|
||||
* @return Pointer to a slot.
|
||||
*/
|
||||
static dly_op_data_t * available_dly_rx_slot_get(void)
|
||||
{
|
||||
return available_dly_ts_slot_from_pool_get(
|
||||
m_dly_rx_data,
|
||||
sizeof(m_dly_rx_data) / sizeof(m_dly_rx_data[0]));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get an ongoing RX delayed operation slot.
|
||||
*
|
||||
* @return Pointer to a slot or NULL if no ongoing RX delayed operations exist at the moment.
|
||||
*/
|
||||
static dly_op_data_t * ongoing_dly_rx_slot_get(void)
|
||||
{
|
||||
dly_op_data_t * p_dly_op_data = NULL;
|
||||
|
||||
for (uint32_t i = 0; i < sizeof(m_dly_rx_data) / sizeof(m_dly_rx_data[0]); i++)
|
||||
{
|
||||
if (m_dly_rx_data[i].state == DELAYED_TRX_OP_STATE_ONGOING)
|
||||
{
|
||||
p_dly_op_data = &m_dly_rx_data[i];
|
||||
}
|
||||
}
|
||||
|
||||
return p_dly_op_data;
|
||||
}
|
||||
|
||||
static void dly_ts_slot_release(dly_op_data_t * p_dly_op_data)
|
||||
{
|
||||
(void)nrf_802154_rsch_delayed_timeslot_cancel(p_dly_op_data->id);
|
||||
|
||||
p_dly_op_data->id = NRF_802154_RESERVED_INVALID_ID;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Atomically push an ID to RX delayed operation ID queue.
|
||||
*
|
||||
* @param[in] id Identifier to be pushed to the queue.
|
||||
*/
|
||||
static void dly_rx_data_atomically_push(dly_op_data_t * p_dly_op_data)
|
||||
{
|
||||
nrf_802154_mcu_critical_state_t mcu_cs;
|
||||
|
||||
nrf_802154_mcu_critical_enter(mcu_cs);
|
||||
|
||||
assert(!nrf_802154_queue_is_full(&m_dly_rx_id_q));
|
||||
|
||||
dly_op_data_t ** pp_op = (dly_op_data_t **)nrf_802154_queue_push_begin(&m_dly_rx_id_q);
|
||||
|
||||
*pp_op = p_dly_op_data;
|
||||
|
||||
nrf_802154_queue_push_commit(&m_dly_rx_id_q);
|
||||
|
||||
nrf_802154_mcu_critical_exit(mcu_cs);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Atomically pop an ID from RX delayed operation ID queue.
|
||||
*
|
||||
* @param[out] p_id Pointer to identifier popped from the queue.
|
||||
*/
|
||||
static dly_op_data_t * dly_rx_data_atomically_pop(void)
|
||||
{
|
||||
nrf_802154_mcu_critical_state_t mcu_cs;
|
||||
|
||||
nrf_802154_mcu_critical_enter(mcu_cs);
|
||||
|
||||
dly_op_data_t ** pp_op = (dly_op_data_t **)nrf_802154_queue_pop_begin(&m_dly_rx_id_q);
|
||||
|
||||
nrf_802154_queue_pop_commit(&m_dly_rx_id_q);
|
||||
|
||||
nrf_802154_mcu_critical_exit(mcu_cs);
|
||||
|
||||
return *pp_op;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set state of a delayed operation.
|
||||
*
|
||||
* @param[in] expected_dly_rx_state Delayed RX current expected state.
|
||||
* @param[in] new_dly_rx_state Delayed RX new state to be set.
|
||||
* @param[in] p_dly_op_data Data of the delayed operation.
|
||||
* @param[in] expected_state Expected delayed operation state prior state transition.
|
||||
* @param[in] new_state Delayed operation state to enter.
|
||||
*
|
||||
* @retval true Successfully set the new state.
|
||||
* @retval false Failed to set the new state.
|
||||
*/
|
||||
static bool dly_rx_state_set(delayed_trx_op_state_t expected_dly_rx_state,
|
||||
delayed_trx_op_state_t new_dly_rx_state)
|
||||
{
|
||||
volatile delayed_trx_op_state_t current_dly_rx_state;
|
||||
|
||||
do
|
||||
{
|
||||
current_dly_rx_state =
|
||||
(delayed_trx_op_state_t)__LDREXB((uint8_t *)&m_dly_op_state[RSCH_DLY_RX]);
|
||||
|
||||
if (current_dly_rx_state != expected_dly_rx_state)
|
||||
{
|
||||
__CLREX();
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
while (__STREXB((uint8_t)new_dly_rx_state, (uint8_t *)&m_dly_op_state[RSCH_DLY_RX]));
|
||||
|
||||
__DMB();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get state of a delayed operation.
|
||||
*
|
||||
* @param[in] dly_ts_id Delayed timeslot ID.
|
||||
*
|
||||
* @retval State of delayed operation.
|
||||
*/
|
||||
static delayed_trx_op_state_t dly_op_state_get(rsch_dly_ts_id_t dly_ts_id)
|
||||
{
|
||||
assert(dly_ts_id < RSCH_DLY_TS_NUM);
|
||||
|
||||
return m_dly_op_state[dly_ts_id];
|
||||
}
|
||||
|
||||
/**
|
||||
* Set state of a delayed operation.
|
||||
*
|
||||
* @param[in] dly_ts_id Delayed timeslot ID.
|
||||
* @param[in] expected_state Expected delayed operation state prior state transition.
|
||||
* @param[in] new_state Delayed operation state to enter.
|
||||
*/
|
||||
static void dly_op_state_set(rsch_dly_ts_id_t dly_ts_id,
|
||||
static bool dly_op_state_set(dly_op_data_t * p_dly_op_data,
|
||||
delayed_trx_op_state_t expected_state,
|
||||
delayed_trx_op_state_t new_state)
|
||||
{
|
||||
assert(new_state < DELAYED_TRX_OP_STATE_NB);
|
||||
|
||||
switch (dly_ts_id)
|
||||
switch (p_dly_op_data->op)
|
||||
{
|
||||
case RSCH_DLY_TX:
|
||||
case RSCH_DLY_TS_OP_DTX:
|
||||
case RSCH_DLY_TS_OP_DRX:
|
||||
{
|
||||
assert(m_dly_op_state[RSCH_DLY_TX] == expected_state);
|
||||
m_dly_op_state[RSCH_DLY_TX] = new_state;
|
||||
break;
|
||||
}
|
||||
volatile delayed_trx_op_state_t current_state;
|
||||
|
||||
case RSCH_DLY_RX:
|
||||
{
|
||||
bool result = dly_rx_state_set(expected_state, new_state);
|
||||
do
|
||||
{
|
||||
current_state = (delayed_trx_op_state_t)__LDREXB((uint8_t *)&p_dly_op_data->state);
|
||||
|
||||
assert(result);
|
||||
(void)result;
|
||||
break;
|
||||
if (current_state != expected_state)
|
||||
{
|
||||
__CLREX();
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
while (__STREXB((uint8_t)new_state, (uint8_t *)&p_dly_op_data->state));
|
||||
|
||||
__DMB();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
default:
|
||||
{
|
||||
assert(false);
|
||||
break;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -199,24 +384,36 @@ static void dly_op_state_set(rsch_dly_ts_id_t dly_ts_id,
|
|||
/**
|
||||
* Start delayed operation.
|
||||
*
|
||||
* @param[in] p_dly_ts_param Parameters of the requested delayed timeslot.
|
||||
* @param[in] p_dly_ts_param Parameters of the requested delayed timeslot.
|
||||
* @param[inout] p_dly_op_data Data of the delayed operation.
|
||||
*/
|
||||
static bool dly_op_request(const rsch_dly_ts_param_t * p_dly_ts_param)
|
||||
static bool dly_op_request(const rsch_dly_ts_param_t * p_dly_ts_param,
|
||||
dly_op_data_t * p_dly_op_data)
|
||||
{
|
||||
// Set PENDING state before timeslot request, in case timeslot starts
|
||||
// immediately and interrupts current function execution.
|
||||
dly_op_state_set(p_dly_ts_param->id, DELAYED_TRX_OP_STATE_STOPPED,
|
||||
DELAYED_TRX_OP_STATE_PENDING);
|
||||
bool state_set = dly_op_state_set(
|
||||
p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_STOPPED,
|
||||
DELAYED_TRX_OP_STATE_PENDING);
|
||||
|
||||
assert(state_set);
|
||||
|
||||
bool result = nrf_802154_rsch_delayed_timeslot_request(p_dly_ts_param);
|
||||
|
||||
if (!result)
|
||||
{
|
||||
dly_op_state_set(p_dly_ts_param->id,
|
||||
DELAYED_TRX_OP_STATE_PENDING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED);
|
||||
state_set = dly_op_state_set(
|
||||
p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_PENDING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED);
|
||||
|
||||
// In case of failure, the value of this parameter is undefined. Reset it
|
||||
p_dly_op_data->id = NRF_802154_RESERVED_INVALID_ID;
|
||||
}
|
||||
|
||||
(void)state_set;
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -227,42 +424,46 @@ static bool dly_op_request(const rsch_dly_ts_param_t * p_dly_ts_param)
|
|||
*/
|
||||
static void notify_rx_timeout(void * p_context)
|
||||
{
|
||||
(void)p_context;
|
||||
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
assert(dly_op_state_get(RSCH_DLY_RX) != DELAYED_TRX_OP_STATE_PENDING);
|
||||
dly_op_data_t * p_dly_op_data = (dly_op_data_t *)p_context;
|
||||
|
||||
if (dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_ONGOING)
|
||||
assert(p_dly_op_data->state != DELAYED_TRX_OP_STATE_PENDING);
|
||||
|
||||
if (p_dly_op_data->state == DELAYED_TRX_OP_STATE_ONGOING)
|
||||
{
|
||||
uint32_t now = nrf_802154_timer_sched_time_get();
|
||||
uint32_t sof_timestamp = m_dly_rx_frame.sof_timestamp;
|
||||
uint32_t sof_timestamp = p_dly_op_data->rx.extension_frame.sof_timestamp;
|
||||
|
||||
// Make sure that the timestamp has been latched safely. If frame reception preempts the code
|
||||
// after executing this line, the RX window will not be extended.
|
||||
__DMB();
|
||||
uint8_t psdu_length = m_dly_rx_frame.psdu_length;
|
||||
bool ack_requested = m_dly_rx_frame.ack_requested;
|
||||
uint8_t psdu_length = p_dly_op_data->rx.extension_frame.psdu_length;
|
||||
bool ack_requested = p_dly_op_data->rx.extension_frame.ack_requested;
|
||||
uint32_t frame_length = nrf_802154_rx_duration_get(psdu_length, ack_requested);
|
||||
|
||||
if (nrf_802154_timer_sched_time_is_in_future(now, sof_timestamp, frame_length))
|
||||
{
|
||||
// @TODO protect against infinite extensions - allow only one timer extension
|
||||
m_timeout_timer.t0 = sof_timestamp;
|
||||
m_timeout_timer.dt = frame_length;
|
||||
p_dly_op_data->rx.timeout_timer.t0 = sof_timestamp;
|
||||
p_dly_op_data->rx.timeout_timer.dt = frame_length;
|
||||
|
||||
nrf_802154_timer_sched_add(&m_timeout_timer, true);
|
||||
nrf_802154_timer_sched_add(&p_dly_op_data->rx.timeout_timer, true);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dly_rx_state_set(DELAYED_TRX_OP_STATE_ONGOING, DELAYED_TRX_OP_STATE_STOPPED))
|
||||
if (dly_op_state_set(p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_ONGOING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED))
|
||||
{
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_TIMEOUT);
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_TIMEOUT,
|
||||
p_dly_op_data->id);
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
}
|
||||
|
||||
// even if the set operation failed, the delayed RX state
|
||||
// should be set to STOPPED from other context anyway
|
||||
assert(dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_STOPPED);
|
||||
assert(p_dly_op_data->state == DELAYED_TRX_OP_STATE_STOPPED);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -276,17 +477,25 @@ static void notify_rx_timeout(void * p_context)
|
|||
*/
|
||||
static void dly_tx_result_notify(bool result)
|
||||
{
|
||||
(void)result;
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
// Currently there's only a single delayed transmission possible at a time
|
||||
dly_op_data_t * p_dly_op_data = &m_dly_tx_data[0];
|
||||
|
||||
// To avoid attaching to every possible transmit hook, in order to be able
|
||||
// to switch from ONGOING to STOPPED state, ONGOING state is not used at all
|
||||
// and state is changed to STOPPED right after transmit request.
|
||||
m_dly_op_state[RSCH_DLY_TX] = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
p_dly_op_data->state = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
|
||||
if (!result)
|
||||
{
|
||||
nrf_802154_notify_transmit_failed(mp_tx_data, NRF_802154_TX_ERROR_TIMESLOT_DENIED);
|
||||
nrf_802154_notify_transmit_failed(p_dly_op_data->tx.p_data,
|
||||
NRF_802154_TX_ERROR_TIMESLOT_DENIED);
|
||||
}
|
||||
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -296,27 +505,122 @@ static void dly_tx_result_notify(bool result)
|
|||
*/
|
||||
static void dly_rx_result_notify(bool result)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
dly_op_data_t * p_dly_op_data = dly_rx_data_atomically_pop();
|
||||
|
||||
if (p_dly_op_data == NULL)
|
||||
{
|
||||
assert(false);
|
||||
return;
|
||||
}
|
||||
|
||||
if (result)
|
||||
{
|
||||
uint32_t now;
|
||||
bool state_set;
|
||||
uint32_t now;
|
||||
dly_op_data_t * p_parallel_ongoing_dly_op_data = ongoing_dly_rx_slot_get();
|
||||
|
||||
dly_op_state_set(RSCH_DLY_RX, DELAYED_TRX_OP_STATE_PENDING, DELAYED_TRX_OP_STATE_ONGOING);
|
||||
if (p_parallel_ongoing_dly_op_data != NULL)
|
||||
{
|
||||
// There's another ongoing delayed RX operation. Close it now
|
||||
state_set = dly_op_state_set(p_parallel_ongoing_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_ONGOING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED);
|
||||
|
||||
assert(state_set);
|
||||
(void)state_set;
|
||||
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_ABORTED,
|
||||
p_parallel_ongoing_dly_op_data->id);
|
||||
dly_ts_slot_release(p_parallel_ongoing_dly_op_data);
|
||||
}
|
||||
|
||||
state_set = dly_op_state_set(
|
||||
p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_PENDING,
|
||||
DELAYED_TRX_OP_STATE_ONGOING);
|
||||
|
||||
assert(state_set);
|
||||
(void)state_set;
|
||||
|
||||
now = nrf_802154_timer_sched_time_get();
|
||||
|
||||
m_timeout_timer.t0 = now;
|
||||
m_dly_rx_frame.sof_timestamp = now;
|
||||
m_dly_rx_frame.psdu_length = 0;
|
||||
m_dly_rx_frame.ack_requested = false;
|
||||
p_dly_op_data->rx.timeout_timer.t0 = now;
|
||||
p_dly_op_data->rx.timeout_timer.p_context = p_dly_op_data;
|
||||
p_dly_op_data->rx.extension_frame.sof_timestamp = now;
|
||||
p_dly_op_data->rx.extension_frame.psdu_length = 0;
|
||||
p_dly_op_data->rx.extension_frame.ack_requested = false;
|
||||
|
||||
nrf_802154_timer_sched_add(&m_timeout_timer, true);
|
||||
nrf_802154_timer_sched_add(&p_dly_op_data->rx.timeout_timer, true);
|
||||
}
|
||||
else
|
||||
{
|
||||
dly_op_state_set(RSCH_DLY_RX, DELAYED_TRX_OP_STATE_PENDING, DELAYED_TRX_OP_STATE_STOPPED);
|
||||
bool state_set = dly_op_state_set(
|
||||
p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_PENDING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED);
|
||||
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_TIMESLOT_DENIED);
|
||||
assert(state_set);
|
||||
(void)state_set;
|
||||
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_TIMESLOT_DENIED,
|
||||
p_dly_op_data->id);
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
}
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
|
||||
static void transmit_attempt(dly_op_data_t * p_dly_op_data)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
// No need to enqueue transmit attempts. Proceed to transmission immediately
|
||||
nrf_802154_pib_channel_set(p_dly_op_data->tx.channel);
|
||||
|
||||
if (nrf_802154_request_channel_update(REQ_ORIG_DELAYED_TRX))
|
||||
{
|
||||
(void)nrf_802154_request_transmit(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_DELAYED_TRX,
|
||||
p_dly_op_data->tx.p_data,
|
||||
p_dly_op_data->tx.cca,
|
||||
true,
|
||||
dly_tx_result_notify);
|
||||
}
|
||||
else
|
||||
{
|
||||
dly_tx_result_notify(false);
|
||||
}
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
|
||||
static void receive_attempt(dly_op_data_t * p_dly_op_data)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
// This function is expected to result in calling @ref dly_rx_result_notify.
|
||||
// In order for that function to differentiate between different delayed RX
|
||||
// windows, we atomically insert the ID of the current delayed RX into a FIFO queue.
|
||||
dly_rx_data_atomically_push(p_dly_op_data);
|
||||
|
||||
nrf_802154_pib_channel_set(p_dly_op_data->rx.channel);
|
||||
|
||||
if (nrf_802154_request_channel_update(REQ_ORIG_DELAYED_TRX))
|
||||
{
|
||||
(void)nrf_802154_request_receive(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_DELAYED_TRX,
|
||||
dly_rx_result_notify,
|
||||
true,
|
||||
p_dly_op_data->id);
|
||||
}
|
||||
else
|
||||
{
|
||||
dly_rx_result_notify(false);
|
||||
}
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -328,32 +632,23 @@ static void tx_timeslot_started_callback(rsch_dly_ts_id_t dly_ts_id)
|
|||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
assert(dly_ts_id == RSCH_DLY_TX);
|
||||
dly_op_data_t * p_dly_op_data = dly_tx_data_by_id_search(dly_ts_id);
|
||||
|
||||
switch (dly_op_state_get(dly_ts_id))
|
||||
if (p_dly_op_data == NULL)
|
||||
{
|
||||
assert(false);
|
||||
return;
|
||||
}
|
||||
|
||||
switch (p_dly_op_data->state)
|
||||
{
|
||||
case DELAYED_TRX_OP_STATE_PENDING:
|
||||
{
|
||||
nrf_802154_pib_channel_set(m_tx_channel);
|
||||
|
||||
if (nrf_802154_request_channel_update())
|
||||
{
|
||||
(void)nrf_802154_request_transmit(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_DELAYED_TRX,
|
||||
mp_tx_data,
|
||||
m_tx_cca,
|
||||
true,
|
||||
dly_tx_result_notify);
|
||||
}
|
||||
else
|
||||
{
|
||||
dly_tx_result_notify(false);
|
||||
}
|
||||
|
||||
transmit_attempt(p_dly_op_data);
|
||||
break;
|
||||
}
|
||||
|
||||
case DELAYED_TRX_OP_STATE_STOPPED:
|
||||
// TODO: is it certain that p_dly_op_data->id has a valid value here?
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
@ -373,30 +668,23 @@ static void rx_timeslot_started_callback(rsch_dly_ts_id_t dly_ts_id)
|
|||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
assert(dly_ts_id == RSCH_DLY_RX);
|
||||
dly_op_data_t * p_dly_op_data = dly_rx_data_by_id_search(dly_ts_id);
|
||||
|
||||
switch (dly_op_state_get(dly_ts_id))
|
||||
if (p_dly_op_data == NULL)
|
||||
{
|
||||
assert(false);
|
||||
return;
|
||||
}
|
||||
|
||||
switch (p_dly_op_data->state)
|
||||
{
|
||||
case DELAYED_TRX_OP_STATE_PENDING:
|
||||
{
|
||||
nrf_802154_pib_channel_set(m_rx_channel);
|
||||
|
||||
if (nrf_802154_request_channel_update())
|
||||
{
|
||||
(void)nrf_802154_request_receive(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_DELAYED_TRX,
|
||||
dly_rx_result_notify,
|
||||
true);
|
||||
}
|
||||
else
|
||||
{
|
||||
dly_rx_result_notify(false);
|
||||
}
|
||||
|
||||
receive_attempt(p_dly_op_data);
|
||||
break;
|
||||
}
|
||||
|
||||
case DELAYED_TRX_OP_STATE_STOPPED:
|
||||
// TODO: is it certain that p_dly_op_data->id has a valid value here?
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
@ -407,13 +695,44 @@ static void rx_timeslot_started_callback(rsch_dly_ts_id_t dly_ts_id)
|
|||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
}
|
||||
|
||||
#ifdef TEST
|
||||
#include "string.h"
|
||||
void nrf_802154_delayed_trx_module_reset(void)
|
||||
{
|
||||
memset(m_dly_rx_data, 0, sizeof(m_dly_rx_data));
|
||||
memset(m_dly_tx_data, 0, sizeof(m_dly_tx_data));
|
||||
memset(&m_dly_rx_id_q, 0, sizeof(m_dly_rx_id_q));
|
||||
memset(m_dly_rx_id_q_mem, 0, sizeof(m_dly_rx_id_q_mem));
|
||||
}
|
||||
|
||||
#endif // TEST
|
||||
|
||||
void nrf_802154_delayed_trx_init(void)
|
||||
{
|
||||
nrf_802154_queue_init(&m_dly_rx_id_q,
|
||||
m_dly_rx_id_q_mem,
|
||||
sizeof(m_dly_rx_id_q_mem),
|
||||
sizeof(m_dly_rx_id_q_mem[0]));
|
||||
|
||||
for (uint32_t i = 0; i < sizeof(m_dly_rx_data) / sizeof(m_dly_rx_data[0]); i++)
|
||||
{
|
||||
m_dly_rx_data[i].id = NRF_802154_RESERVED_INVALID_ID;
|
||||
}
|
||||
|
||||
for (uint32_t i = 0; i < sizeof(m_dly_tx_data) / sizeof(m_dly_tx_data[0]); i++)
|
||||
{
|
||||
m_dly_tx_data[i].id = NRF_802154_RESERVED_INVALID_ID;
|
||||
}
|
||||
}
|
||||
|
||||
bool nrf_802154_delayed_trx_transmit(const uint8_t * p_data,
|
||||
bool cca,
|
||||
uint32_t t0,
|
||||
uint32_t dt,
|
||||
uint8_t channel)
|
||||
{
|
||||
bool result = dly_op_state_get(RSCH_DLY_TX) == DELAYED_TRX_OP_STATE_STOPPED;
|
||||
bool result = is_dly_ts_slot_available(m_dly_tx_data,
|
||||
sizeof(m_dly_tx_data) / sizeof(m_dly_tx_data[0]));
|
||||
|
||||
if (result)
|
||||
{
|
||||
|
@ -425,21 +744,27 @@ bool nrf_802154_delayed_trx_transmit(const uint8_t * p_data,
|
|||
dt -= nrf_802154_cca_before_tx_duration_get();
|
||||
}
|
||||
|
||||
mp_tx_data = p_data;
|
||||
m_tx_cca = cca;
|
||||
m_tx_channel = channel;
|
||||
dly_op_data_t * p_dly_tx_data = available_dly_tx_slot_get();
|
||||
|
||||
p_dly_tx_data->op = RSCH_DLY_TS_OP_DTX;
|
||||
|
||||
p_dly_tx_data->tx.p_data = p_data;
|
||||
p_dly_tx_data->tx.cca = cca;
|
||||
p_dly_tx_data->tx.channel = channel;
|
||||
p_dly_tx_data->id = NRF_802154_RESERVED_DTX_ID;
|
||||
|
||||
rsch_dly_ts_param_t dly_ts_param =
|
||||
{
|
||||
.t0 = t0,
|
||||
.dt = dt,
|
||||
.prio = RSCH_PRIO_TX,
|
||||
.id = RSCH_DLY_TX,
|
||||
.op = RSCH_DLY_TS_OP_DTX,
|
||||
.type = RSCH_DLY_TS_TYPE_PRECISE,
|
||||
.started_callback = tx_timeslot_started_callback,
|
||||
.id = NRF_802154_RESERVED_DTX_ID,
|
||||
};
|
||||
|
||||
result = dly_op_request(&dly_ts_param);
|
||||
result = dly_op_request(&dly_ts_param, p_dly_tx_data);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@ -448,35 +773,42 @@ bool nrf_802154_delayed_trx_transmit(const uint8_t * p_data,
|
|||
bool nrf_802154_delayed_trx_receive(uint32_t t0,
|
||||
uint32_t dt,
|
||||
uint32_t timeout,
|
||||
uint8_t channel)
|
||||
uint8_t channel,
|
||||
uint32_t id)
|
||||
{
|
||||
bool result = dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_STOPPED;
|
||||
bool result = is_dly_ts_slot_available(m_dly_rx_data,
|
||||
sizeof(m_dly_rx_data) / sizeof(m_dly_rx_data[0]));
|
||||
|
||||
if (result)
|
||||
{
|
||||
dt -= RX_SETUP_TIME;
|
||||
dt -= RX_RAMP_UP_TIME;
|
||||
|
||||
m_timeout_timer.dt = timeout + RX_RAMP_UP_TIME;
|
||||
m_timeout_timer.callback = notify_rx_timeout;
|
||||
m_timeout_timer.p_context = NULL;
|
||||
dly_op_data_t * p_dly_rx_data = available_dly_rx_slot_get();
|
||||
|
||||
m_rx_channel = channel;
|
||||
p_dly_rx_data->op = RSCH_DLY_TS_OP_DRX;
|
||||
|
||||
// remove timer in case it was left after abort operation
|
||||
nrf_802154_timer_sched_remove(&m_timeout_timer, NULL);
|
||||
p_dly_rx_data->rx.timeout_timer.dt = timeout + RX_RAMP_UP_TIME;
|
||||
p_dly_rx_data->rx.timeout_timer.callback = notify_rx_timeout;
|
||||
|
||||
p_dly_rx_data->rx.channel = channel;
|
||||
p_dly_rx_data->id = id;
|
||||
|
||||
// Remove timer in case it was left after abort operation
|
||||
nrf_802154_timer_sched_remove(&p_dly_rx_data->rx.timeout_timer, NULL);
|
||||
|
||||
rsch_dly_ts_param_t dly_ts_param =
|
||||
{
|
||||
.t0 = t0,
|
||||
.dt = dt,
|
||||
.prio = RSCH_PRIO_IDLE_LISTENING,
|
||||
.id = RSCH_DLY_RX,
|
||||
.op = RSCH_DLY_TS_OP_DRX,
|
||||
.type = RSCH_DLY_TS_TYPE_PRECISE,
|
||||
.started_callback = rx_timeslot_started_callback,
|
||||
.id = id,
|
||||
};
|
||||
|
||||
result = dly_op_request(&dly_ts_param);
|
||||
result = dly_op_request(&dly_ts_param, p_dly_rx_data);
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@ -484,21 +816,40 @@ bool nrf_802154_delayed_trx_receive(uint32_t t0,
|
|||
|
||||
bool nrf_802154_delayed_trx_transmit_cancel(void)
|
||||
{
|
||||
bool result = nrf_802154_rsch_delayed_timeslot_cancel(RSCH_DLY_TX);
|
||||
// This function does not provide any ID because it assumes that only a single delayed
|
||||
// transmission can be scheduled at a time. Therefore use the first (and only) entry
|
||||
// of m_dly_tx_data
|
||||
dly_op_data_t * p_dly_op_data = &m_dly_tx_data[0];
|
||||
bool result = false;
|
||||
|
||||
m_dly_op_state[RSCH_DLY_TX] = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
if (p_dly_op_data->id != NRF_802154_RESERVED_INVALID_ID)
|
||||
{
|
||||
result = nrf_802154_rsch_delayed_timeslot_cancel(p_dly_op_data->id);
|
||||
|
||||
p_dly_op_data->state = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
p_dly_op_data->id = NRF_802154_RESERVED_INVALID_ID;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
bool nrf_802154_delayed_trx_receive_cancel(void)
|
||||
bool nrf_802154_delayed_trx_receive_cancel(uint32_t id)
|
||||
{
|
||||
bool result = nrf_802154_rsch_delayed_timeslot_cancel(RSCH_DLY_RX);
|
||||
dly_op_data_t * p_dly_op_data = dly_rx_data_by_id_search(id);
|
||||
|
||||
if (p_dly_op_data == NULL)
|
||||
{
|
||||
// Delayed receive window with provided ID could not be found.
|
||||
return false;
|
||||
}
|
||||
|
||||
bool result = nrf_802154_rsch_delayed_timeslot_cancel(id);
|
||||
bool was_running = false;
|
||||
|
||||
nrf_802154_timer_sched_remove(&m_timeout_timer, &was_running);
|
||||
nrf_802154_timer_sched_remove(&p_dly_op_data->rx.timeout_timer, &was_running);
|
||||
|
||||
m_dly_op_state[RSCH_DLY_RX] = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
p_dly_op_data->state = DELAYED_TRX_OP_STATE_STOPPED;
|
||||
p_dly_op_data->id = NRF_802154_RESERVED_INVALID_ID;
|
||||
|
||||
result = result || was_running;
|
||||
|
||||
|
@ -507,24 +858,25 @@ bool nrf_802154_delayed_trx_receive_cancel(void)
|
|||
|
||||
bool nrf_802154_delayed_trx_abort(nrf_802154_term_t term_lvl, req_originator_t req_orig)
|
||||
{
|
||||
bool result = true;
|
||||
bool result = true;
|
||||
dly_op_data_t * p_dly_op_data = ongoing_dly_rx_slot_get();
|
||||
|
||||
if (req_orig == REQ_ORIG_DELAYED_TRX)
|
||||
{
|
||||
// Ignore if self-request.
|
||||
}
|
||||
else if (dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_ONGOING)
|
||||
if (p_dly_op_data != NULL)
|
||||
{
|
||||
if (term_lvl >= NRF_802154_TERM_802154)
|
||||
{
|
||||
if (dly_rx_state_set(DELAYED_TRX_OP_STATE_ONGOING, DELAYED_TRX_OP_STATE_STOPPED))
|
||||
if (dly_op_state_set(p_dly_op_data,
|
||||
DELAYED_TRX_OP_STATE_ONGOING,
|
||||
DELAYED_TRX_OP_STATE_STOPPED))
|
||||
{
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_ABORTED);
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_DELAYED_ABORTED,
|
||||
p_dly_op_data->id);
|
||||
dly_ts_slot_release(p_dly_op_data);
|
||||
}
|
||||
|
||||
// even if the set operation failed, the delayed RX state
|
||||
// Even if the set operation failed, the delayed RX state
|
||||
// should be set to STOPPED from other context anyway
|
||||
assert(dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_STOPPED);
|
||||
assert(p_dly_op_data->state == DELAYED_TRX_OP_STATE_STOPPED);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -537,11 +889,14 @@ bool nrf_802154_delayed_trx_abort(nrf_802154_term_t term_lvl, req_originator_t r
|
|||
|
||||
void nrf_802154_delayed_trx_rx_started_hook(const uint8_t * p_frame)
|
||||
{
|
||||
if (dly_op_state_get(RSCH_DLY_RX) == DELAYED_TRX_OP_STATE_ONGOING)
|
||||
dly_op_data_t * p_dly_op_data = ongoing_dly_rx_slot_get();
|
||||
|
||||
if (p_dly_op_data != NULL)
|
||||
{
|
||||
m_dly_rx_frame.sof_timestamp = nrf_802154_timer_sched_time_get();
|
||||
m_dly_rx_frame.psdu_length = p_frame[PHR_OFFSET];
|
||||
m_dly_rx_frame.ack_requested = nrf_802154_frame_parser_ar_bit_is_set(p_frame);
|
||||
p_dly_op_data->rx.extension_frame.sof_timestamp = nrf_802154_timer_sched_time_get();
|
||||
p_dly_op_data->rx.extension_frame.psdu_length = p_frame[PHR_OFFSET];
|
||||
p_dly_op_data->rx.extension_frame.ack_requested = nrf_802154_frame_parser_ar_bit_is_set(
|
||||
p_frame);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -53,6 +53,11 @@
|
|||
* modes.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief Initializes delayed transmission and reception window features.
|
||||
*/
|
||||
void nrf_802154_delayed_trx_init(void);
|
||||
|
||||
/**
|
||||
* @brief Requests transmission of a frame at a given time.
|
||||
*
|
||||
|
@ -98,25 +103,41 @@ bool nrf_802154_delayed_trx_transmit_cancel(void);
|
|||
* to a denied timeslot request or the reception timeout expires,
|
||||
* the @ref nrf_802154_receive_failed function is called.
|
||||
*
|
||||
* @note The identifier @p id must be unique. It must not have the same value as identifiers
|
||||
* of other delayed timeslots active at the moment, so that it can be mapped unambiguously
|
||||
* to an active delayed operation if the request is successful. In particular, none of the reserved
|
||||
* identifiers can be used.
|
||||
*
|
||||
* @param[in] t0 Base of delay time in microseconds.
|
||||
* @param[in] dt Delta of delay time from @p t0 in microseconds.
|
||||
* @param[in] timeout Reception timeout (counted from @p t0 + @p dt) in microseconds.
|
||||
* @param[in] channel Number of the channel on which the frame is to be received.
|
||||
* @param[in] id Identifier of the scheduled reception window. If the reception has been
|
||||
* scheduled successfully, the value of this parameter can be used in
|
||||
* @ref nrf_802154_delayed_trx_receive_cancel to cancel it.
|
||||
*
|
||||
* @retval true The reception procedure was scheduled.
|
||||
* @retval false The driver could not schedule the reception procedure.
|
||||
*/
|
||||
bool nrf_802154_delayed_trx_receive(uint32_t t0,
|
||||
uint32_t dt,
|
||||
uint32_t timeout,
|
||||
uint8_t channel);
|
||||
uint8_t channel,
|
||||
uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Cancels a reception scheduled by a call to @ref nrf_802154_delayed_trx_receive.
|
||||
*
|
||||
* After a call to this function, no reception timeout event will be notified.
|
||||
*
|
||||
* @param[in] id Identifier of the delayed reception window to be cancelled. If the provided
|
||||
* value does not refer to any scheduled or active receive window, the function
|
||||
* returns false.
|
||||
*
|
||||
* @retval true Successfully cancelled a scheduled transmission.
|
||||
* @retval false No delayed reception was scheduled.
|
||||
*/
|
||||
bool nrf_802154_delayed_trx_receive_cancel(void);
|
||||
bool nrf_802154_delayed_trx_receive_cancel(uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Aborts an ongoing delayed reception procedure.
|
||||
|
|
|
@ -83,7 +83,8 @@ static void timeout_timer_fired(void * p_context)
|
|||
if (nrf_802154_request_receive(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_ACK_TIMEOUT,
|
||||
notify_tx_error,
|
||||
false))
|
||||
false,
|
||||
NRF_802154_RESERVED_IMM_RX_WINDOW_ID))
|
||||
{
|
||||
m_procedure_is_active = false;
|
||||
}
|
||||
|
|
|
@ -116,7 +116,7 @@ void nrf_802154_channel_set(uint8_t channel)
|
|||
|
||||
if (changed)
|
||||
{
|
||||
(void)nrf_802154_request_channel_update();
|
||||
(void)nrf_802154_request_channel_update(REQ_ORIG_HIGHER_LAYER);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -219,6 +219,9 @@ void nrf_802154_init(void)
|
|||
nrf_802154_temperature_init();
|
||||
nrf_802154_timer_coord_init();
|
||||
nrf_802154_timer_sched_init();
|
||||
#if NRF_802154_DELAYED_TRX_ENABLED
|
||||
nrf_802154_delayed_trx_init();
|
||||
#endif
|
||||
}
|
||||
|
||||
void nrf_802154_deinit(void)
|
||||
|
@ -411,7 +414,11 @@ bool nrf_802154_receive(void)
|
|||
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
result = nrf_802154_request_receive(NRF_802154_TERM_802154, REQ_ORIG_HIGHER_LAYER, NULL, true);
|
||||
result = nrf_802154_request_receive(NRF_802154_TERM_802154,
|
||||
REQ_ORIG_HIGHER_LAYER,
|
||||
NULL,
|
||||
true,
|
||||
NRF_802154_RESERVED_IMM_RX_WINDOW_ID);
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
return result;
|
||||
|
@ -489,25 +496,26 @@ bool nrf_802154_transmit_at_cancel(void)
|
|||
bool nrf_802154_receive_at(uint32_t t0,
|
||||
uint32_t dt,
|
||||
uint32_t timeout,
|
||||
uint8_t channel)
|
||||
uint8_t channel,
|
||||
uint32_t id)
|
||||
{
|
||||
bool result;
|
||||
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
result = nrf_802154_delayed_trx_receive(t0, dt, timeout, channel);
|
||||
result = nrf_802154_delayed_trx_receive(t0, dt, timeout, channel, id);
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
return result;
|
||||
}
|
||||
|
||||
bool nrf_802154_receive_at_cancel(void)
|
||||
bool nrf_802154_receive_at_cancel(uint32_t id)
|
||||
{
|
||||
bool result;
|
||||
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
result = nrf_802154_delayed_trx_receive_cancel();
|
||||
result = nrf_802154_delayed_trx_receive_cancel(id);
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
return result;
|
||||
|
@ -899,7 +907,9 @@ __WEAK void nrf_802154_tx_ack_started(const uint8_t * p_data)
|
|||
#if NRF_802154_USE_RAW_API
|
||||
__WEAK void nrf_802154_received_raw(uint8_t * p_data, int8_t power, uint8_t lqi)
|
||||
{
|
||||
nrf_802154_received_timestamp_raw(p_data, power, lqi,
|
||||
nrf_802154_received_timestamp_raw(p_data,
|
||||
power,
|
||||
lqi,
|
||||
nrf_802154_stat_timestamp_read(last_rx_end_timestamp));
|
||||
}
|
||||
|
||||
|
@ -938,9 +948,10 @@ __WEAK void nrf_802154_received_timestamp(uint8_t * p_data,
|
|||
|
||||
#endif // !NRF_802154_USE_RAW_API
|
||||
|
||||
__WEAK void nrf_802154_receive_failed(nrf_802154_rx_error_t error)
|
||||
__WEAK void nrf_802154_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
(void)error;
|
||||
(void)id;
|
||||
}
|
||||
|
||||
__WEAK void nrf_802154_tx_started(const uint8_t * p_frame)
|
||||
|
|
|
@ -147,6 +147,9 @@ static nrf_802154_timer_t m_rx_prestarted_timer;
|
|||
/** @brief Value of Coex TX Request mode */
|
||||
static nrf_802154_coex_tx_request_mode_t m_coex_tx_request_mode;
|
||||
|
||||
/** @brief Identifier of currently active reception window. */
|
||||
static uint32_t m_rx_window_id;
|
||||
|
||||
#if NRF_802154_TOTAL_TIMES_MEASUREMENT_ENABLED
|
||||
#if !NRF_802154_FRAME_TIMESTAMP_ENABLED
|
||||
#error NRF_802154_FRAME_TIMESTAMP_ENABLED == 0 when NRF_802154_TOTAL_TIMES_MEASUREMENT_ENABLED != 0
|
||||
|
@ -181,7 +184,8 @@ static void state_set(radio_state_t state)
|
|||
m_state = state;
|
||||
|
||||
nrf_802154_log_local_event(NRF_802154_LOG_VERBOSITY_LOW,
|
||||
NRF_802154_LOG_LOCAL_EVENT_ID_CORE__SET_STATE, (uint32_t)state);
|
||||
NRF_802154_LOG_LOCAL_EVENT_ID_CORE__SET_STATE,
|
||||
(uint32_t)state);
|
||||
|
||||
request_preconditions_for_state(state);
|
||||
}
|
||||
|
@ -292,7 +296,7 @@ static void receive_failed_notify(nrf_802154_rx_error_t error)
|
|||
{
|
||||
nrf_802154_critical_section_nesting_allow();
|
||||
|
||||
nrf_802154_notify_receive_failed(error);
|
||||
nrf_802154_notify_receive_failed(error, m_rx_window_id);
|
||||
|
||||
nrf_802154_critical_section_nesting_deny();
|
||||
}
|
||||
|
@ -671,7 +675,7 @@ static void operation_terminated_notify(radio_state_t state, bool receiving_psdu
|
|||
case RADIO_STATE_RX:
|
||||
if (receiving_psdu_now)
|
||||
{
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_ABORTED);
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_ABORTED, m_rx_window_id);
|
||||
}
|
||||
|
||||
break;
|
||||
|
@ -1621,7 +1625,7 @@ uint8_t nrf_802154_trx_receive_frame_bcmatched(uint8_t bcc)
|
|||
// which could result in spurious RF emission.
|
||||
rx_init();
|
||||
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_TIMESLOT_ENDED);
|
||||
nrf_802154_notify_receive_failed(NRF_802154_RX_ERROR_TIMESLOT_ENDED, m_rx_window_id);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1741,7 +1745,8 @@ void nrf_802154_trx_receive_frame_crcerror(void)
|
|||
#endif
|
||||
|
||||
#if NRF_802154_TOTAL_TIMES_MEASUREMENT_ENABLED
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp, receive_end_hp_timestamp,
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp,
|
||||
receive_end_hp_timestamp,
|
||||
mp_current_rx_buffer->data[PHR_OFFSET]);
|
||||
#endif
|
||||
|
||||
|
@ -1762,7 +1767,8 @@ void nrf_802154_trx_receive_ack_crcerror(void)
|
|||
uint32_t receive_end_hp_timestamp = nrf_802154_hp_timer_timestamp_get();
|
||||
uint32_t listening_start_hp_timestamp = m_listening_start_hp_timestamp;
|
||||
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp, receive_end_hp_timestamp,
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp,
|
||||
receive_end_hp_timestamp,
|
||||
mp_current_rx_buffer->data[PHR_OFFSET]);
|
||||
#endif
|
||||
|
||||
|
@ -1781,7 +1787,8 @@ void nrf_802154_trx_receive_frame_received(void)
|
|||
uint32_t receive_end_hp_timestamp = nrf_802154_hp_timer_timestamp_get();
|
||||
uint32_t listening_start_hp_timestamp = m_listening_start_hp_timestamp;
|
||||
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp, receive_end_hp_timestamp,
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp,
|
||||
receive_end_hp_timestamp,
|
||||
mp_current_rx_buffer->data[PHR_OFFSET]);
|
||||
#endif
|
||||
|
||||
|
@ -2192,7 +2199,8 @@ void nrf_802154_trx_receive_ack_received(void)
|
|||
uint32_t receive_end_hp_timestamp = nrf_802154_hp_timer_timestamp_get();
|
||||
uint32_t listening_start_hp_timestamp = m_listening_start_hp_timestamp;
|
||||
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp, receive_end_hp_timestamp,
|
||||
update_total_times_on_receive_end(listening_start_hp_timestamp,
|
||||
receive_end_hp_timestamp,
|
||||
mp_current_rx_buffer->data[PHR_OFFSET]);
|
||||
#endif
|
||||
|
||||
|
@ -2405,7 +2413,8 @@ bool nrf_802154_core_sleep(nrf_802154_term_t term_lvl)
|
|||
bool nrf_802154_core_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort)
|
||||
bool notify_abort,
|
||||
uint32_t id)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
|
@ -2423,6 +2432,7 @@ bool nrf_802154_core_receive(nrf_802154_term_t term_lvl,
|
|||
{
|
||||
m_trx_receive_frame_notifications_mask =
|
||||
make_trx_frame_receive_notification_mask();
|
||||
m_rx_window_id = id;
|
||||
state_set(RADIO_STATE_RX);
|
||||
rx_init();
|
||||
}
|
||||
|
@ -2653,7 +2663,7 @@ bool nrf_802154_core_notify_buffer_free(uint8_t * p_data)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool nrf_802154_core_channel_update(void)
|
||||
bool nrf_802154_core_channel_update(req_originator_t req_orig)
|
||||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
|
||||
|
@ -2669,7 +2679,7 @@ bool nrf_802154_core_channel_update(void)
|
|||
switch (m_state)
|
||||
{
|
||||
case RADIO_STATE_RX:
|
||||
if (current_operation_terminate(NRF_802154_TERM_NONE, REQ_ORIG_CORE, true))
|
||||
if (current_operation_terminate(NRF_802154_TERM_802154, req_orig, true))
|
||||
{
|
||||
rx_init();
|
||||
}
|
||||
|
|
|
@ -121,6 +121,7 @@ bool nrf_802154_core_sleep(nrf_802154_term_t term_lvl);
|
|||
* @param[in] req_orig Module that originates this request.
|
||||
* @param[in] notify_function Function called to notify the status of this procedure. May be NULL.
|
||||
* @param[in] notify_abort If abort notification is to be triggered.
|
||||
* @param[in] id Identifier of reception window.
|
||||
*
|
||||
* @retval true Entering the receive state succeeded.
|
||||
* @retval false Entering the receive state failed (the driver is performing other procedure).
|
||||
|
@ -128,7 +129,8 @@ bool nrf_802154_core_sleep(nrf_802154_term_t term_lvl);
|
|||
bool nrf_802154_core_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort);
|
||||
bool notify_abort,
|
||||
uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Requests the transition to the @ref RADIO_STATE_TX state.
|
||||
|
@ -225,8 +227,10 @@ bool nrf_802154_core_notify_buffer_free(uint8_t * p_data);
|
|||
* in the @ref RADIO_STATE_RX, in the @ref RADIO_STATE_CONTINUOUS_CARRIER
|
||||
* or in the @ref RADIO_STATE_MODULATED_CARRIER state, the transceiver is disabled
|
||||
* and enabled again to use the new channel.
|
||||
*
|
||||
* @param[in] req_orig Module that originates this request.
|
||||
*/
|
||||
bool nrf_802154_core_channel_update(void);
|
||||
bool nrf_802154_core_channel_update(req_originator_t req_orig);
|
||||
|
||||
/**
|
||||
* @brief Notifies the core module that the next higher layer requested the change
|
||||
|
|
|
@ -79,8 +79,13 @@ void nrf_802154_notify_received(uint8_t * p_data, int8_t power, uint8_t lqi);
|
|||
* @brief Notifies the next higher layer that the reception of a frame failed.
|
||||
*
|
||||
* @param[in] error Error code that indicates the reason of the failure.
|
||||
* @param[in] id Identifier of reception window the error occurred in.
|
||||
* If the error is related to a delayed reception window requested through
|
||||
* @ref nrf_802154_receive_at, the value of @p id equals the identifier
|
||||
* of the scheduled reception window. Otherwise, the value of @p id equals
|
||||
* @ref NRF_802154_RESERVED_IMM_RX_WINDOW_ID.
|
||||
*/
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error);
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error, uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Notifies the next higher layer that a frame was transmitted.
|
||||
|
|
|
@ -63,9 +63,9 @@ void nrf_802154_notify_received(uint8_t * p_data, int8_t power, uint8_t lqi)
|
|||
#endif // NRF_802154_USE_RAW_API
|
||||
}
|
||||
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error)
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
nrf_802154_receive_failed(error);
|
||||
nrf_802154_receive_failed(error, id);
|
||||
}
|
||||
|
||||
void nrf_802154_notify_transmitted(const uint8_t * p_frame,
|
||||
|
|
|
@ -95,6 +95,7 @@ typedef struct
|
|||
struct
|
||||
{
|
||||
nrf_802154_rx_error_t error; ///< An error code that indicates reason of the failure.
|
||||
uint32_t id; ///< Identifier of reception window the error occured in.
|
||||
} receive_failed;
|
||||
|
||||
struct
|
||||
|
@ -196,12 +197,13 @@ void swi_notify_received(uint8_t * p_data, int8_t power, uint8_t lqi)
|
|||
*
|
||||
* @param[in] error Error code that indicates reason of the failure.
|
||||
*/
|
||||
void swi_notify_receive_failed(nrf_802154_rx_error_t error)
|
||||
void swi_notify_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
nrf_802154_ntf_data_t * p_slot = ntf_enter();
|
||||
|
||||
p_slot->type = NTF_TYPE_RECEIVE_FAILED;
|
||||
p_slot->data.receive_failed.error = error;
|
||||
p_slot->data.receive_failed.id = id;
|
||||
|
||||
ntf_exit();
|
||||
}
|
||||
|
@ -320,7 +322,8 @@ void swi_notify_cca_failed(nrf_802154_cca_error_t error)
|
|||
|
||||
void nrf_802154_notification_init(void)
|
||||
{
|
||||
nrf_802154_queue_init(&m_notifications_queue, m_notifications_queue_memory,
|
||||
nrf_802154_queue_init(&m_notifications_queue,
|
||||
m_notifications_queue_memory,
|
||||
sizeof(m_notifications_queue_memory),
|
||||
sizeof(m_notifications_queue_memory[0]));
|
||||
|
||||
|
@ -334,9 +337,9 @@ void nrf_802154_notify_received(uint8_t * p_data, int8_t power, uint8_t lqi)
|
|||
swi_notify_received(p_data, power, lqi);
|
||||
}
|
||||
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error)
|
||||
void nrf_802154_notify_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
swi_notify_receive_failed(error);
|
||||
swi_notify_receive_failed(error, id);
|
||||
}
|
||||
|
||||
void nrf_802154_notify_transmitted(const uint8_t * p_frame,
|
||||
|
@ -396,7 +399,8 @@ static void irq_handler_ntf_event(void)
|
|||
break;
|
||||
|
||||
case NTF_TYPE_RECEIVE_FAILED:
|
||||
nrf_802154_receive_failed(p_slot->data.receive_failed.error);
|
||||
nrf_802154_receive_failed(p_slot->data.receive_failed.error,
|
||||
p_slot->data.receive_failed.id);
|
||||
break;
|
||||
|
||||
case NTF_TYPE_TRANSMITTED:
|
||||
|
|
|
@ -75,6 +75,7 @@ bool nrf_802154_request_sleep(nrf_802154_term_t term_lvl);
|
|||
* @param[in] req_orig Module that originates this request.
|
||||
* @param[in] notify_function Function called to notify the status of this procedure. May be NULL.
|
||||
* @param[in] notify_abort If the abort notification is to be triggered automatically.
|
||||
* @param[in] id Identifier of a reception window.
|
||||
*
|
||||
* @retval true The driver will enter the receive state.
|
||||
* @retval false The driver cannot enter the receive state due to ongoing operation.
|
||||
|
@ -82,7 +83,8 @@ bool nrf_802154_request_sleep(nrf_802154_term_t term_lvl);
|
|||
bool nrf_802154_request_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort);
|
||||
bool notify_abort,
|
||||
uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Request entering the @ref RADIO_STATE_TX state for the driver.
|
||||
|
@ -162,8 +164,10 @@ bool nrf_802154_request_antenna_update(void);
|
|||
|
||||
/**
|
||||
* @brief Requests the driver to update the channel number used by the RADIO peripheral.
|
||||
*
|
||||
* @param[in] req_orig Module that originates this request.
|
||||
*/
|
||||
bool nrf_802154_request_channel_update(void);
|
||||
bool nrf_802154_request_channel_update(req_originator_t req_orig);
|
||||
|
||||
/**
|
||||
* @brief Requests the driver to update the CCA configuration used by the RADIO peripheral.
|
||||
|
|
|
@ -73,13 +73,15 @@ bool nrf_802154_request_sleep(nrf_802154_term_t term_lvl)
|
|||
bool nrf_802154_request_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort)
|
||||
bool notify_abort,
|
||||
uint32_t id)
|
||||
{
|
||||
REQUEST_FUNCTION_PARMS(nrf_802154_core_receive,
|
||||
term_lvl,
|
||||
req_orig,
|
||||
notify_function,
|
||||
notify_abort)
|
||||
notify_abort,
|
||||
id)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_transmit(nrf_802154_term_t term_lvl,
|
||||
|
@ -129,9 +131,9 @@ bool nrf_802154_request_antenna_update(void)
|
|||
REQUEST_FUNCTION(nrf_802154_core_antenna_update)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_channel_update(void)
|
||||
bool nrf_802154_request_channel_update(req_originator_t req_orig)
|
||||
{
|
||||
REQUEST_FUNCTION(nrf_802154_core_channel_update)
|
||||
REQUEST_FUNCTION_PARMS(nrf_802154_core_channel_update, req_orig)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_cca_cfg_update(void)
|
||||
|
|
|
@ -106,6 +106,7 @@ typedef struct
|
|||
nrf_802154_term_t term_lvl; ///< Request priority.
|
||||
req_originator_t req_orig; ///< Request originator.
|
||||
bool notif_abort; ///< If function termination should be notified.
|
||||
uint32_t id; ///< Identifier of a reception window.
|
||||
bool * p_result; ///< Receive request result.
|
||||
} receive; ///< Receive request details.
|
||||
|
||||
|
@ -154,8 +155,9 @@ typedef struct
|
|||
|
||||
struct
|
||||
{
|
||||
bool * p_result; ///< Channel update request result.
|
||||
} channel_update; ///< Channel update request details.
|
||||
req_originator_t req_orig; ///< Request originator.
|
||||
bool * p_result; ///< Channel update request result.
|
||||
} channel_update; ///< Channel update request details.
|
||||
|
||||
struct
|
||||
{
|
||||
|
@ -293,12 +295,14 @@ static void swi_sleep(nrf_802154_term_t term_lvl, bool * p_result)
|
|||
* @param[in] req_orig Module that originates this request.
|
||||
* @param[in] notify_function Function called to notify the status of the procedure. May be NULL.
|
||||
* @param[in] notify_abort If abort notification should be triggered automatically.
|
||||
* @param[in] id Identifier of the reception window.
|
||||
* @param[out] p_result Result of entering the receive state.
|
||||
*/
|
||||
static void swi_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort,
|
||||
uint32_t id,
|
||||
bool * p_result)
|
||||
{
|
||||
nrf_802154_req_data_t * p_slot = req_enter();
|
||||
|
@ -308,6 +312,7 @@ static void swi_receive(nrf_802154_term_t term_lvl,
|
|||
p_slot->data.receive.req_orig = req_orig;
|
||||
p_slot->data.receive.notif_func = notify_function;
|
||||
p_slot->data.receive.notif_abort = notify_abort;
|
||||
p_slot->data.receive.id = id;
|
||||
p_slot->data.receive.p_result = p_result;
|
||||
|
||||
req_exit();
|
||||
|
@ -467,12 +472,13 @@ static void swi_antenna_update(bool * p_result)
|
|||
* @param[out] p_result Pointer where the result to be returned by
|
||||
* nrf_802154_request_channel_update should be written by the swi handler.
|
||||
*/
|
||||
static void swi_channel_update(bool * p_result)
|
||||
static void swi_channel_update(req_originator_t req_orig, bool * p_result)
|
||||
{
|
||||
nrf_802154_req_data_t * p_slot = req_enter();
|
||||
|
||||
p_slot->type = REQ_TYPE_CHANNEL_UPDATE;
|
||||
p_slot->data.channel_update.p_result = p_result;
|
||||
p_slot->data.channel_update.req_orig = req_orig;
|
||||
|
||||
req_exit();
|
||||
}
|
||||
|
@ -529,8 +535,10 @@ static void swi_rssi_measurement_get(int8_t * p_rssi, bool * p_result)
|
|||
|
||||
void nrf_802154_request_init(void)
|
||||
{
|
||||
nrf_802154_queue_init(&m_requests_queue, m_requests_queue_memory,
|
||||
sizeof(m_requests_queue_memory), sizeof(m_requests_queue_memory[0]));
|
||||
nrf_802154_queue_init(&m_requests_queue,
|
||||
m_requests_queue_memory,
|
||||
sizeof(m_requests_queue_memory),
|
||||
sizeof(m_requests_queue_memory[0]));
|
||||
|
||||
nrf_egu_int_enable(NRF_802154_EGU_INSTANCE, REQ_INT);
|
||||
|
||||
|
@ -545,14 +553,16 @@ bool nrf_802154_request_sleep(nrf_802154_term_t term_lvl)
|
|||
bool nrf_802154_request_receive(nrf_802154_term_t term_lvl,
|
||||
req_originator_t req_orig,
|
||||
nrf_802154_notification_func_t notify_function,
|
||||
bool notify_abort)
|
||||
bool notify_abort,
|
||||
uint32_t id)
|
||||
{
|
||||
REQUEST_FUNCTION(nrf_802154_core_receive,
|
||||
swi_receive,
|
||||
term_lvl,
|
||||
req_orig,
|
||||
notify_function,
|
||||
notify_abort)
|
||||
notify_abort,
|
||||
id)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_transmit(nrf_802154_term_t term_lvl,
|
||||
|
@ -588,7 +598,8 @@ bool nrf_802154_request_cca(nrf_802154_term_t term_lvl)
|
|||
|
||||
bool nrf_802154_request_continuous_carrier(nrf_802154_term_t term_lvl)
|
||||
{
|
||||
REQUEST_FUNCTION(nrf_802154_core_continuous_carrier, swi_continuous_carrier,
|
||||
REQUEST_FUNCTION(nrf_802154_core_continuous_carrier,
|
||||
swi_continuous_carrier,
|
||||
term_lvl)
|
||||
}
|
||||
|
||||
|
@ -611,9 +622,9 @@ bool nrf_802154_request_antenna_update(void)
|
|||
REQUEST_FUNCTION_NO_ARGS(nrf_802154_core_antenna_update, swi_antenna_update)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_channel_update(void)
|
||||
bool nrf_802154_request_channel_update(req_originator_t req_orig)
|
||||
{
|
||||
REQUEST_FUNCTION_NO_ARGS(nrf_802154_core_channel_update, swi_channel_update)
|
||||
REQUEST_FUNCTION(nrf_802154_core_channel_update, swi_channel_update, req_orig)
|
||||
}
|
||||
|
||||
bool nrf_802154_request_cca_cfg_update(void)
|
||||
|
@ -653,7 +664,8 @@ static void irq_handler_req_event(void)
|
|||
nrf_802154_core_receive(p_slot->data.receive.term_lvl,
|
||||
p_slot->data.receive.req_orig,
|
||||
p_slot->data.receive.notif_func,
|
||||
p_slot->data.receive.notif_abort);
|
||||
p_slot->data.receive.notif_abort,
|
||||
p_slot->data.receive.id);
|
||||
break;
|
||||
|
||||
case REQ_TYPE_TRANSMIT:
|
||||
|
@ -695,7 +707,8 @@ static void irq_handler_req_event(void)
|
|||
break;
|
||||
|
||||
case REQ_TYPE_CHANNEL_UPDATE:
|
||||
*(p_slot->data.channel_update.p_result) = nrf_802154_core_channel_update();
|
||||
*(p_slot->data.channel_update.p_result) =
|
||||
nrf_802154_core_channel_update(p_slot->data.channel_update.req_orig);
|
||||
break;
|
||||
|
||||
case REQ_TYPE_CCA_CFG_UPDATE:
|
||||
|
|
|
@ -244,7 +244,8 @@ static void nrf_radio_reset(void)
|
|||
nrf_radio_power_set(NRF_RADIO, true);
|
||||
|
||||
nrf_802154_log_global_event(NRF_802154_LOG_VERBOSITY_LOW,
|
||||
NRF_802154_LOG_GLOBAL_EVENT_ID_RADIO_RESET, 0U);
|
||||
NRF_802154_LOG_GLOBAL_EVENT_ID_RADIO_RESET,
|
||||
0U);
|
||||
|
||||
nrf_802154_log_function_exit(NRF_802154_LOG_VERBOSITY_LOW);
|
||||
}
|
||||
|
@ -605,7 +606,8 @@ void nrf_802154_trx_disable(void)
|
|||
m_trx_state = TRX_STATE_DISABLED;
|
||||
|
||||
nrf_802154_log_global_event(NRF_802154_LOG_VERBOSITY_LOW,
|
||||
NRF_802154_LOG_GLOBAL_EVENT_ID_RADIO_RESET, 0U);
|
||||
NRF_802154_LOG_GLOBAL_EVENT_ID_RADIO_RESET,
|
||||
0U);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -2040,7 +2042,8 @@ static void txframe_finish_disable_ints(void)
|
|||
{
|
||||
nrf_802154_log_function_enter(NRF_802154_LOG_VERBOSITY_HIGH);
|
||||
|
||||
nrf_radio_int_disable(NRF_RADIO, NRF_RADIO_INT_PHYEND_MASK |
|
||||
nrf_radio_int_disable(NRF_RADIO,
|
||||
NRF_RADIO_INT_PHYEND_MASK |
|
||||
NRF_RADIO_INT_CCAIDLE_MASK |
|
||||
NRF_RADIO_INT_CCABUSY_MASK |
|
||||
NRF_RADIO_INT_ADDRESS_MASK |
|
||||
|
|
|
@ -69,7 +69,8 @@ void nrf_802154_trx_ppi_for_ramp_up_set(nrf_radio_task_t ramp_up_task, bool star
|
|||
// Clr event EGU (needed for nrf_802154_trx_ppi_for_ramp_up_was_triggered)
|
||||
nrf_egu_event_clear(NRF_802154_EGU_INSTANCE, EGU_EVENT);
|
||||
|
||||
nrf_ppi_channel_and_fork_endpoint_setup(NRF_PPI, PPI_EGU_RAMP_UP,
|
||||
nrf_ppi_channel_and_fork_endpoint_setup(NRF_PPI,
|
||||
PPI_EGU_RAMP_UP,
|
||||
nrf_egu_event_address_get(
|
||||
NRF_802154_EGU_INSTANCE,
|
||||
EGU_EVENT),
|
||||
|
@ -79,7 +80,8 @@ void nrf_802154_trx_ppi_for_ramp_up_set(nrf_radio_task_t ramp_up_task, bool star
|
|||
|
||||
if (start_timer)
|
||||
{
|
||||
nrf_ppi_channel_endpoint_setup(NRF_PPI, PPI_EGU_TIMER_START,
|
||||
nrf_ppi_channel_endpoint_setup(NRF_PPI,
|
||||
PPI_EGU_TIMER_START,
|
||||
nrf_egu_event_address_get(NRF_802154_EGU_INSTANCE,
|
||||
EGU_EVENT),
|
||||
nrf_timer_task_address_get(NRF_802154_TIMER_INSTANCE,
|
||||
|
|
|
@ -48,6 +48,11 @@
|
|||
#include "nrf_802154_config.h"
|
||||
#include "nrf_802154_types.h"
|
||||
|
||||
/**
|
||||
* @brief Reception window identifier reserved for immediate reception.
|
||||
*/
|
||||
#define NRF_802154_RESERVED_IMM_RX_WINDOW_ID (UINT32_MAX - 1)
|
||||
|
||||
/**
|
||||
* @brief Select the source matching algorithm.
|
||||
*
|
||||
|
@ -61,6 +66,59 @@
|
|||
*/
|
||||
void nrf_802154_src_addr_matching_method_set(nrf_802154_src_addr_match_t match_method);
|
||||
|
||||
/**
|
||||
* @brief Adds the address of a peer node for which the provided ACK data
|
||||
* is to be added to the pending bit list.
|
||||
*
|
||||
* The pending bit list works differently, depending on the upper layer for which the source
|
||||
* address matching method is selected:
|
||||
* - For Thread, @ref NRF_802154_SRC_ADDR_MATCH_THREAD
|
||||
* - For Zigbee, @ref NRF_802154_SRC_ADDR_MATCH_ZIGBEE
|
||||
* - For Standard-compliant, @ref NRF_802154_SRC_ADDR_MATCH_ALWAYS_1
|
||||
* For more information, see @ref nrf_802154_src_addr_match_t.
|
||||
*
|
||||
* The method can be set during initialization phase by calling @ref nrf_802154_src_matching_method.
|
||||
*
|
||||
* @param[in] p_addr Array of bytes containing the address of the node (little-endian).
|
||||
* @param[in] extended If the given address is an extended MAC address or a short MAC address.
|
||||
* @param[in] p_data Pointer to the buffer containing data to be set.
|
||||
* @param[in] length Length of @p p_data.
|
||||
* @param[in] data_type Type of data to be set. Refer to the @ref nrf_802154_ack_data_t type.
|
||||
*
|
||||
* @retval True Address successfully added to the list.
|
||||
* @retval False Not enough memory to store this address in the list.
|
||||
*/
|
||||
bool nrf_802154_ack_data_set(const uint8_t * p_addr,
|
||||
bool extended,
|
||||
const void * p_data,
|
||||
uint16_t length,
|
||||
nrf_802154_ack_data_t data_type);
|
||||
|
||||
/**
|
||||
* @brief Removes the address of a peer node for which the ACK data is set from the pending bit list.
|
||||
*
|
||||
* The ACK data that was previously set for the given address is automatically removed.
|
||||
*
|
||||
* The pending bit list works differently, depending on the upper layer for which the source
|
||||
* address matching method is selected:
|
||||
* - For Thread, @ref NRF_802154_SRC_ADDR_MATCH_THREAD
|
||||
* - For Zigbee, @ref NRF_802154_SRC_ADDR_MATCH_ZIGBEE
|
||||
* - For Standard-compliant, @ref NRF_802154_SRC_ADDR_MATCH_ALWAYS_1
|
||||
* For more information, see @ref nrf_802154_src_addr_match_t.
|
||||
*
|
||||
* The method can be set during initialization phase by calling @ref nrf_802154_src_matching_method.
|
||||
*
|
||||
* @param[in] p_addr Array of bytes containing the address of the node (little-endian).
|
||||
* @param[in] extended If the given address is an extended MAC address or a short MAC address.
|
||||
* @param[in] data_type Type of data to be removed. Refer to the @ref nrf_802154_ack_data_t type.
|
||||
*
|
||||
* @retval True Address removed from the list.
|
||||
* @retval False Address not found in the list.
|
||||
*/
|
||||
bool nrf_802154_ack_data_clear(const uint8_t * p_addr,
|
||||
bool extended,
|
||||
nrf_802154_ack_data_t data_type);
|
||||
|
||||
/**
|
||||
* @brief Enables or disables setting a pending bit in automatically transmitted ACK frames.
|
||||
*
|
||||
|
|
|
@ -131,8 +131,13 @@ extern void nrf_802154_received_timestamp_raw(uint8_t * p_data,
|
|||
* @brief Notifies that the reception of a frame failed.
|
||||
*
|
||||
* @param[in] error Error code that indicates the reason of the failure.
|
||||
* @param[in] id Identifier of reception window the error occurred in.
|
||||
* If the error is related to a delayed reception window requested through
|
||||
* @ref nrf_802154_receive_at, the value of @p id equals the identifier
|
||||
* of the scheduled reception window. Otherwise, the value of @p id equals
|
||||
* @ref NRF_802154_RESERVED_IMM_RX_WINDOW_ID.
|
||||
*/
|
||||
extern void nrf_802154_receive_failed(nrf_802154_rx_error_t error);
|
||||
extern void nrf_802154_receive_failed(nrf_802154_rx_error_t error, uint32_t id);
|
||||
|
||||
/**
|
||||
* @brief Notifies that a frame was transmitted.
|
||||
|
|
|
@ -89,6 +89,14 @@ typedef uint8_t nrf_802154_cca_error_t;
|
|||
|
||||
#define NRF_802154_CCA_ERROR_ABORTED 0x01 // !< Procedure was aborted by another operation.
|
||||
|
||||
/**
|
||||
* @brief Types of data that can be set in an ACK message.
|
||||
*/
|
||||
typedef uint8_t nrf_802154_ack_data_t;
|
||||
|
||||
#define NRF_802154_ACK_DATA_PENDING_BIT 0x00
|
||||
#define NRF_802154_ACK_DATA_IE 0x01
|
||||
|
||||
/**
|
||||
* @brief Methods of source address matching.
|
||||
*
|
||||
|
|
|
@ -254,6 +254,18 @@ typedef enum
|
|||
*/
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_CAPABILITIES_GET =
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154__BEGIN + 31,
|
||||
|
||||
/**
|
||||
* Vendor property for nrf_802154_ack_data_set serialization.
|
||||
*/
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET =
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154__BEGIN + 32,
|
||||
|
||||
/**
|
||||
* Vendor property for nrf_802154_ack_data_clear serialization.
|
||||
*/
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR =
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154__BEGIN + 33,
|
||||
} spinel_prop_vendor_key_t;
|
||||
|
||||
/**
|
||||
|
@ -424,7 +436,8 @@ typedef enum
|
|||
* @brief Spinel data type description for nrf_802154_receive_failed
|
||||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_RECEIVE_FAILED \
|
||||
SPINEL_DATATYPE_UINT8_S /* error */ \
|
||||
SPINEL_DATATYPE_UINT8_S /* error */ \
|
||||
SPINEL_DATATYPE_UINT32_S /* id */
|
||||
|
||||
/**
|
||||
* @brief Spinel data type description for nrf_802154_tx_ack_started
|
||||
|
@ -489,6 +502,35 @@ typedef enum
|
|||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_SRC_ADDR_MATCHING_METHOD_SET SPINEL_DATATYPE_UINT8_S
|
||||
|
||||
/**
|
||||
* @brief Spinel data type desription for nrf_802154_ack_data_set.
|
||||
*
|
||||
* SPINEL_DATATYPE_ARRAY_S encoding is not implemented, SPINEL_DATATYPE_DATA_S has to be used instead.
|
||||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_ACK_DATA_SET \
|
||||
SPINEL_DATATYPE_DATA_WLEN_S /* Address */ \
|
||||
SPINEL_DATATYPE_DATA_WLEN_S /* Data to be set */ \
|
||||
SPINEL_DATATYPE_UINT8_S /* Type of the data */ \
|
||||
|
||||
/**
|
||||
* @brief Spinel data type desription for nrf_802154_ack_data_set return value.
|
||||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_ACK_DATA_SET_RET SPINEL_DATATYPE_BOOL_S
|
||||
|
||||
/**
|
||||
* @brief Spinel data type desription for nrf_802154_ack_data_clear.
|
||||
*
|
||||
* SPINEL_DATATYPE_ARRAY_S encoding is not implemented, SPINEL_DATATYPE_DATA_S has to be used instead.
|
||||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_ACK_DATA_CLEAR \
|
||||
SPINEL_DATATYPE_DATA_WLEN_S /* Address */ \
|
||||
SPINEL_DATATYPE_UINT8_S /* Type of the data */
|
||||
|
||||
/**
|
||||
* @brief Spinel data type desription for nrf_802154_ack_data_clear return value.
|
||||
*/
|
||||
#define SPINEL_DATATYPE_NRF_802154_ACK_DATA_CLEAR_RET SPINEL_DATATYPE_BOOL_S
|
||||
|
||||
/**
|
||||
* @brief Spinel data type description for nrf_802154_transmit_csma_ca_raw.
|
||||
*/
|
||||
|
|
|
@ -502,6 +502,82 @@ bail:
|
|||
SERIALIZATION_ERROR_RAISE_IF_FAILED(error);
|
||||
}
|
||||
|
||||
bool nrf_802154_ack_data_set(const uint8_t * p_addr,
|
||||
bool extended,
|
||||
const void * p_data,
|
||||
uint16_t length,
|
||||
nrf_802154_ack_data_t data_type)
|
||||
{
|
||||
nrf_802154_ser_err_t res;
|
||||
bool ack_data_set_res = false;
|
||||
|
||||
SERIALIZATION_ERROR_INIT(error);
|
||||
|
||||
NRF_802154_SPINEL_LOG_BANNER_CALLING();
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
NRF_802154_SPINEL_LOG_VAR_NAMED("%s", (extended ? "true" : "false"), "extended");
|
||||
|
||||
nrf_802154_spinel_response_notifier_lock_before_request(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET);
|
||||
|
||||
res = nrf_802154_spinel_send_cmd_prop_value_set(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_SET,
|
||||
p_addr,
|
||||
extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE,
|
||||
p_data,
|
||||
length,
|
||||
data_type);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
res = net_generic_bool_response_await(&ack_data_set_res,
|
||||
CONFIG_NRF_802154_SER_DEFAULT_RESPONSE_TIMEOUT);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
bail:
|
||||
SERIALIZATION_ERROR_RAISE_IF_FAILED(error);
|
||||
|
||||
return ack_data_set_res;
|
||||
}
|
||||
|
||||
bool nrf_802154_ack_data_clear(const uint8_t * p_addr,
|
||||
bool extended,
|
||||
nrf_802154_ack_data_t data_type)
|
||||
{
|
||||
nrf_802154_ser_err_t res;
|
||||
bool ack_data_clear_res = false;
|
||||
|
||||
SERIALIZATION_ERROR_INIT(error);
|
||||
|
||||
NRF_802154_SPINEL_LOG_BANNER_CALLING();
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
NRF_802154_SPINEL_LOG_VAR_NAMED("%s", (extended ? "true" : "false"), "extended");
|
||||
|
||||
nrf_802154_spinel_response_notifier_lock_before_request(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR);
|
||||
|
||||
res = nrf_802154_spinel_send_cmd_prop_value_set(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_CLEAR,
|
||||
p_addr,
|
||||
extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE,
|
||||
data_type);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
res = net_generic_bool_response_await(&ack_data_clear_res,
|
||||
CONFIG_NRF_802154_SER_DEFAULT_RESPONSE_TIMEOUT);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
bail:
|
||||
SERIALIZATION_ERROR_RAISE_IF_FAILED(error);
|
||||
|
||||
return ack_data_clear_res;
|
||||
}
|
||||
|
||||
void nrf_802154_auto_pending_bit_set(bool enabled)
|
||||
{
|
||||
nrf_802154_ser_err_t res;
|
||||
|
@ -535,7 +611,7 @@ bool nrf_802154_pending_bit_for_addr_set(const uint8_t * p_addr, bool extended)
|
|||
SERIALIZATION_ERROR_INIT(error);
|
||||
|
||||
NRF_802154_SPINEL_LOG_BANNER_CALLING();
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? 8 : 2);
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
NRF_802154_SPINEL_LOG_VAR_NAMED("%s", (extended ? "true" : "false"), "extended");
|
||||
|
||||
nrf_802154_spinel_response_notifier_lock_before_request(
|
||||
|
@ -545,7 +621,7 @@ bool nrf_802154_pending_bit_for_addr_set(const uint8_t * p_addr, bool extended)
|
|||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_PENDING_BIT_FOR_ADDR_SET,
|
||||
SPINEL_DATATYPE_NRF_802154_PENDING_BIT_FOR_ADDR_SET,
|
||||
p_addr,
|
||||
extended ? 8 : 2);
|
||||
extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
|
@ -568,7 +644,7 @@ bool nrf_802154_pending_bit_for_addr_clear(const uint8_t * p_addr, bool extended
|
|||
SERIALIZATION_ERROR_INIT(error);
|
||||
|
||||
NRF_802154_SPINEL_LOG_BANNER_CALLING();
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? 8 : 2);
|
||||
NRF_802154_SPINEL_LOG_BUFF(p_addr, extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
NRF_802154_SPINEL_LOG_VAR_NAMED("%s", (extended ? "true" : "false"), "extended");
|
||||
|
||||
nrf_802154_spinel_response_notifier_lock_before_request(
|
||||
|
@ -578,7 +654,7 @@ bool nrf_802154_pending_bit_for_addr_clear(const uint8_t * p_addr, bool extended
|
|||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_PENDING_BIT_FOR_ADDR_CLEAR,
|
||||
SPINEL_DATATYPE_NRF_802154_PENDING_BIT_FOR_ADDR_CLEAR,
|
||||
p_addr,
|
||||
extended ? 8 : 2);
|
||||
extended ? EXTENDED_ADDRESS_SIZE : SHORT_ADDRESS_SIZE);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, error, bail);
|
||||
|
||||
|
|
|
@ -221,19 +221,21 @@ static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_receive_failed(
|
|||
const void * p_property_data,
|
||||
size_t property_data_len)
|
||||
{
|
||||
uint8_t error;
|
||||
uint8_t error;
|
||||
uint32_t id;
|
||||
|
||||
spinel_ssize_t siz = spinel_datatype_unpack(p_property_data,
|
||||
property_data_len,
|
||||
SPINEL_DATATYPE_NRF_802154_RECEIVE_FAILED,
|
||||
&error);
|
||||
&error,
|
||||
&id);
|
||||
|
||||
if (siz < 0)
|
||||
{
|
||||
return NRF_802154_SERIALIZATION_ERROR_DECODING_FAILURE;
|
||||
}
|
||||
|
||||
nrf_802154_receive_failed(error);
|
||||
nrf_802154_receive_failed(error, id);
|
||||
|
||||
return NRF_802154_SERIALIZATION_ERROR_OK;
|
||||
}
|
||||
|
@ -514,6 +516,10 @@ nrf_802154_ser_err_t nrf_802154_spinel_decode_cmd_prop_value_is(
|
|||
// fall through
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_PENDING_BIT_FOR_ADDR_CLEAR:
|
||||
// fall through
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET:
|
||||
// fall through
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR:
|
||||
// fall through
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_TRANSMIT_RAW:
|
||||
nrf_802154_spinel_response_notifier_property_notify(property,
|
||||
p_property_data,
|
||||
|
@ -594,9 +600,10 @@ __WEAK void nrf_802154_received_timestamp_raw(uint8_t * p_data,
|
|||
// Intentionally empty
|
||||
}
|
||||
|
||||
__WEAK void nrf_802154_receive_failed(nrf_802154_rx_error_t error)
|
||||
__WEAK void nrf_802154_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
(void)error;
|
||||
(void)id;
|
||||
// Intentionally empty
|
||||
}
|
||||
|
||||
|
|
|
@ -399,11 +399,11 @@ static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_pending_bit_for_addr_s
|
|||
return NRF_802154_SERIALIZATION_ERROR_DECODING_FAILURE;
|
||||
}
|
||||
|
||||
if (addr_len == 8)
|
||||
if (addr_len == EXTENDED_ADDRESS_SIZE)
|
||||
{
|
||||
extended = true;
|
||||
}
|
||||
else if (addr_len == 2)
|
||||
else if (addr_len == SHORT_ADDRESS_SIZE)
|
||||
{
|
||||
extended = false;
|
||||
}
|
||||
|
@ -448,11 +448,11 @@ static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_pending_bit_for_addr_c
|
|||
return NRF_802154_SERIALIZATION_ERROR_DECODING_FAILURE;
|
||||
}
|
||||
|
||||
if (addr_len == 8)
|
||||
if (addr_len == EXTENDED_ADDRESS_SIZE)
|
||||
{
|
||||
extended = true;
|
||||
}
|
||||
else if (addr_len == 2)
|
||||
else if (addr_len == SHORT_ADDRESS_SIZE)
|
||||
{
|
||||
extended = false;
|
||||
}
|
||||
|
@ -539,6 +539,115 @@ static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_src_addr_matching_meth
|
|||
return nrf_802154_spinel_send_prop_last_status_is(SPINEL_STATUS_OK);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Decode and dispatch SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET.
|
||||
*
|
||||
* @param[in] p_property_data Pointer to a buffer that contains data to be decoded.
|
||||
* @param[in] property_data_len Size of the @ref p_data buffer.
|
||||
*
|
||||
*/
|
||||
static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_ack_data_set(
|
||||
const void * p_property_data,
|
||||
size_t property_data_len)
|
||||
{
|
||||
void * p_addr;
|
||||
size_t addr_len;
|
||||
void * p_data;
|
||||
size_t length;
|
||||
nrf_802154_ack_data_t data_type;
|
||||
spinel_ssize_t siz;
|
||||
bool extended;
|
||||
|
||||
siz = spinel_datatype_unpack(p_property_data,
|
||||
property_data_len,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_SET,
|
||||
&p_addr,
|
||||
&addr_len,
|
||||
&p_data,
|
||||
&length,
|
||||
&data_type);
|
||||
|
||||
if (siz < 0)
|
||||
{
|
||||
return NRF_802154_SERIALIZATION_ERROR_DECODING_FAILURE;
|
||||
}
|
||||
|
||||
if (addr_len == EXTENDED_ADDRESS_SIZE)
|
||||
{
|
||||
extended = true;
|
||||
}
|
||||
else if (addr_len == SHORT_ADDRESS_SIZE)
|
||||
{
|
||||
extended = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return NRF_802154_SERIALIZATION_ERROR_REQUEST_INVALID;
|
||||
}
|
||||
|
||||
bool ack_data_set_res = nrf_802154_ack_data_set(
|
||||
(const uint8_t *)p_addr,
|
||||
extended,
|
||||
(const void *)p_data,
|
||||
(uint16_t)length,
|
||||
data_type);
|
||||
|
||||
return nrf_802154_spinel_send_cmd_prop_value_is(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_SET_RET,
|
||||
ack_data_set_res);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Decode and dispatch SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR.
|
||||
*
|
||||
* @param[in] p_property_data Pointer to a buffer that contains data to be decoded.
|
||||
* @param[in] property_data_len Size of the @ref p_data buffer.
|
||||
*
|
||||
*/
|
||||
static nrf_802154_ser_err_t spinel_decode_prop_nrf_802154_ack_data_clear(
|
||||
const void * p_property_data,
|
||||
size_t property_data_len)
|
||||
{
|
||||
const uint8_t * p_addr;
|
||||
size_t addr_len;
|
||||
bool extended;
|
||||
nrf_802154_ack_data_t data_type;
|
||||
spinel_ssize_t siz;
|
||||
|
||||
siz = spinel_datatype_unpack(p_property_data,
|
||||
property_data_len,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_CLEAR,
|
||||
&p_addr,
|
||||
&addr_len,
|
||||
&data_type);
|
||||
|
||||
if (siz < 0)
|
||||
{
|
||||
return NRF_802154_SERIALIZATION_ERROR_DECODING_FAILURE;
|
||||
}
|
||||
|
||||
if (addr_len == EXTENDED_ADDRESS_SIZE)
|
||||
{
|
||||
extended = true;
|
||||
}
|
||||
else if (addr_len == SHORT_ADDRESS_SIZE)
|
||||
{
|
||||
extended = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return NRF_802154_SERIALIZATION_ERROR_REQUEST_INVALID;
|
||||
}
|
||||
|
||||
bool ack_data_clear_res = nrf_802154_ack_data_clear(p_addr, extended, data_type);
|
||||
|
||||
return nrf_802154_spinel_send_cmd_prop_value_is(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR,
|
||||
SPINEL_DATATYPE_NRF_802154_ACK_DATA_CLEAR_RET,
|
||||
ack_data_clear_res);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Decode and dispatch SPINEL_DATATYPE_NRF_802154_TRANSMIT_CSMA_CA_RAW.
|
||||
*
|
||||
|
@ -864,6 +973,14 @@ nrf_802154_ser_err_t nrf_802154_spinel_decode_cmd_prop_value_set(const void * p_
|
|||
return spinel_decode_prop_nrf_802154_capabilities_get(p_property_data,
|
||||
property_data_len);
|
||||
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_SET:
|
||||
return spinel_decode_prop_nrf_802154_ack_data_set(p_property_data,
|
||||
property_data_len);
|
||||
|
||||
case SPINEL_PROP_VENDOR_NORDIC_NRF_802154_ACK_DATA_CLEAR:
|
||||
return spinel_decode_prop_nrf_802154_ack_data_clear(p_property_data,
|
||||
property_data_len);
|
||||
|
||||
default:
|
||||
NRF_802154_SPINEL_LOG_RAW("Unsupported property: %s(%u)\n",
|
||||
spinel_prop_key_to_cstr(property),
|
||||
|
|
|
@ -253,7 +253,7 @@ bail:
|
|||
return;
|
||||
}
|
||||
|
||||
void nrf_802154_receive_failed(nrf_802154_rx_error_t error)
|
||||
void nrf_802154_receive_failed(nrf_802154_rx_error_t error, uint32_t id)
|
||||
{
|
||||
nrf_802154_ser_err_t res;
|
||||
|
||||
|
@ -269,7 +269,8 @@ void nrf_802154_receive_failed(nrf_802154_rx_error_t error)
|
|||
res = nrf_802154_spinel_send_cmd_prop_value_is(
|
||||
SPINEL_PROP_VENDOR_NORDIC_NRF_802154_RECEIVE_FAILED,
|
||||
SPINEL_DATATYPE_NRF_802154_RECEIVE_FAILED,
|
||||
error);
|
||||
error,
|
||||
id);
|
||||
|
||||
SERIALIZATION_ERROR_CHECK(res, ser_error, bail);
|
||||
|
||||
|
|
|
@ -61,6 +61,35 @@ extern "C" {
|
|||
* granted access to the RADIO peripheral.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief Maximum number of DTX delayed timeslots that can be scheduled simultaneously.
|
||||
*/
|
||||
#ifndef NRF_802154_RSCH_DLY_TS_OP_DTX_SLOTS
|
||||
#define NRF_802154_RSCH_DLY_TS_OP_DTX_SLOTS 1
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Maximum number of DRX delayed timeslots that can be scheduled simultaneously.
|
||||
*/
|
||||
#ifndef NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS
|
||||
#define NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS 2
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Maximum number of CSMA/CA delayed timeslots that can be scheduled simultaneously.
|
||||
*/
|
||||
#ifndef NRF_802154_RSCH_DLY_TS_OP_CSMACA_SLOTS
|
||||
#define NRF_802154_RSCH_DLY_TS_OP_CSMACA_SLOTS 1
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Number of available slots for all delayed timeslots.
|
||||
*/
|
||||
#define NRF_802154_RSCH_DLY_TS_SLOTS \
|
||||
NRF_802154_RSCH_DLY_TS_OP_DTX_SLOTS + \
|
||||
NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS + \
|
||||
NRF_802154_RSCH_DLY_TS_OP_CSMACA_SLOTS
|
||||
|
||||
/**
|
||||
* @brief List of the preconditions that have to be met before any radio activity.
|
||||
*/
|
||||
|
@ -88,16 +117,19 @@ typedef enum
|
|||
} rsch_prio_t;
|
||||
|
||||
/**
|
||||
* @brief Enumeration of the delayed timeslot IDs.
|
||||
* @brief Enumeration of the delayed timeslot operation types.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
RSCH_DLY_TX, ///< Timeslot for delayed TX operation.
|
||||
RSCH_DLY_RX, ///< Timeslot for delayed RX operation.
|
||||
RSCH_DLY_CSMACA, ///< Timeslot for CSMA/CA operation.
|
||||
RSCH_DLY_TS_OP_DTX, ///< Timeslot for delayed TX operation.
|
||||
RSCH_DLY_TS_OP_DRX, ///< Timeslot for delayed RX operation.
|
||||
RSCH_DLY_TS_OP_CSMACA, ///< Timeslot for CSMA/CA operation.
|
||||
} rsch_dly_ts_op_t;
|
||||
|
||||
RSCH_DLY_TS_NUM, ///< Number of delayed timeslots.
|
||||
} rsch_dly_ts_id_t;
|
||||
/**
|
||||
* @brief Identifier of a delayed timeslot.
|
||||
*/
|
||||
typedef uint32_t rsch_dly_ts_id_t;
|
||||
|
||||
/**
|
||||
* @brief Enumeration of the precondition requesting strategies.
|
||||
|
@ -121,6 +153,8 @@ typedef enum
|
|||
|
||||
/**
|
||||
* @brief Function pointer used for notifying about delayed timeslot start.
|
||||
*
|
||||
* @param[in] dly_ts_id Identifier of the started delayed timeslot.
|
||||
*/
|
||||
typedef void (* rsch_dly_ts_started_callback_t)(rsch_dly_ts_id_t dly_ts_id);
|
||||
|
||||
|
@ -132,9 +166,10 @@ typedef struct
|
|||
uint32_t t0; ///< Base time of the timestamp of the timeslot start, in microseconds.
|
||||
uint32_t dt; ///< Time delta between @p t0 and the timestamp of the timeslot start, in microseconds.
|
||||
rsch_prio_t prio; ///< Priority level required for the delayed timeslot.
|
||||
rsch_dly_ts_id_t id; ///< ID of the requested timeslot.
|
||||
rsch_dly_ts_op_t op; ///< Operation to be performed in the requested timeslot.
|
||||
rsch_dly_ts_type_t type; ///< Type of the requested timeslot.
|
||||
rsch_dly_ts_started_callback_t started_callback; ///< Callback called when delayed timeslot starts.
|
||||
rsch_dly_ts_id_t id; ///< Identifier of the timeslot provided by its owner. Its value must be unique, to unambigously map to an active slot.
|
||||
} rsch_dly_ts_param_t;
|
||||
|
||||
/**
|
||||
|
@ -200,12 +235,26 @@ bool nrf_802154_rsch_timeslot_request(uint32_t length_us);
|
|||
* the timeslot is supposed to start and how long it is to last. When the requested timeslot starts,
|
||||
* @p p_dly_ts_param->started_callback is called.
|
||||
*
|
||||
* For a given type of operation to be performed in the delayed timeslot, @p p_dly_ts_param->op,
|
||||
* there's a limited number of delayed timeslots that can be scheduled at the same time:
|
||||
* - for delayed transmissions it's @ref NRF_802154_RSCH_DLY_TS_OP_DTX_SLOTS;
|
||||
* - for delayed receptions it's @ref NRF_802154_RSCH_DLY_TS_OP_DRX_SLOTS;
|
||||
* - for CSMA/CA it's @ref NRF_802154_RSCH_DLY_TS_OP_CSMACA_SLOTS.
|
||||
*
|
||||
* If the API user requests more delayed timeslots with given @p p_dly_ts_param->op than specified
|
||||
* by these constants, the request will fail unconditionally. It also implies that there can only
|
||||
* be as many delayed timeslots scheduled simultaneously in total as the sum of these constants.
|
||||
*
|
||||
* @note Every call to this function must be paired with a call to
|
||||
* @ref nrf_802154_rsch_delayed_timeslot_cancel so that the assigned slot becomes
|
||||
* available for future requests.
|
||||
*
|
||||
* @note @p p_dly_ts_param->started_callback can be delayed and it is up to
|
||||
* the called module to check the delay and decide if it causes any issues.
|
||||
*
|
||||
* @note The time parameters use the same units that are used in the Timer Scheduler module.
|
||||
*
|
||||
* @param[in] p_dly_ts_param Parameters of the requested delayed timeslot.
|
||||
* @param[in] p_dly_ts_param Parameters of the requested delayed timeslot.
|
||||
*
|
||||
* @retval true Requested timeslot has been scheduled.
|
||||
* @retval false Requested timeslot cannot be scheduled and will not be granted.
|
||||
|
@ -215,7 +264,8 @@ bool nrf_802154_rsch_delayed_timeslot_request(const rsch_dly_ts_param_t * p_dly_
|
|||
/**
|
||||
* @brief Cancels a requested future timeslot.
|
||||
*
|
||||
* @param[in] dly_ts_id ID of the requested timeslot.
|
||||
* @param[in] dly_ts_id Identifier of the requested timeslot. If the provided value does not refer
|
||||
* to any scheduled delayed timeslot, the function returns false.
|
||||
*
|
||||
* @retval true Scheduled timeslot has been cancelled.
|
||||
* @retval false No scheduled timeslot has been requested (nothing to cancel).
|
||||
|
@ -225,7 +275,9 @@ bool nrf_802154_rsch_delayed_timeslot_cancel(rsch_dly_ts_id_t dly_ts_id);
|
|||
/**
|
||||
* @brief Updates priority of a requested delayed timeslot.
|
||||
*
|
||||
* @param[in] dly_ts_id ID of the requested timeslot.
|
||||
* @param[in] dly_ts_id Identifier of the requested timeslot. If the provided value does not
|
||||
* refer to any scheduled or active delayed timeslot, the function
|
||||
* returns false.
|
||||
* @param[in] dly_ts_prio Priority to be assigned to the requested timeslot.
|
||||
*
|
||||
* @retval true Scheduled timeslot's priority has been updated.
|
||||
|
|
Loading…
Reference in New Issue