/***************************************************************************//**
* @file
* @brief The BLE specific header file for the RAIL library.
*******************************************************************************
* # License
* Copyright 2020 Silicon Laboratories Inc. www.silabs.com
*******************************************************************************
*
* SPDX-License-Identifier: Zlib
*
* The licensor of this software is Silicon Laboratories Inc.
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
******************************************************************************/
#ifndef __RAIL_BLE_H__
#define __RAIL_BLE_H__
// Get the standard include types
#include
#include
// Get the RAIL specific structures and types
#include "rail_types.h"
#ifdef __cplusplus
extern "C" {
#endif
/// @addtogroup BLE
/// @ingroup Protocol_Specific
/// Accelerator routines for Bluetooth Low Energy (BLE).
///
/// The APIs in this module configure the radio for BLE
/// operation and provide additional helper routines necessary for
/// normal BLE send/receive that aren't available directly in RAIL.
/// RAIL APIs should be used to set up the application. However,
/// RAIL_ConfigChannels() and RAIL_ConfigRadio() should not be called to set up
/// the PHY. Instead, RAIL_BLE_Config* APIs should be used to set up the
/// 1 Mbps, 2 Mbps, or Coded PHY configurations needed by the application. These
/// APIs will configure the hardware and also configure the set of valid BLE
/// channels.
///
/// To implement a standard BLE link layer, you will also need to handle tight
/// turnaround times and send packets at specific instants. This can all be
/// managed through general RAIL functions, such as RAIL_ScheduleTx(),
/// RAIL_ScheduleRx(), and RAIL_SetStateTiming(). See RAIL APIs for more
/// useful functions.
///
/// A simple example to set up the application to be in BLE mode is shown
/// below. Note that this will put the radio on the first advertising channel
/// with the advertising Access Address. In any full-featured BLE application you
/// will need to use the RAIL_BLE_ConfigChannelRadioParams() function to change
/// the sync word and other parameters as needed based on your connection.
///
/// @code{.c}
///
/// // RAIL Handle set at initialization time.
/// static RAIL_Handle_t gRailHandle = NULL;
///
/// static void radioEventHandler(RAIL_Handle_t railHandle,
/// RAIL_Events_t events)
/// {
/// // ... handle RAIL events, e.g., receive and transmit completion
/// }
///
/// #if MULTIPROTOCOL
/// // Allocate memory for RAIL to hold BLE-specific state information
/// static RAIL_BLE_State_t bleState; // Must never be const
/// static RAILSched_Config_t schedCfg; // Must never be const
/// static RAIL_Config_t railCfg = { // Must never be const
/// .eventsCallback = &radioEventHandler,
/// .protocol = &bleState, // For BLE, RAIL needs additional state memory
/// .scheduler = &schedCfg, // For MultiProtocol, additional scheduler memory
/// };
/// #else
/// static RAIL_Config_t railCfg = { // Must never be const
/// .eventsCallback = &radioEventHandler,
/// .protocol = NULL,
/// .scheduler = NULL,
/// };
/// #endif
///
/// // Set the radio to receive on the first BLE advertising channel.
/// int bleAdvertiseEnable(void)
/// {
/// // Initializes the RAIL library and any internal state it requires.
/// gRailHandle = RAIL_Init(&railCfg, NULL);
///
/// // Calls the BLE initialization function to load the right radio configuration.
/// RAIL_BLE_Init(gRailHandle);
///
/// // Always choose the Viterbi PHY configuration if available on your chip
/// // for performance reasons.
/// RAIL_BLE_ConfigPhy1MbpsViterbi(gRailHandle);
///
/// // Configures us for the first advertising channel (Physical: 0, Logical: 37).
/// // The CRC init value and Access Address come from the BLE specification.
/// RAIL_BLE_ConfigChannelRadioParams(gRailHandle,
/// 0x555555,
/// 0x8E89BED6,
/// 37,
/// false);
///
/// // Starts receiving on physical channel 0 (logical channel 37).
/// RAIL_StartRx(gRailHandle, 0, NULL);
/// }
/// @endcode
///
/// @{
/**
* @enum RAIL_BLE_Coding_t
* @brief The variant of the BLE Coded PHY.
*/
RAIL_ENUM(RAIL_BLE_Coding_t) {
/** Enables the 125 kbps variant of the BLE Coded PHY */
RAIL_BLE_Coding_125kbps = 0,
/** @deprecated Will be removed in a future version of RAIL */
RAIL_BLE_Coding_125kbps_DSA = 1,
/** Enables the 500 kbps variant of the BLE Coded PHY */
RAIL_BLE_Coding_500kbps = 2,
/** @deprecated Will be removed in a future version of RAIL */
RAIL_BLE_Coding_500kbps_DSA = 3,
};
#ifndef DOXYGEN_SHOULD_SKIP_THIS
// Self-referencing defines minimize compiler complaints when using RAIL_ENUM
#define RAIL_BLE_Coding_125kbps ((RAIL_BLE_Coding_t) RAIL_BLE_Coding_125kbps)
#define RAIL_BLE_Coding_125kbps_DSA ((RAIL_BLE_Coding_t) RAIL_BLE_Coding_125kbps_DSA)
#define RAIL_BLE_Coding_500kbps ((RAIL_BLE_Coding_t) RAIL_BLE_Coding_500kbps)
#define RAIL_BLE_Coding_500kbps_DSA ((RAIL_BLE_Coding_t) RAIL_BLE_Coding_500kbps_DSA)
#endif //DOXYGEN_SHOULD_SKIP_THIS
/**
* @enum RAIL_BLE_Phy_t
* @brief The variant of the BLE PHY.
*/
RAIL_ENUM(RAIL_BLE_Phy_t) {
/** Use the standard BLE 1Mbps PHY */
RAIL_BLE_1Mbps,
/** Use the high data rate BLE 2Mbps PHY */
RAIL_BLE_2Mbps,
/** Enables the 125 kbps variant of the BLE Coded PHY */
RAIL_BLE_Coded125kbps,
/** Enables the 500 kbps variant of the BLE Coded PHY */
RAIL_BLE_Coded500kbps,
};
#ifndef DOXYGEN_SHOULD_SKIP_THIS
// Self-referencing defines minimize compiler complaints when using RAIL_ENUM
#define RAIL_BLE_1Mbps ((RAIL_BLE_Phy_t) RAIL_BLE_1Mbps)
#define RAIL_BLE_2Mbps ((RAIL_BLE_Phy_t) RAIL_BLE_2Mbps)
#define RAIL_BLE_Coded125kbps ((RAIL_BLE_Phy_t) RAIL_BLE_Coded125kbps)
#define RAIL_BLE_Coded500kbps ((RAIL_BLE_Phy_t) RAIL_BLE_Coded500kbps)
#endif //DOXYGEN_SHOULD_SKIP_THIS
/// @addtogroup BLE_PHY BLE Radio Configurations
/// Radio configurations for the RAIL BLE Accelerator
///
/// These radio configurations are used to configure BLE when a function such
/// as \ref RAIL_BLE_ConfigPhy1MbpsViterbi() is called. Each radio
/// configuration listed below is compiled into the RAIL library as a weak
/// symbol that will take into account per-die defaults. If the board
/// configuration in use has different settings than the default, such as a
/// different radio subsystem clock frequency, these radio configurations can
/// be overriden to account for those settings.
/// @{
/**
* Default PHY to use for BLE 1M non-Viterbi. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_1MBPS_NON_VITERBI is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy1Mbps;
/**
* Default PHY to use for BLE 2M non-Viterbi. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_2MBPS_NON_VITERBI is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy2Mbps;
/**
* Default PHY to use for BLE 1M Viterbi. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_1MBPS_VITERBI is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy1MbpsViterbi;
/**
* Default PHY to use for BLE 2M Viterbi. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_2MBPS_VITERBI is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy2MbpsViterbi;
/**
* PHY to use for BLE 2M with AoX functionality. Will be NULL if either
* \ref RAIL_BLE_SUPPORTS_2MBPS_VITERBI or \ref RAIL_BLE_SUPPORTS_AOX is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy2MbpsAox;
/**
* Default PHY to use for BLE Coded 125kbps. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_CODED_PHY is 0. This PHY can receive on both
* 125kbps and 500kbps BLE Coded, but will only transmit at 125kbps.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy125kbps;
/**
* Default PHY to use for BLE Coded 500kbps. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_CODED_PHY is 0. This PHY can receive on both
* 125kbps and 500kbps BLE Coded, but will only transmit at 125kbps.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_Phy500kbps;
/**
* Default PHY to use for BLE Simulscan. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_SIMULSCAN_PHY is 0. This PHY can receive on 1Mbps
* as well as 125kbps and 500kbps BLE Coded, but will only transmit at 1Mbps.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_PhySimulscan;
/**
* Default 1Mbps Quuppa PHY. Will be NULL if
* \ref RAIL_BLE_SUPPORTS_QUUPPA is 0.
*/
extern const RAIL_ChannelConfig_t *const RAIL_BLE_PhyQuuppa;
/// @} // End of group BLE_PHY
// Defines for subPhyID field in RAIL_RxPacketDetails_t
/** subPhyId indicating a 500kbps packet */
#define RAIL_BLE_RX_SUBPHY_ID_500K (0U)
/** subPhyId indicating a 125kbps packet */
#define RAIL_BLE_RX_SUBPHY_ID_125K (1U)
/** subPhyId value indicating a 1Mbps packet */
#define RAIL_BLE_RX_SUBPHY_ID_1M (2U)
/** Invalid subPhyId value */
#define RAIL_BLE_RX_SUBPHY_ID_INVALID (3U)
/** subPhyId indicating the total count */
#define RAIL_BLE_RX_SUBPHY_COUNT (4U)
/**
* @enum RAIL_BLE_SignalIdentifierMode_t
* @brief Available Signal Identifier modes.
*/
RAIL_ENUM(RAIL_BLE_SignalIdentifierMode_t) {
/* Disable signal detection mode. */
RAIL_BLE_SIGNAL_IDENTIFIER_MODE_DISABLE = 0,
/* BLE 1Mbps (GFSK) detection mode. */
RAIL_BLE_SIGNAL_IDENTIFIER_MODE_1MBPS,
/* BLE 2Mbps (GFSK) detection mode. */
RAIL_BLE_SIGNAL_IDENTIFIER_MODE_2MBPS
};
#ifndef DOXYGEN_SHOULD_SKIP_THIS
// Self-referencing defines minimize compiler complaints when using RAIL_ENUM
#define RAIL_BLE_SIGNAL_IDENTIFIER_MODE_DISABLE ((RAIL_BLE_SignalIdentifierMode_t)RAIL_BLE_SIGNAL_IDENTIFIER_MODE_DISABLE)
#define RAIL_BLE_SIGNAL_IDENTIFIER_MODE_1MBPS ((RAIL_BLE_SignalIdentifierMode_t)RAIL_BLE_SIGNAL_IDENTIFIER_MODE_1MBPS)
#define RAIL_BLE_SIGNAL_IDENTIFIER_MODE_2MBPS ((RAIL_BLE_SignalIdentifierMode_t)RAIL_BLE_SIGNAL_IDENTIFIER_MODE_2MBPS)
#endif
/**
* @struct RAIL_BLE_State_t
* @brief A state structure for BLE.
*
* This structure must be allocated in application global read-write memory
* that persists for the duration of BLE usage. It cannot be allocated
* in read-only memory or on the call stack.
*/
typedef struct RAIL_BLE_State {
uint32_t crcInit; /**< The value used to initialize the CRC algorithm. */
uint32_t accessAddress; /**< The access address used for the connection. */
uint16_t channel; /**< The logical channel used. */
bool disableWhitening; /**< Indicates whether the whitening engine should be off. */
} RAIL_BLE_State_t;
/**
* Configure RAIL to run in BLE mode.
*
* @param[in] railHandle A handle for RAIL instance.
* This function changes your radio, channel configuration, and other
* parameters to match what is needed for BLE. To switch back to a
* default RAIL mode, call RAIL_BLE_Deinit() first. This function
* will configure the protocol output on PTI to \ref RAIL_PTI_PROTOCOL_BLE.
*
* @note BLE may not be enabled while Auto-ACKing is enabled.
*/
void RAIL_BLE_Init(RAIL_Handle_t railHandle);
/**
* Take RAIL out of BLE mode.
*
* @param[in] railHandle A handle for RAIL instance.
* This function will undo some of the configuration that happens when you call
* RAIL_BLE_Init(). After this you can safely run your normal radio
* initialization code to use a non-BLE configuration. This function does \b
* not change back your radio or channel configurations so you must do this by
* manually reinitializing. This also resets the protocol output on PTI to \ref
* RAIL_PTI_PROTOCOL_CUSTOM.
*/
void RAIL_BLE_Deinit(RAIL_Handle_t railHandle);
/**
* Determine whether BLE mode is enabled or not.
*
* @param[in] railHandle A handle for RAIL instance.
* @return True if BLE mode is enabled and false otherwise.
* This function returns the current status of RAIL's BLE mode. It is enabled by
* a call to RAIL_BLE_Init() and disabled by a call to RAIL_BLE_Deinit().
*/
bool RAIL_BLE_IsEnabled(RAIL_Handle_t railHandle);
/**
* Switch to the 1 Mbps Quuppa PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return Status code indicating success of the function call.
*
* You can use this function to switch to the Quuppa PHY.
*
* @note Not all chips support the 1Mbps Quuppa PHY. This API should return RAIL_STATUS_INVALID_CALL if
* unsupported by the hardware we're building for.
*/
RAIL_Status_t RAIL_BLE_ConfigPhyQuuppa(RAIL_Handle_t railHandle);
/**
* Switch to the Viterbi 1 Mbps BLE PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return A status code indicating success of the function call.
*
* Use this function to switch back to the default BLE 1 Mbps PHY if you
* have switched to the 2 Mbps or another configuration. You may only call this
* function after initializing BLE and while the radio is idle.
*
* @note The EFR32XG1 family does not support BLE Viterbi PHYs. However, calls
* to this function from that family will be silently redirected to the legacy
* \ref RAIL_BLE_ConfigPhy1Mbps().
*/
RAIL_Status_t RAIL_BLE_ConfigPhy1MbpsViterbi(RAIL_Handle_t railHandle);
/**
* Switch to the legacy non-Viterbi 1 Mbps BLE PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return A status code indicating success of the function call.
*
* Use this function to switch back to the legacy BLE 1 Mbps PHY if you
* have switched to the 2 Mbps or another configuration. You may only call this
* function after initializing BLE and while the radio is idle.
*
* @note The EFR32XG2x family does not support BLE non-Viterbi PHYs.
*/
RAIL_Status_t RAIL_BLE_ConfigPhy1Mbps(RAIL_Handle_t railHandle);
/**
* Switch to the Viterbi 2 Mbps BLE PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return A status code indicating success of the function call.
*
* Use this function to switch back to the BLE 2 Mbps PHY from the
* default 1 Mbps option. You may only call this function after initializing BLE
* and while the radio is idle.
*
* @note The EFR32XG1 family does not support BLE Viterbi PHYs.
*/
RAIL_Status_t RAIL_BLE_ConfigPhy2MbpsViterbi(RAIL_Handle_t railHandle);
/**
* Switch to the legacy non-Viterbi 2 Mbps BLE PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return A status code indicating success of the function call.
*
* Use this function to switch back to legacy BLE 2Mbps PHY from the
* default 1 Mbps option. You may only call this function after initializing BLE
* and while the radio is idle.
*
* @note The EFR32XG1 and EFR32XG2x families do not support BLE non-Viterbi
* 2 Mbps PHY.
*/
RAIL_Status_t RAIL_BLE_ConfigPhy2Mbps(RAIL_Handle_t railHandle);
/**
* Switch to the BLE Coded PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @param[in] bleCoding The RAIL_BLE_Coding_t to use
* @return A status code indicating success of the function call.
*
* Use this function to switch back to BLE Coded PHY from the default
* 1 Mbps option. You may only call this function after initializing BLE and
* while the radio is idle. When using a BLE Coded PHY, the \ref
* RAIL_RxPacketDetails_t::subPhyId marks the coding of the received packet.
* A subPhyId of 0 marks a 500 kbps packet, and a subPhyId of 1 marks a 125
* kbps packet.
*
* @note The EFR32XG1, EFR32XG12, and EFR32XG14 families do not support BLE
* Coded PHYs.
*/
RAIL_Status_t RAIL_BLE_ConfigPhyCoded(RAIL_Handle_t railHandle,
RAIL_BLE_Coding_t bleCoding);
/**
* Switch to the Simulscan PHY.
*
* @param[in] railHandle A handle for RAIL instance.
* @return A status code indicating success of the function call.
*
* Use this function to switch to the BLE Simulscan PHY. You may only
* call this function after initializing BLE and while the radio is idle.
* When using Simulscan PHY, the \ref RAIL_RxPacketDetails_t::subPhyId
* marks the coding of the received packet. A subPhyId of 0 marks a
* 500 kbps packet, a subPhyId of 1 marks a 125 kbps packet, and a
* subPhyId of 2 marks a 1 Mbps packet.
*
* @note: The Simulscan PHY is supported only on some 2.4 GHz Series-2 parts.
* The preprocessor symbol \ref RAIL_BLE_SUPPORTS_SIMULSCAN_PHY and the
* runtime function \ref RAIL_BLE_SupportsSimulscanPhy() may be used to
* test for support of the Simulscan PHY.
*/
RAIL_Status_t RAIL_BLE_ConfigPhySimulscan(RAIL_Handle_t railHandle);
/**
* Change BLE radio parameters.
*
* @param[in] railHandle A handle for RAIL instance.
* @param[in] crcInit The value to use for CRC initialization.
* @param[in] accessAddress The access address to use for the connection. The
* bits of this parameter are transmitted or received LSB first.
* @param[in] channel The logical channel that you're changing to, which
* initializes the whitener if used.
* @param[in] disableWhitening This can turn off the whitening engine and is useful
* for sending BLE test mode packets that don't have this turned on.
* @return A status code indicating success of the function call.
*
* This function can be used to switch radio parameters on every connection
* and/or channel change. It is BLE-aware and will set the access address,
* preamble, CRC initialization value, and whitening configuration without
* requiring you to load a new radio configuration. This function should not be
* called while the radio is active.
*/
RAIL_Status_t RAIL_BLE_ConfigChannelRadioParams(RAIL_Handle_t railHandle,
uint32_t crcInit,
uint32_t accessAddress,
uint16_t channel,
bool disableWhitening);
/**
* Change the current BLE PHY and go into receive.
*
* @param[in] railHandle A handle for RAIL instance.
* @param[in] phy Indicates which PHY to receive on
* @param[in] railChannel Which channel of the given PHY to receive on
* @param[in] startRxTime When to enter RX
* @param[in] crcInit The value to use for CRC initialization.
* @param[in] accessAddress The access address to use for the connection. The
* bits of this parameter are transmitted or received LSB first.
* @param[in] logicalChannel The logical channel that you're changing to, which
* initializes the whitener if used.
* @param[in] disableWhitening This can turn off the whitening engine and is useful
* for sending BLE test mode packets that don't have this turned on.
* @return A status code indicating success of the function call.
*
* This function is used to implement auxiliary packet reception, as defined in
* the BLE specification. The radio will be put into IDLE, the PHY and channel
* will be changed, and then receive will be entered at the start time given.
* The new receive will have a timeout of 30 us, which means that this function
* should only be called if the offset unit is 30 us.
*
* This function is extremely time-sensitive, and may only be called within the
* interrupt context of a \ref RAIL_EVENT_RX_PACKET_RECEIVED event.
*/
RAIL_Status_t RAIL_BLE_PhySwitchToRx(RAIL_Handle_t railHandle,
RAIL_BLE_Phy_t phy,
uint16_t railChannel,
uint32_t startRxTime,
uint32_t crcInit,
uint32_t accessAddress,
uint16_t logicalChannel,
bool disableWhitening);
/**
* Configure and enable signal identifier for BLE signal detection.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] signalIdentifierMode Mode of signal identifier operation.
*
* This features allows detection of BLE signal on air based on the mode.
* This function must be called once before \ref RAIL_BLE_EnableSignalDetection
* to configure and enable signal identifier.
*
* To enable event for signal detection \ref RAIL_ConfigEvents() must be called
* for enabling \ref RAIL_EVENT_SIGNAL_DETECTED.
*
* This function is only supported by chips where
* \ref RAIL_BLE_SUPPORTS_SIGNAL_IDENTIFIER and
* \ref RAIL_BLE_SupportsSignalIdentifier() are true.
*
* @return Status code indicating success of the function call.
*/
RAIL_Status_t RAIL_BLE_ConfigSignalIdentifier(RAIL_Handle_t railHandle,
RAIL_BLE_SignalIdentifierMode_t signalIdentifierMode);
/**
* Enable or Disable signal identifier interrupt for BLE signal detection.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] enable Signal detection is enabled if true, disabled if false.
*
* \ref RAIL_BLE_ConfigSignalIdentifier must be called once before calling this
* function to configure and enable signal identifier.
* Once a signal is detected signal detection will be turned off and this
* function should be called to re-enable the signal detection without needing
* to call \ref RAIL_BLE_ConfigSignalIdentifier if the signal identifier
* is already configured and enabled.
*
* This function is only supported by chips where
* \ref RAIL_BLE_SUPPORTS_SIGNAL_IDENTIFIER and
* \ref RAIL_BLE_SupportsSignalIdentifier() are true.
*
* @return Status code indicating success of the function call.
*/
RAIL_Status_t RAIL_BLE_EnableSignalDetection(RAIL_Handle_t railHandle,
bool enable);
/**
* @brief Backward compatible name for the \ref
* RAIL_BLE_EnableSignalDetection API.
*/
#define RAIL_BLE_EnableSignalIdentifier RAIL_BLE_EnableSignalDetection
/******************************************************************************
* Angle of Arrival/Departure (AoX)
*****************************************************************************/
/**
* @addtogroup AoX Angle of Arrival/Departure
* @{
* @brief These APIs are to a stack implementing BLE's angle of arrival and
* angle of departure functionality.
*
* They are designed for use by the Silicon Labs BLE stack only at this time and
* may cause problems if accessed directly.
*/
/**
*
* The maximum number of GPIO pins used for AoX Antenna switching.
*
* If the user configures more pins using
* \ref RAIL_BLE_ConfigAoxAntenna than allowed
* \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT, then
* \ref RAIL_STATUS_INVALID_PARAMETER status will be returned.
*
* \ref RAIL_STATUS_INVALID_CALL is returned if :
* \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT is set to 0 or
* The user configures no pins.
*
* The maximum value \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT can take depends on
* number of Antenna route pins , a chip provides.
* For EFR32XG22, the maximum value of \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT is 6.
* If the user configures fewer pins than \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT,
* then only number of pins asked by user will be configured with
* \ref RAIL_STATUS_NO_ERROR.
*
*/
#define RAIL_BLE_AOX_ANTENNA_PIN_COUNT (6U)
/**
* @enum RAIL_BLE_AoxOptions_t
* @brief Angle of Arrival/Departure options bit fields
*/
RAIL_ENUM_GENERIC(RAIL_BLE_AoxOptions_t, uint16_t) {
/** Shift position of \ref RAIL_BLE_AOX_OPTIONS_SAMPLE_MODE bit */
RAIL_BLE_AOX_OPTIONS_SAMPLE_MODE_SHIFT = 0,
/** Shift position of \ref RAIL_BLE_AOX_OPTIONS_CONNLESS bit */
RAIL_BLE_AOX_OPTIONS_CONNLESS_SHIFT = 1,
/** Shift position of \ref RAIL_BLE_AOX_OPTIONS_CONN bit */
RAIL_BLE_AOX_OPTIONS_CONN_SHIFT = 2,
/** Shift position of \ref RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK bit */
RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK_SHIFT = 3,
};
/**
* @deprecated Obsolete AOX option
*/
#define RAIL_BLE_AOX_OPTIONS_DO_SWITCH (0U)
/**
* @deprecated Obsolete AOX option
*/
#define RAIL_BLE_AOX_OPTIONS_TX_ENABLED (0U)
/**
* @deprecated Obsolete AOX option
*/
#define RAIL_BLE_AOX_OPTIONS_RX_ENABLED (0U)
/**
* @deprecated Please use \ref RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK_SHIFT instead.
*/
#define RAIL_BLE_AOX_OPTIONS_LOCK_CTE_BUFFER_SHIFT RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK_SHIFT
/**
* Disable the AoX feature.
*/
#define RAIL_BLE_AOX_OPTIONS_DISABLED (0U)
/**
* Sets one of the two AoX sampling/switching modes: 1 us or 2 us window.
*/
#define RAIL_BLE_AOX_OPTIONS_SAMPLE_MODE (1U << RAIL_BLE_AOX_OPTIONS_SAMPLE_MODE_SHIFT)
/**
* Enables connectionless AoX Rx packets.
*/
#define RAIL_BLE_AOX_OPTIONS_CONNLESS (1U << RAIL_BLE_AOX_OPTIONS_CONNLESS_SHIFT)
/**
* Enables connection based AoX Rx packets.
*/
#define RAIL_BLE_AOX_OPTIONS_CONN (1U << RAIL_BLE_AOX_OPTIONS_CONN_SHIFT)
/**
* Disables CTE buffer lock.
*/
#define RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK (1U << RAIL_BLE_AOX_OPTIONS_DISABLE_BUFFER_LOCK_SHIFT)
/**
* Enables connection based or connectionless AoX Rx packets.
*/
#define RAIL_BLE_AOX_OPTIONS_ENABLED (RAIL_BLE_AOX_OPTIONS_CONN | RAIL_BLE_AOX_OPTIONS_CONNLESS)
/**
* @struct RAIL_BLE_AoxConfig_t
* @brief Contains arguments for \ref RAIL_BLE_ConfigAox function.
*/
typedef struct RAIL_BLE_AoxConfig {
/**
* See RAIL_BLE_AOX_OPTIONS_* for bitfield defines for different AoX features.
*/
RAIL_BLE_AoxOptions_t aoxOptions;
/**
* Size of the raw AoX CTE (continuous tone extension) data capture buffer in
* bytes.
*/
uint16_t cteBuffSize;
/**
* Address to where the received CTE is written.
*/
uint32_t * cteBuffAddr;
/**
* Address to first element of antenna pattern array. Array must be in RAM.
* Each element of the array contains an antenna number. The switching pattern
* is defined by the order of antennas in this array.
*/
uint8_t * antArrayAddr;
/**
* Size of the antenna pattern array.
*/
uint8_t antArraySize;
} RAIL_BLE_AoxConfig_t;
/**
* @struct RAIL_BLE_AoxAntennaPortPins_t
* @brief Contains elements of \ref RAIL_BLE_AoxAntennaConfig_t struct.
*/
typedef struct RAIL_BLE_AoxAntennaPortPins {
/**
* The port which is used for AoX antenna switching
*/
uint8_t antPort;
/**
* The pin which is used for AoX antenna switching
*/
uint8_t antPin;
} RAIL_BLE_AoxAntennaPortPins_t;
/**
* @struct RAIL_BLE_AoxAntennaConfig_t
* @brief Contains arguments for \ref RAIL_BLE_ConfigAoxAntenna function for
* EFR32XG22.
*/
typedef struct RAIL_BLE_AoxAntennaConfig {
/**
* A pointer to an array containing struct of port and pin used for
* AoX antenna switching
*/
RAIL_BLE_AoxAntennaPortPins_t *antPortPin;
/**
* Number of antenna pins to be configured.
*/
uint8_t antCount;
} RAIL_BLE_AoxAntennaConfig_t;
/**
* Lock/unlock the CTE buffer from the application's perspective. The radio
* will write to the buffer only if the bit is NOT set at the beginning of the
* sampling period. The radio will set the bit once the sampling period starts
* to indicate that some CTE data has been collected, which will not be
* overwritten during the next sampling period, unless the buffer is unlocked by
* the application.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] lock Lock the CTE buffer if true and unlock it if false.
* @return True if the CTE buffer is locked after the call, otherwise false.
*/
bool RAIL_BLE_LockCteBuffer(RAIL_Handle_t railHandle, bool lock);
/**
* Determine whether the CTE buffer is currently locked or not.
*
* @param[in] railHandle A handle for RAIL instance.
* @return True if CTE buffer is locked and false otherwise.
*/
bool RAIL_BLE_CteBufferIsLocked(RAIL_Handle_t railHandle);
/**
* Get the offset into CTE sample of CTE data.
*
* @param[in] railHandle A handle for RAIL instance.
* @return The offset of CTE data in a CTE sample in bytes.
* On unsupported platforms this returns 0.
*/
uint8_t RAIL_BLE_GetCteSampleOffset(RAIL_Handle_t railHandle);
/**
* Get the effective sample rate used by the ADC to capture the CTE samples.
*
* @param[in] railHandle A handle for RAIL instance.
* @return The actual sample rate used to capture the CTE in samples per second.
* On unsupported platforms this returns 0.
*/
uint32_t RAIL_BLE_GetCteSampleRate(RAIL_Handle_t railHandle);
/**
* Configure Angle of Arrival/Departure (AoX) functionality. AoX is a method
* of radio localization which infers angle of arrival/departure of the signal
* based on different phases of the raw I/Q signal from different antennas by
* controlling external RF switch during the continuous tone extension (CTE).
* Connection based AoX packets are different than normal BLE packets in that
* they have 3 header bytes instead of 2 and they have CTE appended after the
* payload's CRC. 3rd byte or CTE info contains CTE length. Connectionless AoX
* packets have 2 header bytes and CTE info is part of the payload. AoX is
* supported on EFR32XG12/13/14 only on legacy 1Mbps BLE PHY.
* Note that calling \ref RAIL_GetRadioEntropy during AoX reception may break
* receiving packets.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] aoxConfig Configuration options for AoX
* @return RAIL_Status_t indicating success or failure of the call.
*/
RAIL_Status_t RAIL_BLE_ConfigAox(RAIL_Handle_t railHandle,
const RAIL_BLE_AoxConfig_t *aoxConfig);
/**
* Perform one time initialization of AoX registers.
* This function must be called before \ref RAIL_BLE_ConfigAox
* and before configuring the BLE PHY.
*
* @param[in] railHandle A RAIL instance handle.
* @return RAIL_Status_t indicating success or failure of the call.
*/
RAIL_Status_t RAIL_BLE_InitCte(RAIL_Handle_t railHandle);
/**
* Perform initialization of AoX antenna GPIO pins.
* This function must be called before calls to \ref RAIL_BLE_InitCte
* and \ref RAIL_BLE_ConfigAox, and before configuring the BLE PHY,
* else a \ref RAIL_STATUS_INVALID_CALL is returned.
*
* If user configures more pins, i.e., antCount in
* \ref RAIL_BLE_AoxAntennaConfig_t, than allowed
* \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT, then the API returns
* \ref RAIL_STATUS_INVALID_PARAMETER.
*
* If user configures lesser than or equal to number of pins allowed by
* \ref RAIL_BLE_AOX_ANTENNA_PIN_COUNT, then the requested number of pins
* are configured and \ref RAIL_STATUS_NO_ERROR is returned.
*
* If AoX antenna switching is inactive, non-AoX transmits and receives
* will occur on the first antenna specified by the antenna pattern or
* on the default antenna if no antenna pattern is provided.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] antennaConfig structure to hold the set of ports and pins to
* configure Antenna pins for AoX Antenna switching.
* @return RAIL_Status_t indicating success or failure of the call.
*/
RAIL_Status_t RAIL_BLE_ConfigAoxAntenna(RAIL_Handle_t railHandle,
RAIL_BLE_AoxAntennaConfig_t *antennaConfig);
/** @} */ // end of group AoX
/// @addtogroup BLETX2TX BLE TX Channel Hopping
/// @{
/// @code{.c}
///
/// // Configuration to send one additional packet
/// static RAIL_BLE_TxChannelHoppingConfigEntry_t entry[1];
/// static uint32_t buffer[BUFFER_SIZE];
/// static RAIL_BLE_TxRepeatConfig_t repeat = {
/// .iterations = 1,
/// .repeatOptions = RAIL_TX_REPEAT_OPTION_HOP,
/// .delayOrHop.channelHopping = {
/// .buffer = buffer,
/// .bufferLength = BUFFER_SIZE,
/// .numberOfChannels = 1,
/// .entries = &entry[0],
/// },
/// };
///
/// // Send a normal packet on the current channel, then a packet on a new channel
/// int bleSendThenAdvertise(uint8_t *firstPacket, uint8_t *secondPacket)
/// {
/// // Load both packets into the FIFO
/// RAIL_WriteTxFifo(railHandle, firstPacket, FIRST_PACKET_LEN, true);
/// RAIL_WriteTxFifo(railHandle, secondPacket, SECOND_PACKET_LEN, false);
///
/// // Configure a 300 us turnaround between transmits
/// entry[0].delayMode = RAIL_CHANNEL_HOPPING_DELAY_MODE_STATIC;
/// entry[0].delay = 300; // microseconds
///
/// // Use default advertising parameters
/// entry[0].disableWhitening = false;
/// entry[0].crcInit = 0x00555555;
/// entry[0].accessAddress = 0x8E89BED6;
///
/// // Transmit the repeated packet on the first advertising channel
/// entry[0].phy = RAIL_BLE_1Mbps;
/// entry[0].railChannel = 0;
/// entry[0].logicalChannel = 37;
///
/// // Configure repeated transmit in RAIL, then transmit, sending both packets
/// RAIL_BLE_SetNextTxRepeat(railHandle, &repeat);
/// RAIL_StartTx(railHandle, currentChannel, RAIL_TX_OPTIONS_DEFAULT, NULL);
/// }
/// @endcode
/**
* @struct RAIL_BLE_TxChannelHoppingConfigEntry_t
* @brief Structure that represents one of the channels that is part of a
* \ref RAIL_BLE_TxChannelHoppingConfig_t sequence of channels used in
* channel hopping.
*/
typedef struct RAIL_BLE_TxChannelHoppingConfigEntry {
/**
* Idle time in microseconds to wait before hopping into the
* channel indicated by this entry.
*/
uint32_t delay;
/**
* The BLE PHY to use for this hop's transmit.
*/
RAIL_BLE_Phy_t phy;
/**
* The logical channel to use for this hop's transmit. The whitener will
* be reinitialized if used.
*/
uint8_t logicalChannel;
/**
* The channel number to be used for this hop's transmit. If this is an
* invalid channel for the chosen PHY, the call to \ref RAIL_SetNextTxRepeat()
* will fail.
*/
uint8_t railChannel;
/**
* This can turn off the whitening engine and is useful for sending BLE test
* mode packets that don't have this turned on.
*/
bool disableWhitening;
/**
* The value to use for CRC initialization.
*/
uint32_t crcInit;
/**
* The access address to use for the connection.
*/
uint32_t accessAddress;
} RAIL_BLE_TxChannelHoppingConfigEntry_t;
/**
* @struct RAIL_BLE_TxChannelHoppingConfig_t
* @brief Wrapper struct that will contain the sequence of
* \ref RAIL_BLE_TxChannelHoppingConfigEntry_t that represents the channel
* sequence to use during TX Channel Hopping.
*/
typedef struct RAIL_BLE_TxChannelHoppingConfig {
/**
* Pointer to contiguous global read-write memory that will be used
* by RAIL to store channel hopping information throughout its operation.
* It need not be initialized and applications should never write
* data anywhere in this buffer.
*/
uint32_t *buffer;
/**
* This parameter must be set to the length of the buffer array. This way,
* during configuration, the software can confirm it's writing within the
* range of the buffer. The configuration API will return an error
* if bufferLength is insufficient.
*/
uint16_t bufferLength;
/** The number of channels that is in the channel hopping sequence. */
uint8_t numberOfChannels;
/**
* Pad bytes reserved for future use and currently ignored.
*/
uint8_t reserved;
/**
* A pointer to the first element of an array of \ref
* RAIL_BLE_TxChannelHoppingConfigEntry_t that represents the channels
* used during channel hopping. The length of this array must be
* numberOfChannels.
*/
RAIL_BLE_TxChannelHoppingConfigEntry_t *entries;
} RAIL_BLE_TxChannelHoppingConfig_t;
/// @struct RAIL_BLE_TxRepeatConfig_t
/// @brief A configuration structure for repeated transmits
///
typedef struct RAIL_BLE_TxRepeatConfig {
/**
* The number of repeated transmits to run. A total of (iterations + 1)
* transmits will go on-air in the absence of errors.
*/
uint16_t iterations;
/**
* Repeat option(s) to apply.
*/
RAIL_TxRepeatOptions_t repeatOptions;
/**
* Per-repeat delay or hopping configuration, depending on repeatOptions.
*/
union {
/**
* When \ref RAIL_TX_REPEAT_OPTION_HOP is not set, this specifies
* the delay time between each repeated transmit. Specify \ref
* RAIL_TRANSITION_TIME_KEEP to use the current \ref
* RAIL_StateTiming_t::txToTx transition time setting.
*/
RAIL_TransitionTime_t delay;
/**
* When \ref RAIL_TX_REPEAT_OPTION_HOP is set, this specifies
* the channel hopping configuration to use when hopping between
* repeated transmits. Per-hop delays are configured within each
* \ref RAIL_BLE_TxChannelHoppingConfigEntry_t::delay rather than
* this union's delay field.
*/
RAIL_BLE_TxChannelHoppingConfig_t channelHopping;
} delayOrHop;
} RAIL_BLE_TxRepeatConfig_t;
/**
* Set up automatic repeated transmits after the next transmit.
*
* @param[in] railHandle A RAIL instance handle.
* @param[in] repeatConfig The configuration structure for repeated transmits.
* @return Status code indicating a success of the function call.
*
* Repeated transmits will occur after an application-initiated transmit caused
* by calling one of the \ref Packet_TX APIs. The repetition will only occur
* after the first application-initiated transmit after this function is
* called. Future repeated transmits must be requested by calling this function
* again.
*
* Each repeated transmit that occurs will have full \ref PTI information and
* will receive events such as \ref RAIL_EVENT_TX_PACKET_SENT as normal.
*
* If a TX error occurs during the repetition, the process will abort and the
* TX error transition from \ref RAIL_SetTxTransitions will be used. If the
* repetition completes successfully, the TX success transition from
* \ref RAIL_SetTxTransitions will be used.
*
* Any call to \ref RAIL_Idle or \ref RAIL_StopTx will clear the pending
* repeated transmits. The state will also be cleared by another call to this
* function. To clear the repeated transmits before they've started without
* stopping other radio actions, call this function with a \ref
* RAIL_BLE_TxRepeatConfig_t::iterations count of 0. A DMP switch will clear this
* state only if the initial transmit triggering the repeated transmits has
* started.
*
* The application is responsible for populating the transmit data to be used
* by the repeated transmits via \ref RAIL_SetTxFifo or \ref RAIL_WriteTxFifo.
* Data will be transmitted from the TX FIFO. If the TX FIFO does not have
* sufficient data to transmit, a TX error and a \ref
* RAIL_EVENT_TX_UNDERFLOW will occur. To avoid an underflow, the
* application should queue data to be transmitted as early as possible.
*
* This function will fail to configure the repetition if a transmit of any
* kind is ongoing, including during the time between an initial transmit and
* the end of a previously-configured repetition.
*
* @note This feature/API is not supported on the EFR32XG1 family of chips.
* Use the compile time symbol \ref RAIL_SUPPORTS_TX_TO_TX or the runtime
* call \ref RAIL_SupportsTxToTx() to check whether the platform supports
* this feature.
*/
RAIL_Status_t RAIL_BLE_SetNextTxRepeat(RAIL_Handle_t railHandle,
const RAIL_BLE_TxRepeatConfig_t *repeatConfig);
/** @} */ // end of group BLETX2TX
/** @} */ // end of BLE
#ifdef __cplusplus
}
#endif
#endif // __RAIL_BLE_H__