XRange SX1272Lib

Dependents:   XRangePingPong XRange-LoRaWAN-lmic-app lora-transceiver

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