Giorgos Tsapparellas / SX1272Lib

Dependents:   LoRaWAN_mbed_lmic_agriculture_app

Fork of SX1272Lib by Semtech

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers sx1272.cpp Source File

sx1272.cpp

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