sx1302_hal/libloragw/inc/loragw_sx1302.h
Michael Coracin 4c61c5d48e v1.0.0
* Initial release for SX1302 CoreCell Reference Design.
2019-07-12 15:40:13 +02:00

437 lines
13 KiB
C

/*
/ _____) _ | |
( (____ _____ ____ _| |_ _____ ____| |__
\____ \| ___ | (_ _) ___ |/ ___) _ \
_____) ) ____| | | || |_| ____( (___| | | |
(______/|_____)_|_|_| \__)_____)\____)_| |_|
(C)2019 Semtech
Description:
SX1302 Hardware Abstraction Layer entry functions.
License: Revised BSD License, see LICENSE.TXT file include in the project
*/
#ifndef _LORAGW_SX1302_H
#define _LORAGW_SX1302_H
/* -------------------------------------------------------------------------- */
/* --- DEPENDANCIES --------------------------------------------------------- */
#include <stdint.h> /* C99 types*/
#include "config.h" /* library configuration options (dynamically generated) */
/* -------------------------------------------------------------------------- */
/* --- PUBLIC CONSTANTS ----------------------------------------------------- */
/* Default values */
#define SX1302_AGC_RADIO_GAIN_AUTO 0xFF
#define TX_START_DELAY_DEFAULT 1500 /* Calibrated value for 500KHz BW */
/* type of if_chain + modem */
#define IF_UNDEFINED 0
#define IF_LORA_STD 0x10 /* if + standard single-SF LoRa modem */
#define IF_LORA_MULTI 0x11 /* if + LoRa receiver with multi-SF capability */
#define IF_FSK_STD 0x20 /* if + standard FSK modem */
/* -------------------------------------------------------------------------- */
/* --- PUBLIC MACROS -------------------------------------------------------- */
#define REG_SELECT(rf_chain, a, b) ((rf_chain == 0) ? a : b)
#define SET_PPM_ON(bw,dr) (((bw == BW_125KHZ) && ((dr == DR_LORA_SF11) || (dr == DR_LORA_SF12))) || ((bw == BW_250KHZ) && (dr == DR_LORA_SF12)))
/* -------------------------------------------------------------------------- */
/* --- PUBLIC TYPES --------------------------------------------------------- */
/**
@struct sx1302_if_cfg_t
@brief TODO
*/
typedef struct {
bool if_enable;
bool if_rf_chain; /* for each IF, 0 -> radio A, 1 -> radio B */
int32_t if_freq; /* relative to radio frequency, +/- in Hz */
} sx1302_if_cfg_t;
/**
@struct sx1302_lora_service_cfg_t
@brief TODO
*/
typedef struct {
uint8_t lora_rx_bw; /* bandwidth setting for LoRa standalone modem */
uint8_t lora_rx_sf; /* spreading factor setting for LoRa standalone modem */
bool lora_rx_implicit_hdr; /* implicit header setting for LoRa standalone modem */
uint8_t lora_rx_implicit_length; /* implicit header payload length setting for LoRa standalone modem */
bool lora_rx_implicit_crc_en; /* implicit header payload crc enable setting for LoRa standalone modem */
uint8_t lora_rx_implicit_coderate; /* implicit header payload coderate setting for LoRa standalone modem */
} sx1302_lora_service_cfg_t;
/**
@struct sx1302_fsk_cfg_t
@brief TODO
*/
typedef struct {
uint8_t fsk_rx_bw; /* bandwidth setting of FSK modem */
uint32_t fsk_rx_dr; /* FSK modem datarate in bauds */
uint8_t fsk_sync_word_size; /* default number of bytes for FSK sync word */
uint64_t fsk_sync_word; /* default FSK sync word (ALIGNED RIGHT, MSbit first) */
} sx1302_fsk_cfg_t;
/* -------------------------------------------------------------------------- */
/* --- PUBLIC FUNCTIONS PROTOTYPES ------------------------------------------ */
/**
@brief TODO
@param TODO
@return TODO
*/
void sx1302_init(struct lgw_conf_timestamp_s *conf);
/**
@brief Get the SX1302 unique identifier
@param eui pointerto the memory holding the concentrator EUI
@return LGW_REG_SUCCESS if no error, LGW_REG_ERROR otherwise
*/
int sx1302_get_eui(uint64_t * eui);
/**
@brief Check AGC & ARB MCUs parity error, and update timestamp counter wraping status
@brief This function needs to be called regularly (every few seconds) by the upper layer
@param N/A
@return LGW_REG_SUCCESS if no error, LGW_REG_ERROR otherwise
*/
int sx1302_update(void);
/**
@brief Select the clock source radio
@param rf_chain The RF chain index from which to get the clock source
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_clock_select(uint8_t rf_chain);
/**
@brief Apply the radio reset sequence to the required RF chain index
@param rf_chain The RF chain index of the radio to be reset
@param type The type of radio to be reset
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_reset(uint8_t rf_chain, lgw_radio_type_t type);
/**
@brief Configure the radio type for the given RF chain
@param rf_chain The RF chain index to be configured
@param type The type of radio to be set for the given RF chain
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_set_mode(uint8_t rf_chain, lgw_radio_type_t type);
/**
@brief Give/Release control over the radios to/from the Host
@param host_ctrl Set to true to give control to the host, false otherwise
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_host_ctrl(bool host_ctrl);
/**
@brief Perform the radio calibration sequence and fill the TX gain LUT with calibration offsets
@param context_rf_chain The RF chains array from which to get RF chains current configuration
@param clksrc The RF chain index which provides the clock source
@param txgain_lut A pointer to the TX gain LUT to be filled
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_calibrate(struct lgw_conf_rxrf_s * context_rf_chain, uint8_t clksrc, struct lgw_tx_gain_lut_s * txgain_lut);
/**
@brief Configure the PA and LNA LUTs
@param N/A
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_pa_lna_lut_configure(void);
/**
@brief Configure the Radio Front-End stage of the SX1302
@param N/A
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_radio_fe_configure(void);
/**
@brief TODO
@param TODO
@return TODO
*/
uint8_t sx1302_get_ifmod_config(uint8_t if_chain);
/**
@brief Configure the channelizer stage of the SX1302
@param if_cfg A pointer to the channels configuration
@param fix_gain Set to true to force the channelizer to a fixed gain, false to let the AGC controlling it
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_channelizer_configure(struct lgw_conf_rxif_s * if_cfg, bool fix_gain);
/**
@brief Configure the correlator stage of the SX1302 LoRa multi-SF modems
@param N/A
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_lora_correlator_configure(void);
/**
@brief Configure the correlator stage of the SX1302 LoRa single-SF modem
@param cfg A pointer to the channel configuration
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_lora_service_correlator_configure(struct lgw_conf_rxif_s * cfg);
/**
@brief Configure the syncword to be used by LoRa modems (public:0x34, private:0x12)
@param public Set to true to use the "public" syncword, false to use the private one
@param lora_service_sf The spreading factor configured for the single-SF LoRa modem
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_lora_syncword(bool public, uint8_t lora_service_sf);
/**
@brief Configure the LoRa multi-SF modems
@param radio_freq_hz The center frequency of the RF chain (0 or 1)
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_lora_modem_configure(uint32_t radio_freq_hz);
/**
@brief Configure the LoRa single-SF modem
@param cfg A pointer to the channel configuration
@param radio_freq_hz The center frequency of the RF chain (0 or 1)
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_lora_service_modem_configure(struct lgw_conf_rxif_s * cfg, uint32_t radio_freq_hz);
/**
@brief Configure the FSK modem
@param cfg A pointer to the channel configuration
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_fsk_configure(struct lgw_conf_rxif_s * cfg);
/**
@brief Enable the modems
@param N/A
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_modem_enable(void);
/**
@brief Enable/Disable the GPS to allow PPS trigger and counter sampling
@param enbale Set to true to enable, false otherwise
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_gps_enable(bool enable);
/**
@brief Get the current SX1302 internal counter value
@param pps True for getting the counter value at last PPS
@return the counter value in mciroseconds (32-bits)
*/
uint32_t sx1302_timestamp_counter(bool pps);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_load_firmware(const uint8_t *firmware);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_status(uint8_t* status);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_wait_status(uint8_t status);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_mailbox_read(uint8_t mailbox, uint8_t* value);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_mailbox_write(uint8_t mailbox, uint8_t value);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_agc_start(uint8_t version, lgw_radio_type_t radio_type, uint8_t ana_gain, uint8_t dec_gain, uint8_t fdd_mode);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_load_firmware(const uint8_t *firmware);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_status(uint8_t* status);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_wait_status(uint8_t status);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_debug_read(uint8_t reg_id, uint8_t* value);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_debug_write(uint8_t reg_id, uint8_t value);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_arb_start(uint8_t version);
/**
@brief TODO
@param TODO
@return TODO
*/
uint8_t sx1302_arb_get_debug_stats_detect(uint8_t channel);
/**
@brief TODO
@param TODO
@return TODO
*/
uint8_t sx1302_arb_get_debug_stats_alloc(uint8_t channel);
/**
@brief TODO
@param TODO
@return TODO
*/
void sx1302_arb_print_debug_stats(void);
/**
@brief TODO
@param TODO
@return TODO
*/
uint16_t sx1302_lora_payload_crc(const uint8_t * data, uint8_t size);
/**
@brief TODO
@param TODO
@return TODO
*/
uint16_t sx1302_rx_buffer_read_ptr_addr(void);
/**
@brief TODO
@param TODO
@return TODO
*/
uint16_t sx1302_rx_buffer_write_ptr_addr(void);
/**
@brief Check if any data to be fetched from the SX1302 RX buffer and fetch it if any.
@param nb_bytes A pointer to allocated memory to hold the number of bytes fetched
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_fetch(uint16_t * nb_bytes);
/**
@brief Parse and return the next packet available in the fetched RX buffer.
@param context Gateway configuration context
@param p The structure to get the packet parsed
@return LGW_REG_SUCCESS if a packet could be parsed, LGW_REG_ERROR otherwise
*/
int sx1302_parse(lgw_context_t * context, struct lgw_pkt_rx_s * p);
/**
@brief Configure the delay to be applied by the SX1302 for TX to start
@param rf_chain The RF chain index to be configured
@param radio_type The type of radio for this RF chain
@param modulation The modulation used for the TX
@param bandwidth The bandwidth used for the TX
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_tx_set_start_delay(uint8_t rf_chain, lgw_radio_type_t radio_type, uint8_t modulation, uint8_t bandwidth);
/**
@brief Compute the offset to be applied on RSSI for temperature compensation
@param context a pointer to the memory that holds the current temp comp context
@param temperature the temperature for which to compute the offset to be applied
@return the offset to be applied to RSSI
*/
float sx1302_rssi_get_temperature_offset(struct lgw_rssi_tcomp_s * context, float temperature);
/**
@brief Get current TX status of the SX1302
@param rf_chain the TX chain we want to get the status from
@return current status
*/
uint8_t sx1302_tx_status(uint8_t rf_chain);
/**
@brief Get current RX status of the SX1302
@param rf_chain the RX chain we want to get the status from
@return current status
@note NOT IMPLEMENTED
*/
uint8_t sx1302_rx_status(uint8_t rf_chain);
/**
@brief Abort current transmit
@param rf_chain the TX chain on which we want to abort transmit
@return LGW_REG_SUCCESS if success, LGW_REG_ERROR otherwise
*/
int sx1302_tx_abort(uint8_t rf_chain);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_tx_configure(lgw_radio_type_t radio_type);
/**
@brief TODO
@param TODO
@return TODO
*/
int sx1302_send(lgw_radio_type_t radio_type, struct lgw_tx_gain_lut_s * tx_lut, bool lwan_public, struct lgw_conf_rxif_s * context_fsk, struct lgw_pkt_tx_s * pkt_data);
#endif
/* --- EOF ------------------------------------------------------------------ */