From 96405b938da6a7f93a1b1220901d58d4b773982f Mon Sep 17 00:00:00 2001 From: jgromes Date: Wed, 8 Jul 2020 18:52:08 +0200 Subject: [PATCH] [SX126x] Added methods to manually set LoRa LDRO --- src/modules/SX126x/SX126x.cpp | 31 ++++++++++++++++++++++++++----- src/modules/SX126x/SX126x.h | 21 ++++++++++++++++++++- 2 files changed, 46 insertions(+), 6 deletions(-) diff --git a/src/modules/SX126x/SX126x.cpp b/src/modules/SX126x/SX126x.cpp index b5b0d8b9..fbd0edf4 100644 --- a/src/modules/SX126x/SX126x.cpp +++ b/src/modules/SX126x/SX126x.cpp @@ -650,7 +650,7 @@ int16_t SX126x::setBandwidth(float bw) { // update modulation parameters _bwKhz = bw; - return(setModulationParams(_sf, _bw, _cr)); + return(setModulationParams(_sf, _bw, _cr, _ldro)); } int16_t SX126x::setSpreadingFactor(uint8_t sf) { @@ -663,7 +663,7 @@ int16_t SX126x::setSpreadingFactor(uint8_t sf) { // update modulation parameters _sf = sf; - return(setModulationParams(_sf, _bw, _cr)); + return(setModulationParams(_sf, _bw, _cr, _ldro)); } int16_t SX126x::setCodingRate(uint8_t cr) { @@ -676,7 +676,7 @@ int16_t SX126x::setCodingRate(uint8_t cr) { // update modulation parameters _cr = cr - 4; - return(setModulationParams(_sf, _bw, _cr)); + return(setModulationParams(_sf, _bw, _cr, _ldro)); } int16_t SX126x::setSyncWord(uint8_t syncWord, uint8_t controlBits) { @@ -1152,6 +1152,27 @@ void SX126x::setRfSwitchPins(RADIOLIB_PIN_TYPE rxEn, RADIOLIB_PIN_TYPE txEn) { _mod->setRfSwitchPins(rxEn, txEn); } +int16_t SX126x::forceLDRO(bool enable) { + // check active modem + if(getPacketType() != SX126X_PACKET_TYPE_LORA) { + return(ERR_WRONG_MODEM); + } + + // update modulation parameters + _ldroAuto = false; + _ldro = (uint8_t)enable; + return(setModulationParams(_sf, _bw, _cr, _ldro)); +} + +int16_t SX126x::autoLDRO() { + if(getPacketType() != SX126X_PACKET_TYPE_LORA) { + return(ERR_WRONG_MODEM); + } + + _ldroAuto = true; + return(ERR_NONE); +} + int16_t SX126x::setTCXO(float voltage, uint32_t delay) { // set mode to standby standby(); @@ -1316,8 +1337,8 @@ int16_t SX126x::setHeaderType(uint8_t headerType, size_t len) { } int16_t SX126x::setModulationParams(uint8_t sf, uint8_t bw, uint8_t cr, uint8_t ldro) { - // calculate symbol length and enable low data rate optimization, if needed - if(ldro == 0xFF) { + // calculate symbol length and enable low data rate optimization, if auto-configuration is enabled + if(_ldroAuto) { float symbolLength = (float)(uint32_t(1) << _sf) / (float)_bwKhz; RADIOLIB_DEBUG_PRINT("Symbol length: "); RADIOLIB_DEBUG_PRINT(symbolLength); diff --git a/src/modules/SX126x/SX126x.h b/src/modules/SX126x/SX126x.h index 0461e10b..3d45266a 100644 --- a/src/modules/SX126x/SX126x.h +++ b/src/modules/SX126x/SX126x.h @@ -852,6 +852,24 @@ class SX126x: public PhysicalLayer { */ void setRfSwitchPins(RADIOLIB_PIN_TYPE rxEn, RADIOLIB_PIN_TYPE txEn); + /*! + \brief Forces LoRa low data rate optimization. Only available in LoRa mode. After calling this method, LDRO will always be set to + the provided value, regardless of symbol length. To re-enable automatic LDRO configuration, call SX1278::autoLDRO() + + \param enable Force LDRO to be always enabled (true) or disabled (false). + + \returns \ref status_codes + */ + int16_t forceLDRO(bool enable); + + /*! + \brief Re-enables automatic LDRO configuration. Only available in LoRa mode. After calling this method, LDRO will be enabled automatically + when symbol length exceeds 16 ms. + + \returns \ref status_codes + */ + int16_t autoLDRO(); + #ifndef RADIOLIB_GODMODE protected: #endif @@ -871,7 +889,7 @@ class SX126x: public PhysicalLayer { int16_t calibrateImage(uint8_t* data); uint8_t getPacketType(); int16_t setTxParams(uint8_t power, uint8_t rampTime = SX126X_PA_RAMP_200U); - int16_t setModulationParams(uint8_t sf, uint8_t bw, uint8_t cr, uint8_t ldro = 0xFF); + int16_t setModulationParams(uint8_t sf, uint8_t bw, uint8_t cr, uint8_t ldro); int16_t setModulationParamsFSK(uint32_t br, uint8_t pulseShape, uint8_t rxBw, uint32_t freqDev); int16_t setPacketParams(uint16_t preambleLength, uint8_t crcType, uint8_t payloadLength, uint8_t headerType, uint8_t invertIQ = SX126X_LORA_IQ_STANDARD); int16_t setPacketParamsFSK(uint16_t preambleLength, uint8_t crcType, uint8_t syncWordLength, uint8_t addrComp, uint8_t whitening, uint8_t packetType = SX126X_GFSK_PACKET_VARIABLE, uint8_t payloadLength = 0xFF, uint8_t preambleDetectorLength = SX126X_GFSK_PREAMBLE_DETECT_16); @@ -901,6 +919,7 @@ class SX126x: public PhysicalLayer { uint8_t _bw = 0, _sf = 0, _cr = 0, _ldro = 0, _crcType = 0, _headerType = 0; uint16_t _preambleLength = 0; float _bwKhz = 0; + bool _ldroAuto = true; uint32_t _br = 0, _freqDev = 0; uint8_t _rxBw = 0, _pulseShape = 0, _crcTypeFSK = 0, _syncWordLength = 0, _addrComp = 0, _whitening = 0, _packetType = 0;