LCOV - code coverage report
Current view: top level - src/modules/LR11x0 - LR1120.cpp (source / functions) Hit Total Coverage
Test: lcov.info Lines: 34 112 30.4 %
Date: 2026-06-03 18:53:41 Functions: 8 14 57.1 %

          Line data    Source code
       1             : #include "LR1120.h"
       2             : #include <math.h>
       3             : 
       4             : #if !RADIOLIB_EXCLUDE_LR11X0
       5             : 
       6           2 : LR1120::LR1120(Module* mod) : LR11x0(mod) {
       7           2 :   chipType = RADIOLIB_LR11X0_DEVICE_LR1120;
       8           2 : }
       9             : 
      10           0 : int16_t LR1120::begin(const ConfigLoRa_t& cfg) {
      11             :   // execute common part
      12           0 :   int16_t state = LR11x0::begin(cfg.bandwidth, cfg.spreadingFactor, cfg.codingRate, cfg.syncWord, cfg.preambleLength);
      13           0 :   RADIOLIB_ASSERT(state);
      14             : 
      15             :   // configure publicly accessible settings
      16           0 :   state = setFrequency(cfg.frequency);
      17           0 :   RADIOLIB_ASSERT(state);
      18             : 
      19           0 :   state = setOutputPower(cfg.power);
      20           0 :   return(state);
      21             : }
      22             : 
      23           0 : int16_t LR1120::begin(float freq, float bw, uint8_t sf, uint8_t cr, uint8_t syncWord, int8_t power, uint16_t preambleLength, float tcxoVoltage) {
      24           0 :   ConfigLoRa_t cfg;
      25           0 :   cfg.frequency = freq;
      26           0 :   cfg.bandwidth = bw;
      27           0 :   cfg.spreadingFactor = sf;
      28           0 :   cfg.codingRate = cr;
      29           0 :   cfg.syncWord = syncWord;
      30           0 :   cfg.power = power;
      31           0 :   cfg.preambleLength = preambleLength;
      32           0 :   this->tcxoVoltage = tcxoVoltage;
      33           0 :   return(begin(cfg));
      34             : }
      35             : 
      36           0 : int16_t LR1120::beginGFSK(const ConfigFSK_t& cfg) {
      37             :   // execute common part
      38           0 :   int16_t state = LR11x0::beginGFSK(cfg.bitRate, cfg.frequencyDeviation, cfg.receiverBandwidth, cfg.preambleLength);
      39           0 :   RADIOLIB_ASSERT(state);
      40             : 
      41             :   // configure publicly accessible settings
      42           0 :   state = setFrequency(cfg.frequency);
      43           0 :   RADIOLIB_ASSERT(state);
      44             : 
      45           0 :   state = setOutputPower(cfg.power);
      46           0 :   return(state);
      47             : }
      48             : 
      49           0 : int16_t LR1120::beginGFSK(float freq, float br, float freqDev, float rxBw, int8_t power, uint16_t preambleLength, float tcxoVoltage) {
      50           0 :   ConfigFSK_t cfg;
      51           0 :   cfg.frequency = freq;
      52           0 :   cfg.bitRate = br;
      53           0 :   cfg.frequencyDeviation = freqDev;
      54           0 :   cfg.receiverBandwidth = rxBw;
      55           0 :   cfg.power = power;
      56           0 :   cfg.preambleLength = preambleLength;
      57           0 :   this->tcxoVoltage = tcxoVoltage;
      58           0 :   return(beginGFSK(cfg));
      59             : }
      60             : 
      61           0 : int16_t LR1120::beginLRFHSS(const ConfigLRFHSS_t& cfg) {
      62             :   // execute common part
      63           0 :   int16_t state = LR11x0::beginLRFHSS(cfg.bandwidth, cfg.bandwidth, cfg.narrowGrid);
      64           0 :   RADIOLIB_ASSERT(state);
      65             : 
      66             :   // configure publicly accessible settings
      67           0 :   state = setFrequency(cfg.frequency);
      68           0 :   RADIOLIB_ASSERT(state);
      69             : 
      70           0 :   state = setOutputPower(cfg.power);
      71           0 :   return(state);
      72             : }
      73             : 
      74           0 : int16_t LR1120::beginLRFHSS(float freq, uint8_t bw, uint8_t cr, bool narrowGrid, int8_t power, float tcxoVoltage) {
      75           0 :   ConfigLRFHSS_t cfg;
      76           0 :   cfg.frequency = freq;
      77           0 :   cfg.bandwidth = bw;
      78           0 :   cfg.codingRate = cr;
      79           0 :   cfg.narrowGrid = narrowGrid;
      80           0 :   cfg.power = power;
      81           0 :   this->tcxoVoltage = tcxoVoltage;
      82           0 :   return(beginLRFHSS(cfg));
      83             : }
      84             : 
      85           2 : int16_t LR1120::setFrequency(float freq) {
      86           2 :   return(this->setFrequency(freq, false));
      87             : }
      88             : 
      89           2 : int16_t LR1120::setFrequency(float freq, bool skipCalibration, float band) {
      90             :   #if RADIOLIB_CHECK_PARAMS
      91           2 :   if(!(((freq >= 150.0f) && (freq <= 960.0f)) ||
      92           2 :     ((freq >= 1900.0f) && (freq <= 2200.0f)) ||
      93           2 :     ((freq >= 2400.0f) && (freq <= 2500.0f)))) {
      94           2 :       return(RADIOLIB_ERR_INVALID_FREQUENCY);
      95             :   }
      96             :   #endif
      97             : 
      98             :   // check if we need to recalibrate image
      99             :   int16_t state;
     100           0 :   if(!skipCalibration && (fabsf(freq - this->freqMHz) >= RADIOLIB_LR11X0_CAL_IMG_FREQ_TRIG_MHZ)) {
     101           0 :     state = LR11x0::calibrateImageRejection(freq - band, freq + band);
     102           0 :     RADIOLIB_ASSERT(state);
     103             :   }
     104             : 
     105             :   // set frequency
     106           0 :   state = LR11x0::setRfFrequency((uint32_t)(freq*1000000.0f));
     107           0 :   RADIOLIB_ASSERT(state);
     108           0 :   this->freqMHz = freq;
     109           0 :   this->highFreq = (freq > 1000.0f);
     110             : 
     111             :   // apply workaround for GFSK
     112           0 :   return(workaroundGFSK());
     113             : }
     114             : 
     115           2 : int16_t LR1120::setOutputPower(int8_t power) {
     116           2 :   return(this->setOutputPower(power, false));
     117             : }
     118             : 
     119           2 : int16_t LR1120::setOutputPower(int8_t power, bool forceHighPower, uint32_t rampTimeUs) {
     120             :   // check if power value is configurable
     121           2 :   int16_t state = this->checkOutputPower(power, NULL, forceHighPower);
     122           2 :   RADIOLIB_ASSERT(state);
     123             : 
     124             :   // determine whether to use HP or LP PA and check range accordingly
     125           2 :   uint8_t paSel = 0;
     126           2 :   uint8_t paSupply = 0;
     127           2 :   this->txMode = LR11x0::MODE_TX;
     128           2 :   if(this->highFreq) {
     129           0 :     paSel = 2;
     130           0 :     this->txMode = LR11x0::MODE_TX_HF;
     131           2 :   } else if(forceHighPower || (power > 14)) {
     132           0 :     paSel = 1;
     133           0 :     paSupply = 1;
     134           0 :     this->txMode = LR11x0::MODE_TX_HP;
     135             :   }
     136             :   
     137             :   // TODO how and when to configure OCP?
     138             : 
     139             :   // update PA config and set output power - always use VBAT for high-power PA
     140             :   // the value returned by LRxxxx class is offset by 3 for LR11x0
     141           2 :   state = LR11x0::setOutputPower(power, paSel, paSupply, 0x04, 0x07, roundRampTime(rampTimeUs) - 0x03);
     142           2 :   return(state);
     143             : }
     144             : 
     145           2 : int16_t LR1120::checkOutputPower(int8_t power, int8_t* clipped) {
     146           2 :   return(checkOutputPower(power, clipped, false));
     147             : }
     148             : 
     149           4 : int16_t LR1120::checkOutputPower(int8_t power, int8_t* clipped, bool forceHighPower) {
     150           4 :   if(this->highFreq) {
     151           0 :     if(clipped) {
     152           0 :       *clipped = RADIOLIB_MAX(-18, RADIOLIB_MIN(13, power));
     153             :     }
     154           0 :     RADIOLIB_CHECK_RANGE(power, -18, 13, RADIOLIB_ERR_INVALID_OUTPUT_POWER);
     155           0 :     return(RADIOLIB_ERR_NONE);
     156             :   }
     157             : 
     158           4 :   if(forceHighPower || (power > 14)) {
     159           0 :     if(clipped) {
     160           0 :       *clipped = RADIOLIB_MAX(-9, RADIOLIB_MIN(22, power));
     161             :     }
     162           0 :     RADIOLIB_CHECK_RANGE(power, -9, 22, RADIOLIB_ERR_INVALID_OUTPUT_POWER);
     163             :   
     164             :   } else {
     165           4 :     if(clipped) {
     166           0 :       *clipped = RADIOLIB_MAX(-17, RADIOLIB_MIN(14, power));
     167             :     }
     168           4 :     RADIOLIB_CHECK_RANGE(power, -17, 14, RADIOLIB_ERR_INVALID_OUTPUT_POWER);
     169             :   
     170             :   }
     171           4 :   return(RADIOLIB_ERR_NONE);
     172             : }
     173             : 
     174           2 : int16_t LR1120::setModem(ModemType_t modem) {
     175           2 :   switch(modem) {
     176           0 :     case(ModemType_t::RADIOLIB_MODEM_LORA): {
     177           0 :       return(this->begin());
     178             :     } break;
     179           0 :     case(ModemType_t::RADIOLIB_MODEM_FSK): {
     180           0 :       return(this->beginGFSK());
     181             :     } break;
     182           0 :     case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
     183           0 :       return(this->beginLRFHSS());
     184             :     } break;
     185           2 :     default:
     186           2 :       return(RADIOLIB_ERR_WRONG_MODEM);
     187             :   }
     188             :   return(RADIOLIB_ERR_WRONG_MODEM);
     189             : }
     190             : 
     191             : #endif

Generated by: LCOV version 1.14