SX1276Lib
Fork of SX1276Lib by
Embed:
(wiki syntax)
Show/hide line numbers
sx1276.cpp
00001 /* 00002 / _____) _ | | 00003 ( (____ _____ ____ _| |_ _____ ____| |__ 00004 \____ \| ___ | (_ _) ___ |/ ___) _ \ 00005 _____) ) ____| | | || |_| ____( (___| | | | 00006 (______/|_____)_|_|_| \__)_____)\____)_| |_| 00007 (C) 2014 Semtech 00008 00009 Description: Actual implementation of a SX1276 radio, inherits Radio 00010 00011 License: Revised BSD License, see LICENSE.TXT file include in the project 00012 00013 Maintainers: Miguel Luis, Gregory Cristian and Nicolas Huguenin 00014 */ 00015 #include "sx1276.h" 00016 00017 const FskBandwidth_t SX1276::FskBandwidths[] = 00018 { 00019 { 2600 , 0x17 }, 00020 { 3100 , 0x0F }, 00021 { 3900 , 0x07 }, 00022 { 5200 , 0x16 }, 00023 { 6300 , 0x0E }, 00024 { 7800 , 0x06 }, 00025 { 10400 , 0x15 }, 00026 { 12500 , 0x0D }, 00027 { 15600 , 0x05 }, 00028 { 20800 , 0x14 }, 00029 { 25000 , 0x0C }, 00030 { 31300 , 0x04 }, 00031 { 41700 , 0x13 }, 00032 { 50000 , 0x0B }, 00033 { 62500 , 0x03 }, 00034 { 83333 , 0x12 }, 00035 { 100000, 0x0A }, 00036 { 125000, 0x02 }, 00037 { 166700, 0x11 }, 00038 { 200000, 0x09 }, 00039 { 250000, 0x01 }, 00040 { 300000, 0x00 }, // Invalid Badwidth 00041 }; 00042 00043 00044 SX1276::SX1276( RadioEvents_t *events, 00045 PinName mosi, PinName miso, PinName sclk, PinName nss, PinName reset, 00046 PinName dio0, PinName dio1, PinName dio2, PinName dio3, PinName dio4, PinName dio5 ) 00047 : Radio ( events ), 00048 spi( mosi, miso, sclk ), 00049 nss( nss ), 00050 reset( reset ), 00051 dio0( dio0 ), dio1( dio1 ), dio2( dio2 ), dio3( dio3 ), dio4( dio4 ), dio5( dio5 ), 00052 isRadioActive( false ) 00053 { 00054 wait_ms( 10 ); 00055 this->rxTx = 0; 00056 this->rxBuffer = new uint8_t[RX_BUFFER_SIZE]; 00057 previousOpMode = RF_OPMODE_STANDBY; 00058 00059 this->RadioEvents = events; 00060 00061 this->dioIrq = new DioIrqHandler[6]; 00062 00063 this->dioIrq [0] = &SX1276::OnDio0Irq; 00064 this->dioIrq [1] = &SX1276::OnDio1Irq; 00065 this->dioIrq [2] = &SX1276::OnDio2Irq; 00066 this->dioIrq [3] = &SX1276::OnDio3Irq; 00067 this->dioIrq [4] = &SX1276::OnDio4Irq; 00068 this->dioIrq [5] = NULL; 00069 00070 this->settings.State = RF_IDLE; 00071 } 00072 00073 SX1276::~SX1276( ) 00074 { 00075 delete this->rxBuffer; 00076 delete this->dioIrq ; 00077 } 00078 00079 void SX1276::Init( RadioEvents_t *events ) 00080 { 00081 this->RadioEvents = events; 00082 } 00083 00084 RadioState SX1276::GetStatus ( void ) 00085 { 00086 return this->settings.State; 00087 } 00088 00089 void SX1276::SetChannel( uint32_t freq ) 00090 { 00091 this->settings.Channel = freq; 00092 freq = ( uint32_t )( ( double )freq / ( double )FREQ_STEP ); 00093 Write( REG_FRFMSB, ( uint8_t )( ( freq >> 16 ) & 0xFF ) ); 00094 Write( REG_FRFMID, ( uint8_t )( ( freq >> 8 ) & 0xFF ) ); 00095 Write( REG_FRFLSB, ( uint8_t )( freq & 0xFF ) ); 00096 } 00097 00098 bool SX1276::IsChannelFree( RadioModems_t modem, uint32_t freq, int16_t rssiThresh ) 00099 { 00100 int16_t rssi = 0; 00101 00102 SetModem( modem ); 00103 00104 SetChannel( freq ); 00105 00106 SetOpMode( RF_OPMODE_RECEIVER ); 00107 00108 wait_ms( 1 ); 00109 00110 rssi = GetRssi( modem ); 00111 00112 Sleep( ); 00113 00114 if( rssi > rssiThresh ) 00115 { 00116 return false; 00117 } 00118 return true; 00119 } 00120 00121 uint32_t SX1276::Random( void ) 00122 { 00123 uint8_t i; 00124 uint32_t rnd = 0; 00125 00126 /* 00127 * Radio setup for random number generation 00128 */ 00129 // Set LoRa modem ON 00130 SetModem( MODEM_LORA ); 00131 00132 // Disable LoRa modem interrupts 00133 Write( REG_LR_IRQFLAGSMASK, RFLR_IRQFLAGS_RXTIMEOUT | 00134 RFLR_IRQFLAGS_RXDONE | 00135 RFLR_IRQFLAGS_PAYLOADCRCERROR | 00136 RFLR_IRQFLAGS_VALIDHEADER | 00137 RFLR_IRQFLAGS_TXDONE | 00138 RFLR_IRQFLAGS_CADDONE | 00139 RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL | 00140 RFLR_IRQFLAGS_CADDETECTED ); 00141 00142 // Set radio in continuous reception 00143 SetOpMode( RF_OPMODE_RECEIVER ); 00144 00145 for( i = 0; i < 32; i++ ) 00146 { 00147 wait_ms( 1 ); 00148 // Unfiltered RSSI value reading. Only takes the LSB value 00149 rnd |= ( ( uint32_t )Read( REG_LR_RSSIWIDEBAND ) & 0x01 ) << i; 00150 } 00151 00152 Sleep( ); 00153 00154 return rnd; 00155 } 00156 00157 /*! 00158 * Performs the Rx chain calibration for LF and HF bands 00159 * \remark Must be called just after the reset so all registers are at their 00160 * default values 00161 */ 00162 void SX1276::RxChainCalibration ( void ) 00163 { 00164 uint8_t regPaConfigInitVal; 00165 uint32_t initialFreq; 00166 00167 // Save context 00168 regPaConfigInitVal = this->Read( REG_PACONFIG ); 00169 initialFreq = ( double )( ( ( uint32_t )this->Read( REG_FRFMSB ) << 16 ) | 00170 ( ( uint32_t )this->Read( REG_FRFMID ) << 8 ) | 00171 ( ( uint32_t )this->Read( REG_FRFLSB ) ) ) * ( double )FREQ_STEP; 00172 00173 // Cut the PA just in case, RFO output, power = -1 dBm 00174 this->Write( REG_PACONFIG, 0x00 ); 00175 00176 // Launch Rx chain calibration for LF band 00177 Write ( REG_IMAGECAL, ( Read( REG_IMAGECAL ) & RF_IMAGECAL_IMAGECAL_MASK ) | RF_IMAGECAL_IMAGECAL_START ); 00178 while( ( Read( REG_IMAGECAL ) & RF_IMAGECAL_IMAGECAL_RUNNING ) == RF_IMAGECAL_IMAGECAL_RUNNING ) 00179 { 00180 } 00181 00182 // Sets a Frequency in HF band 00183 SetChannel( 868000000 ); 00184 00185 // Launch Rx chain calibration for HF band 00186 Write ( REG_IMAGECAL, ( Read( REG_IMAGECAL ) & RF_IMAGECAL_IMAGECAL_MASK ) | RF_IMAGECAL_IMAGECAL_START ); 00187 while( ( Read( REG_IMAGECAL ) & RF_IMAGECAL_IMAGECAL_RUNNING ) == RF_IMAGECAL_IMAGECAL_RUNNING ) 00188 { 00189 } 00190 00191 // Restore context 00192 this->Write( REG_PACONFIG, regPaConfigInitVal ); 00193 SetChannel( initialFreq ); 00194 } 00195 00196 /*! 00197 * Returns the known FSK bandwidth registers value 00198 * 00199 * \param [IN] bandwidth Bandwidth value in Hz 00200 * \retval regValue Bandwidth register value. 00201 */ 00202 uint8_t SX1276::GetFskBandwidthRegValue ( uint32_t bandwidth ) 00203 { 00204 uint8_t i; 00205 00206 for( i = 0; i < ( sizeof( FskBandwidths ) / sizeof( FskBandwidth_t ) ) - 1; i++ ) 00207 { 00208 if( ( bandwidth >= FskBandwidths[i].bandwidth ) && ( bandwidth < FskBandwidths[i + 1].bandwidth ) ) 00209 { 00210 return FskBandwidths[i].RegValue; 00211 } 00212 } 00213 // ERROR: Value not found 00214 while( 1 ); 00215 } 00216 00217 void SX1276::SetRxConfig( RadioModems_t modem, uint32_t bandwidth, 00218 uint32_t datarate, uint8_t coderate, 00219 uint32_t bandwidthAfc, uint16_t preambleLen, 00220 uint16_t symbTimeout, bool fixLen, 00221 uint8_t payloadLen, 00222 bool crcOn, bool freqHopOn, uint8_t hopPeriod, 00223 bool iqInverted, bool rxContinuous ) 00224 { 00225 SetModem( modem ); 00226 00227 switch( modem ) 00228 { 00229 case MODEM_FSK: 00230 { 00231 this->settings.Fsk.Bandwidth = bandwidth; 00232 this->settings.Fsk.Datarate = datarate; 00233 this->settings.Fsk.BandwidthAfc = bandwidthAfc; 00234 this->settings.Fsk.FixLen = fixLen; 00235 this->settings.Fsk.PayloadLen = payloadLen; 00236 this->settings.Fsk.CrcOn = crcOn; 00237 this->settings.Fsk.IqInverted = iqInverted; 00238 this->settings.Fsk.RxContinuous = rxContinuous; 00239 this->settings.Fsk.PreambleLen = preambleLen; 00240 00241 datarate = ( uint16_t )( ( double )XTAL_FREQ / ( double )datarate ); 00242 Write( REG_BITRATEMSB, ( uint8_t )( datarate >> 8 ) ); 00243 Write( REG_BITRATELSB, ( uint8_t )( datarate & 0xFF ) ); 00244 00245 Write( REG_RXBW, GetFskBandwidthRegValue ( bandwidth ) ); 00246 Write( REG_AFCBW, GetFskBandwidthRegValue ( bandwidthAfc ) ); 00247 00248 Write( REG_PREAMBLEMSB, ( uint8_t )( ( preambleLen >> 8 ) & 0xFF ) ); 00249 Write( REG_PREAMBLELSB, ( uint8_t )( preambleLen & 0xFF ) ); 00250 00251 if( fixLen == 1 ) 00252 { 00253 Write( REG_PAYLOADLENGTH, payloadLen ); 00254 } 00255 00256 Write( REG_PACKETCONFIG1, 00257 ( Read( REG_PACKETCONFIG1 ) & 00258 RF_PACKETCONFIG1_CRC_MASK & 00259 RF_PACKETCONFIG1_PACKETFORMAT_MASK ) | 00260 ( ( fixLen == 1 ) ? RF_PACKETCONFIG1_PACKETFORMAT_FIXED : RF_PACKETCONFIG1_PACKETFORMAT_VARIABLE ) | 00261 ( crcOn << 4 ) ); 00262 } 00263 break; 00264 case MODEM_LORA: 00265 { 00266 if( bandwidth > 2 ) 00267 { 00268 // Fatal error: When using LoRa modem only bandwidths 125, 250 and 500 kHz are supported 00269 while( 1 ); 00270 } 00271 bandwidth += 7; 00272 this->settings.LoRa.Bandwidth = bandwidth; 00273 this->settings.LoRa.Datarate = datarate; 00274 this->settings.LoRa.Coderate = coderate; 00275 this->settings.LoRa.PreambleLen = preambleLen; 00276 this->settings.LoRa.FixLen = fixLen; 00277 this->settings.LoRa.PayloadLen = payloadLen; 00278 this->settings.LoRa.CrcOn = crcOn; 00279 this->settings.LoRa.FreqHopOn = freqHopOn; 00280 this->settings.LoRa.HopPeriod = hopPeriod; 00281 this->settings.LoRa.IqInverted = iqInverted; 00282 this->settings.LoRa.RxContinuous = rxContinuous; 00283 00284 if( datarate > 12 ) 00285 { 00286 datarate = 12; 00287 } 00288 else if( datarate < 6 ) 00289 { 00290 datarate = 6; 00291 } 00292 00293 if( ( ( bandwidth == 7 ) && ( ( datarate == 11 ) || ( datarate == 12 ) ) ) || 00294 ( ( bandwidth == 8 ) && ( datarate == 12 ) ) ) 00295 { 00296 this->settings.LoRa.LowDatarateOptimize = 0x01; 00297 } 00298 else 00299 { 00300 this->settings.LoRa.LowDatarateOptimize = 0x00; 00301 } 00302 00303 Write( REG_LR_MODEMCONFIG1, 00304 ( Read( REG_LR_MODEMCONFIG1 ) & 00305 RFLR_MODEMCONFIG1_BW_MASK & 00306 RFLR_MODEMCONFIG1_CODINGRATE_MASK & 00307 RFLR_MODEMCONFIG1_IMPLICITHEADER_MASK ) | 00308 ( bandwidth << 4 ) | ( coderate << 1 ) | 00309 fixLen ); 00310 00311 Write( REG_LR_MODEMCONFIG2, 00312 ( Read( REG_LR_MODEMCONFIG2 ) & 00313 RFLR_MODEMCONFIG2_SF_MASK & 00314 RFLR_MODEMCONFIG2_RXPAYLOADCRC_MASK & 00315 RFLR_MODEMCONFIG2_SYMBTIMEOUTMSB_MASK ) | 00316 ( datarate << 4 ) | ( crcOn << 2 ) | 00317 ( ( symbTimeout >> 8 ) & ~RFLR_MODEMCONFIG2_SYMBTIMEOUTMSB_MASK ) ); 00318 00319 Write( REG_LR_MODEMCONFIG3, 00320 ( Read( REG_LR_MODEMCONFIG3 ) & 00321 RFLR_MODEMCONFIG3_LOWDATARATEOPTIMIZE_MASK ) | 00322 ( this->settings.LoRa.LowDatarateOptimize << 3 ) ); 00323 00324 Write( REG_LR_SYMBTIMEOUTLSB, ( uint8_t )( symbTimeout & 0xFF ) ); 00325 00326 Write( REG_LR_PREAMBLEMSB, ( uint8_t )( ( preambleLen >> 8 ) & 0xFF ) ); 00327 Write( REG_LR_PREAMBLELSB, ( uint8_t )( preambleLen & 0xFF ) ); 00328 00329 if( fixLen == 1 ) 00330 { 00331 Write( REG_LR_PAYLOADLENGTH, payloadLen ); 00332 } 00333 00334 if( this->settings.LoRa.FreqHopOn == true ) 00335 { 00336 Write( REG_LR_PLLHOP, ( Read( REG_LR_PLLHOP ) & RFLR_PLLHOP_FASTHOP_MASK ) | RFLR_PLLHOP_FASTHOP_ON ); 00337 Write( REG_LR_HOPPERIOD, this->settings.LoRa.HopPeriod ); 00338 } 00339 00340 if( ( bandwidth == 9 ) && ( RF_MID_BAND_THRESH ) ) 00341 { 00342 // ERRATA 2.1 - Sensitivity Optimization with a 500 kHz Bandwidth 00343 Write( REG_LR_TEST36, 0x02 ); 00344 Write( REG_LR_TEST3A, 0x64 ); 00345 } 00346 else if( bandwidth == 9 ) 00347 { 00348 // ERRATA 2.1 - Sensitivity Optimization with a 500 kHz Bandwidth 00349 Write( REG_LR_TEST36, 0x02 ); 00350 Write( REG_LR_TEST3A, 0x7F ); 00351 } 00352 else 00353 { 00354 // ERRATA 2.1 - Sensitivity Optimization with a 500 kHz Bandwidth 00355 Write( REG_LR_TEST36, 0x03 ); 00356 } 00357 00358 if( datarate == 6 ) 00359 { 00360 Write( REG_LR_DETECTOPTIMIZE, 00361 ( Read( REG_LR_DETECTOPTIMIZE ) & 00362 RFLR_DETECTIONOPTIMIZE_MASK ) | 00363 RFLR_DETECTIONOPTIMIZE_SF6 ); 00364 Write( REG_LR_DETECTIONTHRESHOLD, 00365 RFLR_DETECTIONTHRESH_SF6 ); 00366 } 00367 else 00368 { 00369 Write( REG_LR_DETECTOPTIMIZE, 00370 ( Read( REG_LR_DETECTOPTIMIZE ) & 00371 RFLR_DETECTIONOPTIMIZE_MASK ) | 00372 RFLR_DETECTIONOPTIMIZE_SF7_TO_SF12 ); 00373 Write( REG_LR_DETECTIONTHRESHOLD, 00374 RFLR_DETECTIONTHRESH_SF7_TO_SF12 ); 00375 } 00376 } 00377 break; 00378 } 00379 } 00380 00381 void SX1276::SetTxConfig( RadioModems_t modem, int8_t power, uint32_t fdev, 00382 uint32_t bandwidth, uint32_t datarate, 00383 uint8_t coderate, uint16_t preambleLen, 00384 bool fixLen, bool crcOn, bool freqHopOn, 00385 uint8_t hopPeriod, bool iqInverted, uint32_t timeout ) 00386 { 00387 uint8_t paConfig = 0; 00388 uint8_t paDac = 0; 00389 00390 SetModem( modem ); 00391 00392 paConfig = Read( REG_PACONFIG ); 00393 paDac = Read( REG_PADAC ); 00394 00395 paConfig = ( paConfig & RF_PACONFIG_PASELECT_MASK ) | GetPaSelect( this->settings.Channel ); 00396 paConfig = ( paConfig & RF_PACONFIG_MAX_POWER_MASK ) | 0x70; 00397 00398 if( ( paConfig & RF_PACONFIG_PASELECT_PABOOST ) == RF_PACONFIG_PASELECT_PABOOST ) 00399 { 00400 if( power > 17 ) 00401 { 00402 paDac = ( paDac & RF_PADAC_20DBM_MASK ) | RF_PADAC_20DBM_ON; 00403 } 00404 else 00405 { 00406 paDac = ( paDac & RF_PADAC_20DBM_MASK ) | RF_PADAC_20DBM_OFF; 00407 } 00408 if( ( paDac & RF_PADAC_20DBM_ON ) == RF_PADAC_20DBM_ON ) 00409 { 00410 if( power < 5 ) 00411 { 00412 power = 5; 00413 } 00414 if( power > 20 ) 00415 { 00416 power = 20; 00417 } 00418 paConfig = ( paConfig & RF_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power - 5 ) & 0x0F ); 00419 } 00420 else 00421 { 00422 if( power < 2 ) 00423 { 00424 power = 2; 00425 } 00426 if( power > 17 ) 00427 { 00428 power = 17; 00429 } 00430 paConfig = ( paConfig & RF_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power - 2 ) & 0x0F ); 00431 } 00432 } 00433 else 00434 { 00435 if( power < -1 ) 00436 { 00437 power = -1; 00438 } 00439 if( power > 14 ) 00440 { 00441 power = 14; 00442 } 00443 paConfig = ( paConfig & RF_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power + 1 ) & 0x0F ); 00444 } 00445 Write( REG_PACONFIG, paConfig ); 00446 Write( REG_PADAC, paDac ); 00447 00448 switch( modem ) 00449 { 00450 case MODEM_FSK: 00451 { 00452 this->settings.Fsk.Power = power; 00453 this->settings.Fsk.Fdev = fdev; 00454 this->settings.Fsk.Bandwidth = bandwidth; 00455 this->settings.Fsk.Datarate = datarate; 00456 this->settings.Fsk.PreambleLen = preambleLen; 00457 this->settings.Fsk.FixLen = fixLen; 00458 this->settings.Fsk.CrcOn = crcOn; 00459 this->settings.Fsk.IqInverted = iqInverted; 00460 this->settings.Fsk.TxTimeout = timeout; 00461 00462 fdev = ( uint16_t )( ( double )fdev / ( double )FREQ_STEP ); 00463 Write( REG_FDEVMSB, ( uint8_t )( fdev >> 8 ) ); 00464 Write( REG_FDEVLSB, ( uint8_t )( fdev & 0xFF ) ); 00465 00466 datarate = ( uint16_t )( ( double )XTAL_FREQ / ( double )datarate ); 00467 Write( REG_BITRATEMSB, ( uint8_t )( datarate >> 8 ) ); 00468 Write( REG_BITRATELSB, ( uint8_t )( datarate & 0xFF ) ); 00469 00470 Write( REG_PREAMBLEMSB, ( preambleLen >> 8 ) & 0x00FF ); 00471 Write( REG_PREAMBLELSB, preambleLen & 0xFF ); 00472 00473 Write( REG_PACKETCONFIG1, 00474 ( Read( REG_PACKETCONFIG1 ) & 00475 RF_PACKETCONFIG1_CRC_MASK & 00476 RF_PACKETCONFIG1_PACKETFORMAT_MASK ) | 00477 ( ( fixLen == 1 ) ? RF_PACKETCONFIG1_PACKETFORMAT_FIXED : RF_PACKETCONFIG1_PACKETFORMAT_VARIABLE ) | 00478 ( crcOn << 4 ) ); 00479 00480 } 00481 break; 00482 case MODEM_LORA: 00483 { 00484 this->settings.LoRa.Power = power; 00485 if( bandwidth > 2 ) 00486 { 00487 // Fatal error: When using LoRa modem only bandwidths 125, 250 and 500 kHz are supported 00488 while( 1 ); 00489 } 00490 bandwidth += 7; 00491 this->settings.LoRa.Bandwidth = bandwidth; 00492 this->settings.LoRa.Datarate = datarate; 00493 this->settings.LoRa.Coderate = coderate; 00494 this->settings.LoRa.PreambleLen = preambleLen; 00495 this->settings.LoRa.FixLen = fixLen; 00496 this->settings.LoRa.FreqHopOn = freqHopOn; 00497 this->settings.LoRa.HopPeriod = hopPeriod; 00498 this->settings.LoRa.CrcOn = crcOn; 00499 this->settings.LoRa.IqInverted = iqInverted; 00500 this->settings.LoRa.TxTimeout = timeout; 00501 00502 if( datarate > 12 ) 00503 { 00504 datarate = 12; 00505 } 00506 else if( datarate < 6 ) 00507 { 00508 datarate = 6; 00509 } 00510 if( ( ( bandwidth == 7 ) && ( ( datarate == 11 ) || ( datarate == 12 ) ) ) || 00511 ( ( bandwidth == 8 ) && ( datarate == 12 ) ) ) 00512 { 00513 this->settings.LoRa.LowDatarateOptimize = 0x01; 00514 } 00515 else 00516 { 00517 this->settings.LoRa.LowDatarateOptimize = 0x00; 00518 } 00519 00520 if( this->settings.LoRa.FreqHopOn == true ) 00521 { 00522 Write( REG_LR_PLLHOP, ( Read( REG_LR_PLLHOP ) & RFLR_PLLHOP_FASTHOP_MASK ) | RFLR_PLLHOP_FASTHOP_ON ); 00523 Write( REG_LR_HOPPERIOD, this->settings.LoRa.HopPeriod ); 00524 } 00525 00526 Write( REG_LR_MODEMCONFIG1, 00527 ( Read( REG_LR_MODEMCONFIG1 ) & 00528 RFLR_MODEMCONFIG1_BW_MASK & 00529 RFLR_MODEMCONFIG1_CODINGRATE_MASK & 00530 RFLR_MODEMCONFIG1_IMPLICITHEADER_MASK ) | 00531 ( bandwidth << 4 ) | ( coderate << 1 ) | 00532 fixLen ); 00533 00534 Write( REG_LR_MODEMCONFIG2, 00535 ( Read( REG_LR_MODEMCONFIG2 ) & 00536 RFLR_MODEMCONFIG2_SF_MASK & 00537 RFLR_MODEMCONFIG2_RXPAYLOADCRC_MASK ) | 00538 ( datarate << 4 ) | ( crcOn << 2 ) ); 00539 00540 Write( REG_LR_MODEMCONFIG3, 00541 ( Read( REG_LR_MODEMCONFIG3 ) & 00542 RFLR_MODEMCONFIG3_LOWDATARATEOPTIMIZE_MASK ) | 00543 ( this->settings.LoRa.LowDatarateOptimize << 3 ) ); 00544 00545 Write( REG_LR_PREAMBLEMSB, ( preambleLen >> 8 ) & 0x00FF ); 00546 Write( REG_LR_PREAMBLELSB, preambleLen & 0xFF ); 00547 00548 if( datarate == 6 ) 00549 { 00550 Write( REG_LR_DETECTOPTIMIZE, 00551 ( Read( REG_LR_DETECTOPTIMIZE ) & 00552 RFLR_DETECTIONOPTIMIZE_MASK ) | 00553 RFLR_DETECTIONOPTIMIZE_SF6 ); 00554 Write( REG_LR_DETECTIONTHRESHOLD, 00555 RFLR_DETECTIONTHRESH_SF6 ); 00556 } 00557 else 00558 { 00559 Write( REG_LR_DETECTOPTIMIZE, 00560 ( Read( REG_LR_DETECTOPTIMIZE ) & 00561 RFLR_DETECTIONOPTIMIZE_MASK ) | 00562 RFLR_DETECTIONOPTIMIZE_SF7_TO_SF12 ); 00563 Write( REG_LR_DETECTIONTHRESHOLD, 00564 RFLR_DETECTIONTHRESH_SF7_TO_SF12 ); 00565 } 00566 } 00567 break; 00568 } 00569 } 00570 00571 double SX1276::TimeOnAir( RadioModems_t modem, uint8_t pktLen ) 00572 { 00573 uint32_t airTime = 0; 00574 00575 switch( modem ) 00576 { 00577 case MODEM_FSK: 00578 { 00579 airTime = rint( ( 8 * ( this->settings.Fsk.PreambleLen + 00580 ( ( Read( REG_SYNCCONFIG ) & ~RF_SYNCCONFIG_SYNCSIZE_MASK ) + 1 ) + 00581 ( ( this->settings.Fsk.FixLen == 0x01 ) ? 0.0 : 1.0 ) + 00582 ( ( ( Read( REG_PACKETCONFIG1 ) & ~RF_PACKETCONFIG1_ADDRSFILTERING_MASK ) != 0x00 ) ? 1.0 : 0 ) + 00583 pktLen + 00584 ( ( this->settings.Fsk.CrcOn == 0x01 ) ? 2.0 : 0 ) ) / 00585 this->settings.Fsk.Datarate ) * 1e6 ); 00586 } 00587 break; 00588 case MODEM_LORA: 00589 { 00590 double bw = 0.0; 00591 // REMARK: When using LoRa modem only bandwidths 125, 250 and 500 kHz are supported 00592 switch( this->settings.LoRa.Bandwidth ) 00593 { 00594 //case 0: // 7.8 kHz 00595 // bw = 78e2; 00596 // break; 00597 //case 1: // 10.4 kHz 00598 // bw = 104e2; 00599 // break; 00600 //case 2: // 15.6 kHz 00601 // bw = 156e2; 00602 // break; 00603 //case 3: // 20.8 kHz 00604 // bw = 208e2; 00605 // break; 00606 //case 4: // 31.2 kHz 00607 // bw = 312e2; 00608 // break; 00609 //case 5: // 41.4 kHz 00610 // bw = 414e2; 00611 // break; 00612 //case 6: // 62.5 kHz 00613 // bw = 625e2; 00614 // break; 00615 case 7: // 125 kHz 00616 bw = 125e3; 00617 break; 00618 case 8: // 250 kHz 00619 bw = 250e3; 00620 break; 00621 case 9: // 500 kHz 00622 bw = 500e3; 00623 break; 00624 } 00625 00626 // Symbol rate : time for one symbol (secs) 00627 double rs = bw / ( 1 << this->settings.LoRa.Datarate ); 00628 double ts = 1 / rs; 00629 // time of preamble 00630 double tPreamble = ( this->settings.LoRa.PreambleLen + 4.25 ) * ts; 00631 // Symbol length of payload and time 00632 double tmp = ceil( ( 8 * pktLen - 4 * this->settings.LoRa.Datarate + 00633 28 + 16 * this->settings.LoRa.CrcOn - 00634 ( this->settings.LoRa.FixLen ? 20 : 0 ) ) / 00635 ( double )( 4 * this->settings.LoRa.Datarate - 00636 ( ( this->settings.LoRa.LowDatarateOptimize > 0 ) ? 2 : 0 ) ) ) * 00637 ( this->settings.LoRa.Coderate + 4 ); 00638 double nPayload = 8 + ( ( tmp > 0 ) ? tmp : 0 ); 00639 double tPayload = nPayload * ts; 00640 // Time on air 00641 double tOnAir = tPreamble + tPayload; 00642 // return us secs 00643 airTime = floor( tOnAir * 1e6 + 0.999 ); 00644 } 00645 break; 00646 } 00647 return airTime; 00648 } 00649 00650 void SX1276::Send( uint8_t *buffer, uint8_t size ) 00651 { 00652 uint32_t txTimeout = 0; 00653 00654 switch( this->settings.Modem ) 00655 { 00656 case MODEM_FSK: 00657 { 00658 this->settings.FskPacketHandler.NbBytes = 0; 00659 this->settings.FskPacketHandler.Size = size; 00660 00661 if( this->settings.Fsk.FixLen == false ) 00662 { 00663 WriteFifo( ( uint8_t* )&size, 1 ); 00664 } 00665 else 00666 { 00667 Write( REG_PAYLOADLENGTH, size ); 00668 } 00669 00670 if( ( size > 0 ) && ( size <= 64 ) ) 00671 { 00672 this->settings.FskPacketHandler.ChunkSize = size; 00673 } 00674 else 00675 { 00676 this->settings.FskPacketHandler.ChunkSize = 32; 00677 } 00678 00679 // Write payload buffer 00680 WriteFifo( buffer, this->settings.FskPacketHandler.ChunkSize ); 00681 this->settings.FskPacketHandler.NbBytes += this->settings.FskPacketHandler.ChunkSize; 00682 txTimeout = this->settings.Fsk.TxTimeout; 00683 } 00684 break; 00685 case MODEM_LORA: 00686 { 00687 if( this->settings.LoRa.IqInverted == true ) 00688 { 00689 Write( REG_LR_INVERTIQ, ( ( Read( REG_LR_INVERTIQ ) & RFLR_INVERTIQ_TX_MASK & RFLR_INVERTIQ_RX_MASK ) | RFLR_INVERTIQ_RX_OFF | RFLR_INVERTIQ_TX_ON ) ); 00690 Write( REG_LR_INVERTIQ2, RFLR_INVERTIQ2_ON ); 00691 } 00692 else 00693 { 00694 Write( REG_LR_INVERTIQ, ( ( Read( REG_LR_INVERTIQ ) & RFLR_INVERTIQ_TX_MASK & RFLR_INVERTIQ_RX_MASK ) | RFLR_INVERTIQ_RX_OFF | RFLR_INVERTIQ_TX_OFF ) ); 00695 Write( REG_LR_INVERTIQ2, RFLR_INVERTIQ2_OFF ); 00696 } 00697 00698 this->settings.LoRaPacketHandler.Size = size; 00699 00700 // Initializes the payload size 00701 Write( REG_LR_PAYLOADLENGTH, size ); 00702 00703 // Full buffer used for Tx 00704 Write( REG_LR_FIFOTXBASEADDR, 0 ); 00705 Write( REG_LR_FIFOADDRPTR, 0 ); 00706 00707 // FIFO operations can not take place in Sleep mode 00708 if( ( Read( REG_OPMODE ) & ~RF_OPMODE_MASK ) == RF_OPMODE_SLEEP ) 00709 { 00710 Standby( ); 00711 wait_ms( 1 ); 00712 } 00713 // Write payload buffer 00714 WriteFifo( buffer, size ); 00715 txTimeout = this->settings.LoRa.TxTimeout; 00716 } 00717 break; 00718 } 00719 00720 Tx( txTimeout ); 00721 } 00722 00723 void SX1276::Sleep( void ) 00724 { 00725 txTimeoutTimer .detach( ); 00726 rxTimeoutTimer.detach( ); 00727 00728 SetOpMode( RF_OPMODE_SLEEP ); 00729 this->settings.State = RF_IDLE; 00730 } 00731 00732 void SX1276::Standby( void ) 00733 { 00734 txTimeoutTimer .detach( ); 00735 rxTimeoutTimer.detach( ); 00736 00737 SetOpMode( RF_OPMODE_STANDBY ); 00738 this->settings.State = RF_IDLE; 00739 } 00740 00741 void SX1276::Rx( uint32_t timeout ) 00742 { 00743 bool rxContinuous = false; 00744 00745 switch( this->settings.Modem ) 00746 { 00747 case MODEM_FSK: 00748 { 00749 rxContinuous = this->settings.Fsk.RxContinuous; 00750 00751 // DIO0=PayloadReady 00752 // DIO1=FifoLevel 00753 // DIO2=SyncAddr 00754 // DIO3=FifoEmpty 00755 // DIO4=Preamble 00756 // DIO5=ModeReady 00757 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RF_DIOMAPPING1_DIO0_MASK & 00758 RF_DIOMAPPING1_DIO2_MASK ) | 00759 RF_DIOMAPPING1_DIO0_00 | 00760 RF_DIOMAPPING1_DIO2_11 ); 00761 00762 Write( REG_DIOMAPPING2, ( Read( REG_DIOMAPPING2 ) & RF_DIOMAPPING2_DIO4_MASK & 00763 RF_DIOMAPPING2_MAP_MASK ) | 00764 RF_DIOMAPPING2_DIO4_11 | 00765 RF_DIOMAPPING2_MAP_PREAMBLEDETECT ); 00766 00767 this->settings.FskPacketHandler.FifoThresh = Read( REG_FIFOTHRESH ) & 0x3F; 00768 00769 this->settings.FskPacketHandler.PreambleDetected = false; 00770 this->settings.FskPacketHandler.SyncWordDetected = false; 00771 this->settings.FskPacketHandler.NbBytes = 0; 00772 this->settings.FskPacketHandler.Size = 0; 00773 } 00774 break; 00775 case MODEM_LORA: 00776 { 00777 if( this->settings.LoRa.IqInverted == true ) 00778 { 00779 Write( REG_LR_INVERTIQ, ( ( Read( REG_LR_INVERTIQ ) & RFLR_INVERTIQ_TX_MASK & RFLR_INVERTIQ_RX_MASK ) | RFLR_INVERTIQ_RX_ON | RFLR_INVERTIQ_TX_OFF ) ); 00780 Write( REG_LR_INVERTIQ2, RFLR_INVERTIQ2_ON ); 00781 } 00782 else 00783 { 00784 Write( REG_LR_INVERTIQ, ( ( Read( REG_LR_INVERTIQ ) & RFLR_INVERTIQ_TX_MASK & RFLR_INVERTIQ_RX_MASK ) | RFLR_INVERTIQ_RX_OFF | RFLR_INVERTIQ_TX_OFF ) ); 00785 Write( REG_LR_INVERTIQ2, RFLR_INVERTIQ2_OFF ); 00786 } 00787 00788 00789 // ERRATA 2.3 - Receiver Spurious Reception of a LoRa Signal 00790 if( this->settings.LoRa.Bandwidth < 9 ) 00791 { 00792 Write( REG_LR_DETECTOPTIMIZE, Read( REG_LR_DETECTOPTIMIZE ) & 0x7F ); 00793 Write( REG_LR_TEST30, 0x00 ); 00794 switch( this->settings.LoRa.Bandwidth ) 00795 { 00796 case 0: // 7.8 kHz 00797 Write( REG_LR_TEST2F, 0x48 ); 00798 SetChannel(this->settings.Channel + 7.81e3 ); 00799 break; 00800 case 1: // 10.4 kHz 00801 Write( REG_LR_TEST2F, 0x44 ); 00802 SetChannel(this->settings.Channel + 10.42e3 ); 00803 break; 00804 case 2: // 15.6 kHz 00805 Write( REG_LR_TEST2F, 0x44 ); 00806 SetChannel(this->settings.Channel + 15.62e3 ); 00807 break; 00808 case 3: // 20.8 kHz 00809 Write( REG_LR_TEST2F, 0x44 ); 00810 SetChannel(this->settings.Channel + 20.83e3 ); 00811 break; 00812 case 4: // 31.2 kHz 00813 Write( REG_LR_TEST2F, 0x44 ); 00814 SetChannel(this->settings.Channel + 31.25e3 ); 00815 break; 00816 case 5: // 41.4 kHz 00817 Write( REG_LR_TEST2F, 0x44 ); 00818 SetChannel(this->settings.Channel + 41.67e3 ); 00819 break; 00820 case 6: // 62.5 kHz 00821 Write( REG_LR_TEST2F, 0x40 ); 00822 break; 00823 case 7: // 125 kHz 00824 Write( REG_LR_TEST2F, 0x40 ); 00825 break; 00826 case 8: // 250 kHz 00827 Write( REG_LR_TEST2F, 0x40 ); 00828 break; 00829 } 00830 } 00831 else 00832 { 00833 Write( REG_LR_DETECTOPTIMIZE, Read( REG_LR_DETECTOPTIMIZE ) | 0x80 ); 00834 } 00835 00836 rxContinuous = this->settings.LoRa.RxContinuous; 00837 00838 if( this->settings.LoRa.FreqHopOn == true ) 00839 { 00840 Write( REG_LR_IRQFLAGSMASK, //RFLR_IRQFLAGS_RXTIMEOUT | 00841 //RFLR_IRQFLAGS_RXDONE | 00842 //RFLR_IRQFLAGS_PAYLOADCRCERROR | 00843 RFLR_IRQFLAGS_VALIDHEADER | 00844 RFLR_IRQFLAGS_TXDONE | 00845 RFLR_IRQFLAGS_CADDONE | 00846 //RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL | 00847 RFLR_IRQFLAGS_CADDETECTED ); 00848 00849 // DIO0=RxDone, DIO2=FhssChangeChannel 00850 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RFLR_DIOMAPPING1_DIO0_MASK & RFLR_DIOMAPPING1_DIO2_MASK ) | RFLR_DIOMAPPING1_DIO0_00 | RFLR_DIOMAPPING1_DIO2_00 ); 00851 } 00852 else 00853 { 00854 Write( REG_LR_IRQFLAGSMASK, //RFLR_IRQFLAGS_RXTIMEOUT | 00855 //RFLR_IRQFLAGS_RXDONE | 00856 //RFLR_IRQFLAGS_PAYLOADCRCERROR | 00857 RFLR_IRQFLAGS_VALIDHEADER | 00858 RFLR_IRQFLAGS_TXDONE | 00859 RFLR_IRQFLAGS_CADDONE | 00860 RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL | 00861 RFLR_IRQFLAGS_CADDETECTED ); 00862 00863 // DIO0=RxDone 00864 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RFLR_DIOMAPPING1_DIO0_MASK ) | RFLR_DIOMAPPING1_DIO0_00 ); 00865 } 00866 Write( REG_LR_FIFORXBASEADDR, 0 ); 00867 Write( REG_LR_FIFOADDRPTR, 0 ); 00868 } 00869 break; 00870 } 00871 00872 memset( rxBuffer, 0, ( size_t )RX_BUFFER_SIZE ); 00873 00874 this->settings.State = RF_RX_RUNNING; 00875 if( timeout != 0 ) 00876 { 00877 rxTimeoutTimer.attach_us( this, &SX1276::OnTimeoutIrq, timeout ); 00878 } 00879 00880 if( this->settings.Modem == MODEM_FSK ) 00881 { 00882 SetOpMode( RF_OPMODE_RECEIVER ); 00883 00884 if( rxContinuous == false ) 00885 { 00886 rxTimeoutSyncWord.attach_us( this, &SX1276::OnTimeoutIrq, ( 8.0 * ( this->settings.Fsk.PreambleLen + 00887 ( ( Read( REG_SYNCCONFIG ) & 00888 ~RF_SYNCCONFIG_SYNCSIZE_MASK ) + 00889 1.0 ) + 10.0 ) / 00890 ( double )this->settings.Fsk.Datarate ) * 1e6 ); 00891 } 00892 } 00893 else 00894 { 00895 if( rxContinuous == true ) 00896 { 00897 SetOpMode( RFLR_OPMODE_RECEIVER ); 00898 } 00899 else 00900 { 00901 SetOpMode( RFLR_OPMODE_RECEIVER_SINGLE ); 00902 } 00903 } 00904 } 00905 00906 void SX1276::Tx( uint32_t timeout ) 00907 { 00908 00909 switch( this->settings.Modem ) 00910 { 00911 case MODEM_FSK: 00912 { 00913 // DIO0=PacketSent 00914 // DIO1=FifoLevel 00915 // DIO2=FifoFull 00916 // DIO3=FifoEmpty 00917 // DIO4=LowBat 00918 // DIO5=ModeReady 00919 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RF_DIOMAPPING1_DIO0_MASK & 00920 RF_DIOMAPPING1_DIO2_MASK ) ); 00921 00922 Write( REG_DIOMAPPING2, ( Read( REG_DIOMAPPING2 ) & RF_DIOMAPPING2_DIO4_MASK & 00923 RF_DIOMAPPING2_MAP_MASK ) ); 00924 this->settings.FskPacketHandler.FifoThresh = Read( REG_FIFOTHRESH ) & 0x3F; 00925 } 00926 break; 00927 case MODEM_LORA: 00928 { 00929 if( this->settings.LoRa.FreqHopOn == true ) 00930 { 00931 Write( REG_LR_IRQFLAGSMASK, RFLR_IRQFLAGS_RXTIMEOUT | 00932 RFLR_IRQFLAGS_RXDONE | 00933 RFLR_IRQFLAGS_PAYLOADCRCERROR | 00934 RFLR_IRQFLAGS_VALIDHEADER | 00935 //RFLR_IRQFLAGS_TXDONE | 00936 RFLR_IRQFLAGS_CADDONE | 00937 //RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL | 00938 RFLR_IRQFLAGS_CADDETECTED ); 00939 00940 // DIO0=TxDone, DIO2=FhssChangeChannel 00941 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RFLR_DIOMAPPING1_DIO0_MASK & RFLR_DIOMAPPING1_DIO2_MASK ) | RFLR_DIOMAPPING1_DIO0_01 | RFLR_DIOMAPPING1_DIO2_00 ); 00942 } 00943 else 00944 { 00945 Write( REG_LR_IRQFLAGSMASK, RFLR_IRQFLAGS_RXTIMEOUT | 00946 RFLR_IRQFLAGS_RXDONE | 00947 RFLR_IRQFLAGS_PAYLOADCRCERROR | 00948 RFLR_IRQFLAGS_VALIDHEADER | 00949 //RFLR_IRQFLAGS_TXDONE | 00950 RFLR_IRQFLAGS_CADDONE | 00951 RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL | 00952 RFLR_IRQFLAGS_CADDETECTED ); 00953 00954 // DIO0=TxDone 00955 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RFLR_DIOMAPPING1_DIO0_MASK ) | RFLR_DIOMAPPING1_DIO0_01 ); 00956 } 00957 } 00958 break; 00959 } 00960 00961 this->settings.State = RF_TX_RUNNING; 00962 txTimeoutTimer .attach_us( this, &SX1276::OnTimeoutIrq, timeout ); 00963 SetOpMode( RF_OPMODE_TRANSMITTER ); 00964 } 00965 00966 void SX1276::StartCad( void ) 00967 { 00968 switch( this->settings.Modem ) 00969 { 00970 case MODEM_FSK: 00971 { 00972 00973 } 00974 break; 00975 case MODEM_LORA: 00976 { 00977 Write( REG_LR_IRQFLAGSMASK, RFLR_IRQFLAGS_RXTIMEOUT | 00978 RFLR_IRQFLAGS_RXDONE | 00979 RFLR_IRQFLAGS_PAYLOADCRCERROR | 00980 RFLR_IRQFLAGS_VALIDHEADER | 00981 RFLR_IRQFLAGS_TXDONE | 00982 //RFLR_IRQFLAGS_CADDONE | 00983 RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL // | 00984 //RFLR_IRQFLAGS_CADDETECTED 00985 ); 00986 00987 // DIO3=CADDone 00988 Write( REG_DIOMAPPING1, ( Read( REG_DIOMAPPING1 ) & RFLR_DIOMAPPING1_DIO0_MASK ) | RFLR_DIOMAPPING1_DIO0_00 ); 00989 00990 this->settings.State = RF_CAD; 00991 SetOpMode( RFLR_OPMODE_CAD ); 00992 } 00993 break; 00994 default: 00995 break; 00996 } 00997 } 00998 00999 int16_t SX1276::GetRssi( RadioModems_t modem ) 01000 { 01001 int16_t rssi = 0; 01002 01003 switch( modem ) 01004 { 01005 case MODEM_FSK: 01006 rssi = -( Read( REG_RSSIVALUE ) >> 1 ); 01007 break; 01008 case MODEM_LORA: 01009 if( this->settings.Channel > RF_MID_BAND_THRESH ) 01010 { 01011 rssi = RSSI_OFFSET_HF + Read( REG_LR_RSSIVALUE ); 01012 } 01013 else 01014 { 01015 rssi = RSSI_OFFSET_LF + Read( REG_LR_RSSIVALUE ); 01016 } 01017 break; 01018 default: 01019 rssi = -1; 01020 break; 01021 } 01022 return rssi; 01023 } 01024 01025 void SX1276::SetOpMode( uint8_t opMode ) 01026 { 01027 if( opMode != previousOpMode ) 01028 { 01029 previousOpMode = opMode; 01030 if( opMode == RF_OPMODE_SLEEP ) 01031 { 01032 SetAntSwLowPower( true ); 01033 } 01034 else 01035 { 01036 SetAntSwLowPower( false ); 01037 if( opMode == RF_OPMODE_TRANSMITTER ) 01038 { 01039 SetAntSw( 1 ); 01040 } 01041 else 01042 { 01043 SetAntSw( 0 ); 01044 } 01045 } 01046 Write( REG_OPMODE, ( Read( REG_OPMODE ) & RF_OPMODE_MASK ) | opMode ); 01047 } 01048 } 01049 01050 void SX1276::SetModem( RadioModems_t modem ) 01051 { 01052 if( this->settings.Modem == modem ) 01053 { 01054 return; 01055 } 01056 01057 this->settings.Modem = modem; 01058 switch( this->settings.Modem ) 01059 { 01060 default: 01061 case MODEM_FSK: 01062 SetOpMode( RF_OPMODE_SLEEP ); 01063 Write( REG_OPMODE, ( Read( REG_OPMODE ) & RFLR_OPMODE_LONGRANGEMODE_MASK ) | RFLR_OPMODE_LONGRANGEMODE_OFF ); 01064 01065 Write( REG_DIOMAPPING1, 0x00 ); 01066 Write( REG_DIOMAPPING2, 0x30 ); // DIO5=ModeReady 01067 break; 01068 case MODEM_LORA: 01069 SetOpMode( RF_OPMODE_SLEEP ); 01070 Write( REG_OPMODE, ( Read( REG_OPMODE ) & RFLR_OPMODE_LONGRANGEMODE_MASK ) | RFLR_OPMODE_LONGRANGEMODE_ON ); 01071 01072 Write( REG_DIOMAPPING1, 0x00 ); 01073 Write( REG_DIOMAPPING2, 0x00 ); 01074 break; 01075 } 01076 } 01077 01078 void SX1276::SetMaxPayloadLength( RadioModems_t modem, uint8_t max ) 01079 { 01080 this->SetModem( modem ); 01081 01082 switch( modem ) 01083 { 01084 case MODEM_FSK: 01085 if( this->settings.Fsk.FixLen == false ) 01086 { 01087 this->Write( REG_PAYLOADLENGTH, max ); 01088 } 01089 break; 01090 case MODEM_LORA: 01091 this->Write( REG_LR_PAYLOADMAXLENGTH, max ); 01092 break; 01093 } 01094 } 01095 01096 void SX1276::OnTimeoutIrq( void ) 01097 { 01098 switch( this->settings.State ) 01099 { 01100 case RF_RX_RUNNING: 01101 if( this->settings.Modem == MODEM_FSK ) 01102 { 01103 this->settings.FskPacketHandler.PreambleDetected = false; 01104 this->settings.FskPacketHandler.SyncWordDetected = false; 01105 this->settings.FskPacketHandler.NbBytes = 0; 01106 this->settings.FskPacketHandler.Size = 0; 01107 01108 // Clear Irqs 01109 Write( REG_IRQFLAGS1, RF_IRQFLAGS1_RSSI | 01110 RF_IRQFLAGS1_PREAMBLEDETECT | 01111 RF_IRQFLAGS1_SYNCADDRESSMATCH ); 01112 Write( REG_IRQFLAGS2, RF_IRQFLAGS2_FIFOOVERRUN ); 01113 01114 if( this->settings.Fsk.RxContinuous == true ) 01115 { 01116 // Continuous mode restart Rx chain 01117 Write( REG_RXCONFIG, Read( REG_RXCONFIG ) | RF_RXCONFIG_RESTARTRXWITHOUTPLLLOCK ); 01118 } 01119 else 01120 { 01121 this->settings.State = RF_IDLE; 01122 rxTimeoutSyncWord.detach( ); 01123 } 01124 } 01125 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxTimeout != NULL ) ) 01126 { 01127 this->RadioEvents->RxTimeout( ); 01128 } 01129 break; 01130 case RF_TX_RUNNING: 01131 this->settings.State = RF_IDLE; 01132 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->TxTimeout != NULL ) ) 01133 { 01134 this->RadioEvents->TxTimeout( ); 01135 } 01136 break; 01137 default: 01138 break; 01139 } 01140 } 01141 01142 void SX1276::OnDio0Irq( void ) 01143 { 01144 volatile uint8_t irqFlags = 0; 01145 01146 switch( this->settings.State ) 01147 { 01148 case RF_RX_RUNNING: 01149 //TimerStop( &RxTimeoutTimer ); 01150 // RxDone interrupt 01151 switch( this->settings.Modem ) 01152 { 01153 case MODEM_FSK: 01154 if( this->settings.Fsk.CrcOn == true ) 01155 { 01156 irqFlags = Read( REG_IRQFLAGS2 ); 01157 if( ( irqFlags & RF_IRQFLAGS2_CRCOK ) != RF_IRQFLAGS2_CRCOK ) 01158 { 01159 // Clear Irqs 01160 Write( REG_IRQFLAGS1, RF_IRQFLAGS1_RSSI | 01161 RF_IRQFLAGS1_PREAMBLEDETECT | 01162 RF_IRQFLAGS1_SYNCADDRESSMATCH ); 01163 Write( REG_IRQFLAGS2, RF_IRQFLAGS2_FIFOOVERRUN ); 01164 01165 if( this->settings.Fsk.RxContinuous == false ) 01166 { 01167 this->settings.State = RF_IDLE; 01168 rxTimeoutSyncWord.attach_us( this, &SX1276::OnTimeoutIrq, ( 8.0 * ( this->settings.Fsk.PreambleLen + 01169 ( ( Read( REG_SYNCCONFIG ) & 01170 ~RF_SYNCCONFIG_SYNCSIZE_MASK ) + 01171 1.0 ) + 10.0 ) / 01172 ( double )this->settings.Fsk.Datarate ) * 1e6 ) ; 01173 } 01174 else 01175 { 01176 // Continuous mode restart Rx chain 01177 Write( REG_RXCONFIG, Read( REG_RXCONFIG ) | RF_RXCONFIG_RESTARTRXWITHOUTPLLLOCK ); 01178 } 01179 rxTimeoutTimer.detach( ); 01180 01181 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxError != NULL ) ) 01182 { 01183 this->RadioEvents->RxError( ); 01184 } 01185 this->settings.FskPacketHandler.PreambleDetected = false; 01186 this->settings.FskPacketHandler.SyncWordDetected = false; 01187 this->settings.FskPacketHandler.NbBytes = 0; 01188 this->settings.FskPacketHandler.Size = 0; 01189 break; 01190 } 01191 } 01192 01193 // Read received packet size 01194 if( ( this->settings.FskPacketHandler.Size == 0 ) && ( this->settings.FskPacketHandler.NbBytes == 0 ) ) 01195 { 01196 if( this->settings.Fsk.FixLen == false ) 01197 { 01198 ReadFifo( ( uint8_t* )&this->settings.FskPacketHandler.Size, 1 ); 01199 } 01200 else 01201 { 01202 this->settings.FskPacketHandler.Size = Read( REG_PAYLOADLENGTH ); 01203 } 01204 ReadFifo( rxBuffer + this->settings.FskPacketHandler.NbBytes, this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01205 this->settings.FskPacketHandler.NbBytes += ( this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01206 } 01207 else 01208 { 01209 ReadFifo( rxBuffer + this->settings.FskPacketHandler.NbBytes, this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01210 this->settings.FskPacketHandler.NbBytes += ( this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01211 } 01212 01213 if( this->settings.Fsk.RxContinuous == false ) 01214 { 01215 this->settings.State = RF_IDLE; 01216 rxTimeoutSyncWord.attach_us( this, &SX1276::OnTimeoutIrq, ( 8.0 * ( this->settings.Fsk.PreambleLen + 01217 ( ( Read( REG_SYNCCONFIG ) & 01218 ~RF_SYNCCONFIG_SYNCSIZE_MASK ) + 01219 1.0 ) + 10.0 ) / 01220 ( double )this->settings.Fsk.Datarate ) * 1e6 ) ; 01221 } 01222 else 01223 { 01224 // Continuous mode restart Rx chain 01225 Write( REG_RXCONFIG, Read( REG_RXCONFIG ) | RF_RXCONFIG_RESTARTRXWITHOUTPLLLOCK ); 01226 } 01227 rxTimeoutTimer.detach( ); 01228 01229 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxDone != NULL ) ) 01230 { 01231 this->RadioEvents->RxDone( rxBuffer, this->settings.FskPacketHandler.Size, this->settings.FskPacketHandler.RssiValue, 0 ); 01232 } 01233 this->settings.FskPacketHandler.PreambleDetected = false; 01234 this->settings.FskPacketHandler.SyncWordDetected = false; 01235 this->settings.FskPacketHandler.NbBytes = 0; 01236 this->settings.FskPacketHandler.Size = 0; 01237 break; 01238 case MODEM_LORA: 01239 { 01240 int8_t snr = 0; 01241 01242 // Clear Irq 01243 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_RXDONE ); 01244 01245 irqFlags = Read( REG_LR_IRQFLAGS ); 01246 if( ( irqFlags & RFLR_IRQFLAGS_PAYLOADCRCERROR_MASK ) == RFLR_IRQFLAGS_PAYLOADCRCERROR ) 01247 { 01248 // Clear Irq 01249 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_PAYLOADCRCERROR ); 01250 01251 if( this->settings.LoRa.RxContinuous == false ) 01252 { 01253 this->settings.State = RF_IDLE; 01254 } 01255 rxTimeoutTimer.detach( ); 01256 01257 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxError != NULL ) ) 01258 { 01259 this->RadioEvents->RxError( ); 01260 } 01261 break; 01262 } 01263 01264 this->settings.LoRaPacketHandler.SnrValue = Read( REG_LR_PKTSNRVALUE ); 01265 if( this->settings.LoRaPacketHandler.SnrValue & 0x80 ) // The SNR sign bit is 1 01266 { 01267 // Invert and divide by 4 01268 snr = ( ( ~this->settings.LoRaPacketHandler.SnrValue + 1 ) & 0xFF ) >> 2; 01269 snr = -snr; 01270 } 01271 else 01272 { 01273 // Divide by 4 01274 snr = ( this->settings.LoRaPacketHandler.SnrValue & 0xFF ) >> 2; 01275 } 01276 01277 int16_t rssi = Read( REG_LR_PKTRSSIVALUE ); 01278 if( snr < 0 ) 01279 { 01280 if( this->settings.Channel > RF_MID_BAND_THRESH ) 01281 { 01282 this->settings.LoRaPacketHandler.RssiValue = RSSI_OFFSET_HF + rssi + ( rssi >> 4 ) + 01283 snr; 01284 } 01285 else 01286 { 01287 this->settings.LoRaPacketHandler.RssiValue = RSSI_OFFSET_LF + rssi + ( rssi >> 4 ) + 01288 snr; 01289 } 01290 } 01291 else 01292 { 01293 if( this->settings.Channel > RF_MID_BAND_THRESH ) 01294 { 01295 this->settings.LoRaPacketHandler.RssiValue = RSSI_OFFSET_HF + rssi + ( rssi >> 4 ); 01296 } 01297 else 01298 { 01299 this->settings.LoRaPacketHandler.RssiValue = RSSI_OFFSET_LF + rssi + ( rssi >> 4 ); 01300 } 01301 } 01302 01303 this->settings.LoRaPacketHandler.Size = Read( REG_LR_RXNBBYTES ); 01304 ReadFifo( rxBuffer, this->settings.LoRaPacketHandler.Size ); 01305 01306 if( this->settings.LoRa.RxContinuous == false ) 01307 { 01308 this->settings.State = RF_IDLE; 01309 } 01310 rxTimeoutTimer.detach( ); 01311 01312 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxDone != NULL ) ) 01313 { 01314 this->RadioEvents->RxDone( rxBuffer, this->settings.LoRaPacketHandler.Size, this->settings.LoRaPacketHandler.RssiValue, this->settings.LoRaPacketHandler.SnrValue ); 01315 } 01316 } 01317 break; 01318 default: 01319 break; 01320 } 01321 break; 01322 case RF_TX_RUNNING: 01323 txTimeoutTimer .detach( ); 01324 // TxDone interrupt 01325 switch( this->settings.Modem ) 01326 { 01327 case MODEM_LORA: 01328 // Clear Irq 01329 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_TXDONE ); 01330 // Intentional fall through 01331 case MODEM_FSK: 01332 default: 01333 this->settings.State = RF_IDLE; 01334 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->TxDone != NULL ) ) 01335 { 01336 this->RadioEvents->TxDone( ); 01337 } 01338 break; 01339 } 01340 break; 01341 default: 01342 break; 01343 } 01344 } 01345 01346 void SX1276::OnDio1Irq( void ) 01347 { 01348 switch( this->settings.State ) 01349 { 01350 case RF_RX_RUNNING: 01351 switch( this->settings.Modem ) 01352 { 01353 case MODEM_FSK: 01354 // FifoLevel interrupt 01355 // Read received packet size 01356 if( ( this->settings.FskPacketHandler.Size == 0 ) && ( this->settings.FskPacketHandler.NbBytes == 0 ) ) 01357 { 01358 if( this->settings.Fsk.FixLen == false ) 01359 { 01360 ReadFifo( ( uint8_t* )&this->settings.FskPacketHandler.Size, 1 ); 01361 } 01362 else 01363 { 01364 this->settings.FskPacketHandler.Size = Read( REG_PAYLOADLENGTH ); 01365 } 01366 } 01367 01368 if( ( this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ) > this->settings.FskPacketHandler.FifoThresh ) 01369 { 01370 ReadFifo( ( rxBuffer + this->settings.FskPacketHandler.NbBytes ), this->settings.FskPacketHandler.FifoThresh ); 01371 this->settings.FskPacketHandler.NbBytes += this->settings.FskPacketHandler.FifoThresh; 01372 } 01373 else 01374 { 01375 ReadFifo( ( rxBuffer + this->settings.FskPacketHandler.NbBytes ), this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01376 this->settings.FskPacketHandler.NbBytes += ( this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01377 } 01378 break; 01379 case MODEM_LORA: 01380 // Sync time out 01381 rxTimeoutTimer.detach( ); 01382 this->settings.State = RF_IDLE; 01383 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->RxTimeout != NULL ) ) 01384 { 01385 this->RadioEvents->RxTimeout( ); 01386 } 01387 break; 01388 default: 01389 break; 01390 } 01391 break; 01392 case RF_TX_RUNNING: 01393 switch( this->settings.Modem ) 01394 { 01395 case MODEM_FSK: 01396 // FifoLevel interrupt 01397 if( ( this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ) > this->settings.FskPacketHandler.ChunkSize ) 01398 { 01399 WriteFifo( ( rxBuffer + this->settings.FskPacketHandler.NbBytes ), this->settings.FskPacketHandler.ChunkSize ); 01400 this->settings.FskPacketHandler.NbBytes += this->settings.FskPacketHandler.ChunkSize; 01401 } 01402 else 01403 { 01404 // Write the last chunk of data 01405 WriteFifo( rxBuffer + this->settings.FskPacketHandler.NbBytes, this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes ); 01406 this->settings.FskPacketHandler.NbBytes += this->settings.FskPacketHandler.Size - this->settings.FskPacketHandler.NbBytes; 01407 } 01408 break; 01409 case MODEM_LORA: 01410 break; 01411 default: 01412 break; 01413 } 01414 break; 01415 default: 01416 break; 01417 } 01418 } 01419 01420 void SX1276::OnDio2Irq( void ) 01421 { 01422 switch( this->settings.State ) 01423 { 01424 case RF_RX_RUNNING: 01425 switch( this->settings.Modem ) 01426 { 01427 case MODEM_FSK: 01428 if( ( this->settings.FskPacketHandler.PreambleDetected == true ) && ( this->settings.FskPacketHandler.SyncWordDetected == false ) ) 01429 { 01430 rxTimeoutSyncWord.detach( ); 01431 01432 this->settings.FskPacketHandler.SyncWordDetected = true; 01433 01434 this->settings.FskPacketHandler.RssiValue = -( Read( REG_RSSIVALUE ) >> 1 ); 01435 01436 this->settings.FskPacketHandler.AfcValue = ( int32_t )( double )( ( ( uint16_t )Read( REG_AFCMSB ) << 8 ) | 01437 ( uint16_t )Read( REG_AFCLSB ) ) * 01438 ( double )FREQ_STEP; 01439 this->settings.FskPacketHandler.RxGain = ( Read( REG_LNA ) >> 5 ) & 0x07; 01440 } 01441 break; 01442 case MODEM_LORA: 01443 if( this->settings.LoRa.FreqHopOn == true ) 01444 { 01445 // Clear Irq 01446 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL ); 01447 01448 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->FhssChangeChannel != NULL ) ) 01449 { 01450 this->RadioEvents->FhssChangeChannel( ( Read( REG_LR_HOPCHANNEL ) & RFLR_HOPCHANNEL_CHANNEL_MASK ) ); 01451 } 01452 } 01453 break; 01454 default: 01455 break; 01456 } 01457 break; 01458 case RF_TX_RUNNING: 01459 switch( this->settings.Modem ) 01460 { 01461 case MODEM_FSK: 01462 break; 01463 case MODEM_LORA: 01464 if( this->settings.LoRa.FreqHopOn == true ) 01465 { 01466 // Clear Irq 01467 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_FHSSCHANGEDCHANNEL ); 01468 01469 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->FhssChangeChannel != NULL ) ) 01470 { 01471 this->RadioEvents->FhssChangeChannel( ( Read( REG_LR_HOPCHANNEL ) & RFLR_HOPCHANNEL_CHANNEL_MASK ) ); 01472 } 01473 } 01474 break; 01475 default: 01476 break; 01477 } 01478 break; 01479 default: 01480 break; 01481 } 01482 } 01483 01484 void SX1276::OnDio3Irq( void ) 01485 { 01486 switch( this->settings.Modem ) 01487 { 01488 case MODEM_FSK: 01489 break; 01490 case MODEM_LORA: 01491 if( ( Read( REG_LR_IRQFLAGS ) & RFLR_IRQFLAGS_CADDETECTED ) == RFLR_IRQFLAGS_CADDETECTED ) 01492 { 01493 // Clear Irq 01494 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_CADDETECTED | RFLR_IRQFLAGS_CADDONE ); 01495 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->CadDone != NULL ) ) 01496 { 01497 this->RadioEvents->CadDone( true ); 01498 } 01499 } 01500 else 01501 { 01502 // Clear Irq 01503 Write( REG_LR_IRQFLAGS, RFLR_IRQFLAGS_CADDONE ); 01504 if( ( this->RadioEvents != NULL ) && ( this->RadioEvents->CadDone != NULL ) ) 01505 { 01506 this->RadioEvents->CadDone( false ); 01507 } 01508 } 01509 break; 01510 default: 01511 break; 01512 } 01513 } 01514 01515 void SX1276::OnDio4Irq( void ) 01516 { 01517 switch( this->settings.Modem ) 01518 { 01519 case MODEM_FSK: 01520 { 01521 if( this->settings.FskPacketHandler.PreambleDetected == false ) 01522 { 01523 this->settings.FskPacketHandler.PreambleDetected = true; 01524 } 01525 } 01526 break; 01527 case MODEM_LORA: 01528 break; 01529 default: 01530 break; 01531 } 01532 } 01533 01534 void SX1276::OnDio5Irq( void ) 01535 { 01536 switch( this->settings.Modem ) 01537 { 01538 case MODEM_FSK: 01539 break; 01540 case MODEM_LORA: 01541 break; 01542 default: 01543 break; 01544 } 01545 }
Generated on Wed Jul 13 2022 22:23:27 by
