RadioHead
|
Driver to send and receive unaddressed, unreliable datagrams via a SX1261 LoRa capable radio transceiver embedded in a ST Microelectronics STM32WLE5xx and STM32WLE4xx processors. More...
#include <RH_STM32WLx.h>
Public Member Functions | |
virtual bool | init () |
Public Member Functions inherited from RH_SX126x | |
RH_SX126x (uint8_t slaveSelectPin=SS, uint8_t interruptPin=2, uint8_t busyPin=RH_INVALID_PIN, uint8_t resetPin=RH_INVALID_PIN, RHGenericSPI &spi=hardware_spi, RadioPinConfig *radioPinConfig=nullptr) | |
bool | printRegisters (uint16_t address, uint8_t count) |
bool | setModemRegisters (const ModemConfig *config) |
bool | setModemConfig (ModemConfigChoice index) |
virtual bool | available () |
virtual bool | recv (uint8_t *buf, uint8_t *len) |
virtual bool | send (const uint8_t *data, uint8_t len) |
void | setPreambleLength (uint16_t bytes) |
virtual uint8_t | maxMessageLength () |
bool | setFrequency (float centre, bool calibrate=true) |
void | setModeIdle () |
void | setModeRx () |
void | setModeTx () |
virtual bool | setTxPower (int8_t power) |
virtual bool | sleep () |
virtual bool | isChannelActive () |
int | lastSNR () |
void | setRadioPinConfig (RadioPinConfig *config) |
bool | setTxContinuous () |
uint8_t | getStatus () |
Read and return the radio status byte. | |
uint16_t | lastIrq () |
Return the last interrupt mask, for debugging. | |
bool | getIflag () |
Return true if an interrupt has occurred since the last clearIflag(). For debugging. | |
void | clearIflag () |
Reset the interrupt flag. For debugging. | |
void | clearLastIrq () |
REsets the last interrupt mask. For debugging. | |
void | enableCrcErrorIrq (bool enable) |
Enable or disable the ability to detect CRC errors. | |
void | enableRawMode (bool enable) |
Tells the driver to enable RAW mode, which prevents the transmissions of the 4 byte address header. | |
float | getFrequencyError () |
Returns the frequency error from the last received packet. | |
Public Member Functions inherited from RHSPIDriver | |
RHSPIDriver (uint8_t slaveSelectPin=SS, RHGenericSPI &spi=hardware_spi) | |
bool | init () |
uint8_t | spiRead (uint8_t reg) |
uint8_t | spiWrite (uint8_t reg, uint8_t val) |
uint8_t | spiBurstRead (uint8_t reg, uint8_t *dest, uint8_t len) |
uint8_t | spiBurstWrite (uint8_t reg, const uint8_t *src, uint8_t len) |
void | setSlaveSelectPin (uint8_t slaveSelectPin) |
void | spiUsingInterrupt (uint8_t interruptNumber) |
Public Member Functions inherited from RHGenericDriver | |
RHGenericDriver () | |
Constructor. | |
virtual | ~RHGenericDriver () |
Generic destructor to prevent warnings when objects are dynamically allocated. | |
virtual void | waitAvailable (uint16_t polldelay=0) |
virtual bool | waitPacketSent () |
virtual bool | waitPacketSent (uint16_t timeout) |
virtual bool | waitAvailableTimeout (uint16_t timeout, uint16_t polldelay=0) |
virtual bool | waitCAD () |
void | setCADTimeout (unsigned long cad_timeout) |
virtual void | setThisAddress (uint8_t thisAddress) |
virtual void | setHeaderTo (uint8_t to) |
virtual void | setHeaderFrom (uint8_t from) |
virtual void | setHeaderId (uint8_t id) |
virtual void | setHeaderFlags (uint8_t set, uint8_t clear=RH_FLAGS_APPLICATION_SPECIFIC) |
virtual void | setPromiscuous (bool promiscuous) |
virtual uint8_t | headerTo () |
virtual uint8_t | headerFrom () |
virtual uint8_t | headerId () |
virtual uint8_t | headerFlags () |
virtual int16_t | lastRssi () |
virtual RHMode | mode () |
virtual void | setMode (RHMode mode) |
Sets the operating mode of the transport. | |
virtual uint16_t | rxBad () |
virtual uint16_t | rxGood () |
virtual uint16_t | txGood () |
Protected Member Functions | |
virtual bool | waitUntilNotBusy () |
bool | setupInterruptHandler () |
Protected Member Functions inherited from RH_SX126x | |
bool | sendCommand (uint8_t command, uint8_t data[], uint8_t len) |
Send a command with multi-byte data to the radio. | |
bool | sendCommand (uint8_t command, uint8_t value) |
Send a command with a single data byte to the radio. | |
bool | sendCommand (uint8_t command) |
Send a command without any data to the radio. | |
bool | getCommand (uint8_t command, uint8_t data[], uint8_t len) |
Send a command to the radio and get a multi-byte respose. | |
bool | readRegisters (uint16_t address, uint8_t data[], uint8_t len) |
Read multiple registers from the radio. | |
uint8_t | readRegister (uint16_t address) |
Read and return a single register byte from the radio. | |
bool | writeRegisters (uint16_t address, uint8_t data[], uint8_t len) |
Write multibyte data to the given register and sunbsequent registers. | |
bool | writeRegister (uint16_t address, uint8_t data) |
Write a single byte to the given register. | |
bool | writeBuffer (uint8_t offset, const uint8_t data[], uint8_t len) |
Write multibyte data to the radio IO buffer at the current buffer address. | |
bool | writeBuffer (uint8_t offset, const char *text) |
Write a single byte to the radio IO bufferat the current buffer address. | |
bool | readBuffer (uint8_t offset, uint8_t data[], uint8_t len) |
Read multibyte data from the radio IO buffer at the current buffer address. | |
bool | setPaConfig (uint8_t paDutyCycle, uint8_t hpMax, uint8_t deviceSel, uint8_t paLut) |
Set the radio Power Amplifier configuration. | |
bool | setTxParams (uint8_t power, uint8_t rampTime) |
Set the radio power output. CAUTION: for internal use only. Users should use setTxPower() | |
bool | clearDeviceErrors () |
Clear the radio error byte. | |
bool | setDIO2AsRfSwitchCtrl (bool value) |
bool | setRxFallbackMode (uint8_t mode) |
Sets the mode that the radio will change to after a transmit or receive is complete. | |
bool | setModulationParameters (uint8_t p1, uint8_t p2, uint8_t p3, uint8_t p4, uint8_t p5, uint8_t p6, uint8_t p7, uint8_t p8) |
Set the low-level registers for any desired modulation scheme. | |
bool | setModulationParametersLoRa (uint8_t sf, float bw, uint8_t cr, bool ldro) |
Set the low-level registers for the desired LoRA modulation scheme. | |
bool | setModulationParametersGFSK (uint32_t br, uint8_t sh, uint8_t rxBw, uint32_t freqDev) |
Set the low-level registers for the desired GFSK modulation scheme. | |
bool | calibrate (uint8_t calib_param) |
Cause the radio to calibrate all its sections at the currently selected frequency. | |
bool | calibrateImage (uint8_t f1, uint8_t f2) |
Allows the user to calibrate the image rejection of the device for the device operating frequency band. | |
bool | setLoRaSyncWord (uint16_t sync) |
Set the 16 bit LoRa sync word. | |
bool | setOCPConfiguration (uint8_t setting) |
Set the radio power amplifier over-current protection. | |
bool | setDIO3AsTcxoCtrl (uint8_t voltage, uint32_t delay) |
bool | setTCXO (float voltage, uint32_t delay) |
Set the voltage to use for the TCXO oven. | |
bool | setPacketParams (uint8_t p1, uint8_t p2, uint8_t p3, uint8_t p4, uint8_t p5, uint8_t p6, uint8_t p7, uint8_t p8, uint8_t p9) |
Low level function to set the radio packet confiuration. | |
bool | setPacketParametersLoRa (uint8_t payload_length) |
Set the necessary radio packet parameters for a forthcoming transmission of payload_length bytes. | |
bool | setBufferBaseAddress (uint8_t txbase, uint8_t rxbase) |
Low level function to set the address wherge the next radBuffer or writeBuffer will occur. | |
bool | setSleep (uint8_t config) |
Set the radio to sleep mode. Automatically configures the radio control pins to the configuration RadioPinConfigMode_IDLE. | |
bool | setStandby (uint8_t config) |
Set the radio to sleep mode. Automatically configures the radio control pins to the configuration RadioPinConfigMode_IDLE. | |
bool | setTx (uint32_t timeout) |
bool | setCad () |
Starts the radio in Clear Air Detect (CAD) mode. CAUTION: NOT YET WORKING, always retuns false. | |
bool | setRx (uint32_t timeout) |
Set the radio to receive mode. Automatically configures the radio control pins to the configuration RadioPinConfigMode_RX. | |
bool | setRxBoostMode (bool boost, bool retain) |
Sets whether radios receiver gain boost should be enabled instead of the default power saving mode. | |
bool | setRegulatorMode (uint8_t mode) |
bool | setDioIrqParams (uint16_t irqmask, uint16_t dio1mask, uint16_t dio2mask, uint16_t dio3mask) |
Configures the conditions under which the radio will enable an interrupt, and for which DIO pins. | |
bool | clearIrqStatus (uint16_t mask) |
Clear the radio IRQ state. | |
uint16_t | getIrqStatus () |
Return the radio IRQ state. | |
uint8_t | getPacketType () |
return the current packet type | |
void | setInvertIQ (bool invertIQ) |
bool | fixPAClamping (bool enable) |
Per SX1262_datasheet.pdf Rev 1.2 section 15.2, this fixes an error in the radio Power Amplifier clamping. | |
void | handleInterrupt () |
void | validateRxBuf () |
Examine the revceive buffer to determine whether the message is for this node. | |
void | clearRxBuf () |
Clear our local receive buffer. | |
virtual bool | modeWillChange (RHMode) |
virtual bool | setRadioPinsForMode (RadioPinConfigMode mode) |
virtual RadioPinConfigEntry * | findRadioPinConfigEntry (RadioPinConfigMode mode) |
Find the pin configuration entry for a desired radio mode. | |
Protected Member Functions inherited from RHSPIDriver | |
virtual void | beginTransaction () |
virtual void | endTransaction () |
virtual void | selectSlave () |
virtual void | deselectSlave () |
Additional Inherited Members | |
Public Types inherited from RH_SX126x | |
enum | PacketType { PacketTypeLoRa = 0 , PacketTypeGFSK } |
Packet types the modem can be configured for. More... | |
enum | ModemConfigChoice { LoRa_Bw125Cr45Sf128 = 0 , LoRa_Bw500Cr45Sf128 , LoRa_Bw31_25Cr48Sf512 , LoRa_Bw125Cr48Sf4096 , LoRa_Bw125Cr45Sf2048 } |
enum | RadioPinConfigMode { RadioPinConfigMode_EOT = 0 , RadioPinConfigMode_IDLE , RadioPinConfigMode_RX , RadioPinConfigMode_TX_LOW_POWER , RadioPinConfigMode_TX_HIGH_POWER } |
Public Types inherited from RHGenericDriver | |
enum | RHMode { RHModeInitialising = 0 , RHModeSleep , RHModeIdle , RHModeTx , RHModeRx , RHModeCad } |
Defines different operating modes for the transport hardware. More... | |
Static Public Member Functions inherited from RHGenericDriver | |
static void | printBuffer (const char *prompt, const uint8_t *buf, uint8_t len) |
Protected Attributes inherited from RHSPIDriver | |
RHGenericSPI & | _spi |
Reference to the RHGenericSPI instance to use to transfer data with the SPI device. | |
uint8_t | _slaveSelectPin |
The pin number of the Slave Select pin that is used to select the desired device. | |
Protected Attributes inherited from RHGenericDriver | |
volatile RHMode | _mode |
The current transport operating mode. | |
uint8_t | _thisAddress |
This node id. | |
bool | _promiscuous |
Whether the transport is in promiscuous mode. | |
volatile uint8_t | _rxHeaderTo |
TO header in the last received mesasge. | |
volatile uint8_t | _rxHeaderFrom |
FROM header in the last received mesasge. | |
volatile uint8_t | _rxHeaderId |
ID header in the last received mesasge. | |
volatile uint8_t | _rxHeaderFlags |
FLAGS header in the last received mesasge. | |
uint8_t | _txHeaderTo |
TO header to send in all messages. | |
uint8_t | _txHeaderFrom |
FROM header to send in all messages. | |
uint8_t | _txHeaderId |
ID header to send in all messages. | |
uint8_t | _txHeaderFlags |
FLAGS header to send in all messages. | |
volatile int16_t | _lastRssi |
The value of the last received RSSI value, in some transport specific units. | |
volatile uint16_t | _rxBad |
Count of the number of bad messages (eg bad checksum etc) received. | |
volatile uint16_t | _rxGood |
Count of the number of successfully transmitted messaged. | |
volatile uint16_t | _txGood |
Count of the number of bad messages (correct checksum etc) received. | |
volatile bool | _cad |
Channel activity detected. | |
unsigned int | _cad_timeout |
Channel activity timeout in ms. | |
Driver to send and receive unaddressed, unreliable datagrams via a SX1261 LoRa capable radio transceiver embedded in a ST Microelectronics STM32WLE5xx and STM32WLE4xx processors.
The ST Microelectronics STM32WLE5xx and STM32WLE4xx Arm Cortex processors contain a SX1261 radio with 2 power amplifiers (PAs), a bit like a combination of a SX1261 and SX1262. There is a dedicated SPI interface (called the SubGhzSPI that is used only to communicate with the radio.
The Seeed LoRa-E5-HF and LoRa-E5-LF modules encapsulate a STM32WLE5JC processor, along with an antenna switch, Temperature Controlled Crystal Oscillator (TCXO) and some support components. The Seeed Wio-E5 mini developement board (described below) has a LoRa-E5-HF along with voltage regulator, USB interface, antenna connector etc.
This class is a subclass of RH_SX126x. See the documentation for that class for more details about configuring and using this class.
The stmx32wl_* examples provided should compile out of the box on Arduino 2.1 or later and run with either modules equipped with LoRa-E4 or on the NUCLEO_WL55JC1. Make sure you select the appropriate board in Arduino.
One example of a development board that includes a STM32WLE5xx and SX1261 radio is the Wio-E5 mini.
The Wio-E5 mini is powered by the ST Microelectronics STM32WLE5JC, which contains an ARM Cortex-M4 core and Semtech SX126X LoRa capable radio. The core and radio are enclosed in a sealed Seeed LoRa-E5-HF module, and which includes an antenna switch.
https://wiki.seeedstudio.com/LoRa_E5_mini/ https://files.seeedstudio.com/products/317990687/res/LoRa-E5+module+datasheet_V1.0.pdf
It comes with a 868 to 915MHz compatible antenna and USB-C cable.
As shipped, the Wio-E5 mini contains firmware that provides a serial AT command set that allows the device to connect to join a LoRaWAN network (via a LoRaWAN gateway) using LoRA radio modulation. https://files.seeedstudio.com/products/317990687/res/LoRa-E5+AT+Command+Specification_V1.0+.pdf
You can plug the WiO E5 into a USB port, and use a serial port program (gtkterm, putty, Hyperterm or whatever) to communicate (using AT commands) with the Wio-E5, configure it and then use it to send LoRaWAN messages to a LoRaWAN server.
However, what we want to do is to upload RadioHead based firmware into the Wio-E5 and use the built in SX126X radio to communicate via LoRa radio modulation with other similar LoRA radio nodes.
Note: LoRa is NOT the same thing as LoRaWAN. LoRaWAN is a complete networking system that uses LoRa radio modulation as the transport layer. If you want to work with a LoRaWAN network, you should be using LoRaWAN software and libraries, not RadioHead. LoRa is a much simpler and lower level transport layer that can he used to send short messages over significant distances withglow power.
So, we want to upload RadioHead based software (containing the RadioHead SX126X driver) to the STM32WLE5JC on the Wio-E5. Before we can do that we have to disable the firmware write protection on the STM32WLE5JC.
The Wio-E5 (as shipped) AT command firmware is protected by the ARM processor's Read Out Protection (RDP) byte, meaning you cant read out the AT command set firmware, nor can you upload new firmware, The RDP byte has to be reset first.
But CAUTION: resetting the RDP byte will permanently ERASE the as-shipped AT command firmware, and THERE IS NO WAY TO GET IT BACK. So make sure thats what you want to do.
In order to be able to upload our own firmware we must reset the RDP byte from the as-shipped value of 0xBB (Level 1 read protection) to 0xAA (Level 0, no protection). In order to do this you will need:
Good! The STM32WLE5JC firmware can now be written and read as we need (note that the factory supplied LoRaWan firmware has now been erased), by either STM32CubeProgrammer or Arduino IDE (2.1.1 or later) via the STLink/V2, so leave it connected
In order to use the Arduino IDE to program the Wio-E5, you must install the stm32duino package using these instructions: https://community.st.com/t5/stm32-mcus/stm32-arduino-stm32duino-tutorial/ta-p/49649
Leave STLink/V2 connected but close STM32CubeProgrammer In Arduino IDE: select the following menu options: Tools -> Board -> STM32 MCU based boards -> LoRa boards Tools -> Board part number -> LoRa-E5 mini Tools -> U(S)ART support -> Enabled (generic Serial) You will then be able to edit and upload directly from Arduino IDE through the STLink/V2 You can connect the Wio-E5 USB-C to your hosts USB port and use Arduino IDE to monitor the serial output to Serial (Note: programming does not occur over the USB connection).
There are other options for programming the STM32WLE5JC, including STM32CubeIDE from ST. We did not test them.
https://www.rfsolutions.co.uk/downloads/1537522406DS_SX1261-2_V1.1_SEMTECH.pdf
Lora-net software: https://github.com/Lora-net/SWL2001/releases/tag/v3.3.0
This driver uses the SubGhzClass class (part of the Arduino stm32duino board support) to interface with the internal SX1261/2 radio. That class implements the dedicated radio SPI interface. The radio also has a dedicated internal pin for the radio interrupt and the SPI device select pin and the radio reset pin. The SubGhzClass class includes methods for using all those pins.
Nevertheless it should be possible to use this processor with the normal external SPI interfaces to also interface with another SPI based RadioHEad supported radio, in oprder to make a radio gateway etc.
|
virtual |
Initialise the Driver transport hardware and software. Leaves the radio in idle mode, with default configuration of: 915.0MHz, 13dBm, Bw = 125 kHz, Cr = 4/5, Sf = 128chips/symbol, CRC on
Reimplemented from RH_SX126x.
|
protectedvirtual |
Do whatever is necesary to establish the interrupt handler. This device has special requirements for setting up the interupt handler through the SUBGHZSPI interface so we override
Reimplemented from RH_SX126x.
|
inlineprotectedvirtual |
Wait until the busy pin (if speecified in the contructor) is no longer low On timeout, prints an error to eSerial and returns false. Else returns true.
Reimplemented from RH_SX126x.