Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: LoRaWAN_mbed_lmic_agriculture_app
Fork of SX1272Lib by
sx1272-hal.cpp
00001 /* 00002 / _____) _ | | 00003 ( (____ _____ ____ _| |_ _____ ____| |__ 00004 \____ \| ___ | (_ _) ___ |/ ___) _ \ 00005 _____) ) ____| | | || |_| ____( (___| | | | 00006 (______/|_____)_|_|_| \__)_____)\____)_| |_| 00007 (C) 2015 Semtech 00008 00009 Description: - 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 Notice that, connectivity for SX1272MB2xAS LoRa shield is allocated as: 00025 SX1272MB2xAS MBED Pin 00026 SCK D13 00027 MOSI D11 00028 MISO D12 00029 NSS D10 00030 DIO0 D2 00031 DIO1 D3 00032 DIO2 D4 00033 DIO3 D5 00034 DIO4 D8 00035 DIO5 D9 00036 NRESET A0 00037 */ 00038 #include "sx1272-hal.h" 00039 00040 #if defined ( TARGET_MOTE_L152RC ) 00041 /* 00042 PD_2=0 PD_2=1 00043 op PaB rfo rfo 00044 0 4.6 18.5 27.0 00045 1 5.6 21.1 28.1 00046 2 6.7 23.3 29.1 00047 3 7.7 25.3 30.1 00048 4 8.8 26.2 30.7 00049 5 9.8 27.3 31.2 00050 6 10.7 28.1 31.6 00051 7 11.7 28.6 32.2 00052 8 12.8 29.2 32.4 00053 9 13.7 29.9 32.9 00054 10 14.7 30.5 33.1 00055 11 15.6 30.8 33.4 00056 12 16.4 30.9 33.6 00057 13 17.1 31.0 33.7 00058 14 17.8 31.1 33.7 00059 15 18.4 31.1 33.7 00060 */ 00061 // txpow: 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 00062 static const uint8_t PaBTable[20] = { 0, 0, 0, 0, 0, 1, 2, 3, 3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 14, 15 }; 00063 00064 // txpow: 20 21 22 23 24 25 26 27 28 29 30 00065 static const uint8_t RfoTable[11] = { 1, 1, 1, 2, 2, 3, 4, 5, 6, 8, 9 }; 00066 00067 #endif 00068 00069 const RadioRegisters_t SX1272MB2xAS::RadioRegsInit[] = RADIO_INIT_REGISTERS_VALUE; 00070 00071 SX1272MB2xAS::SX1272MB2xAS( RadioEvents_t *events, 00072 PinName mosi, PinName miso, PinName sclk, PinName nss, PinName reset, 00073 PinName dio0, PinName dio1, PinName dio2, PinName dio3, PinName dio4, PinName dio5, 00074 #if defined ( TARGET_MOTE_L152RC ) 00075 PinName rfSwitchCntr1, PinName rfSwitchCntr2 ) 00076 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00077 PinName txctl, PinName rxctl ) 00078 #else 00079 PinName antSwitch ) 00080 #endif 00081 : SX1272 ( events, mosi, miso, sclk, nss, reset, dio0, dio1, dio2, dio3, dio4, dio5 ), 00082 #if defined ( TARGET_MOTE_L152RC ) 00083 RfSwitchCntr1( rfSwitchCntr1 ), 00084 RfSwitchCntr2( rfSwitchCntr2 ), 00085 PwrAmpCntr( PD_2 ) 00086 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00087 TxCtl ( txctl ), 00088 RxCtl ( rxctl ) 00089 #else 00090 AntSwitch( antSwitch ), 00091 #if( defined ( TARGET_NUCLEO_L152RE ) ) || defined ( TARGET_NUCLEO_L476RG ) 00092 Fake( D8 ) 00093 #else 00094 Fake( A3 ) 00095 #endif 00096 #endif 00097 { 00098 this->RadioEvents = events; 00099 00100 Reset( ); 00101 00102 IoInit( ); 00103 00104 SetOpMode( RF_OPMODE_SLEEP ); 00105 00106 IoIrqInit( dioIrq ); 00107 00108 RadioRegistersInit( ); 00109 00110 SetModem( MODEM_FSK ); 00111 00112 this->settings.State = RF_IDLE ; 00113 } 00114 00115 SX1272MB2xAS::SX1272MB2xAS( RadioEvents_t *events ) 00116 #if defined ( TARGET_NUCLEO_L152RE ) || defined ( TARGET_NUCLEO_L476RG ) 00117 : SX1272 ( events, D11, D12, D13, D10, A0, D2, D3, D4, D5, A3, D9 ), // For NUCLEO L152RE dio4 is on port A3 00118 AntSwitch( A4 ), 00119 Fake( D8 ) 00120 #elif defined ( TARGET_MOTE_L152RC ) 00121 : SX1272 ( events, PB_15, PB_14, PB_13, PB_12, PC_2, PC_6, PC_10, PC_11, PC_8, PC_9, PC_12 ), 00122 RfSwitchCntr1( PC_4 ), 00123 RfSwitchCntr2( PC_13 ), 00124 PwrAmpCntr( PD_2 ) 00125 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00126 : SX1272 ( events, LORA_MOSI, LORA_MISO, LORA_SCK, LORA_NSS, LORA_RESET, LORA_DIO0, LORA_DIO1, LORA_DIO2, LORA_DIO3, LORA_DIO4, LORA_DIO5 ), 00127 TxCtl( LORA_TXCTL ), 00128 RxCtl( LORA_RXCTL ) 00129 #else 00130 : SX1272 ( events, D11, D12, D13, D10, A0, D2, D3, D4, D5, D8, D9 ), 00131 AntSwitch( A4 ), 00132 Fake( A3 ) 00133 #endif 00134 { 00135 this->RadioEvents = events; 00136 00137 Reset( ); 00138 00139 boardConnected = UNKNOWN; 00140 00141 DetectBoardType( ); 00142 00143 IoInit( ); 00144 00145 SetOpMode( RF_OPMODE_SLEEP ); 00146 IoIrqInit( dioIrq ); 00147 00148 RadioRegistersInit( ); 00149 00150 SetModem( MODEM_FSK ); 00151 00152 this->settings.State = RF_IDLE ; 00153 } 00154 00155 //------------------------------------------------------------------------- 00156 // Board relative functions 00157 //------------------------------------------------------------------------- 00158 uint8_t SX1272MB2xAS::DetectBoardType( void ) 00159 { 00160 if( boardConnected == UNKNOWN ) 00161 { 00162 #if defined ( TARGET_MOTE_L152RC ) 00163 boardConnected = NA_MOTE_72; 00164 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00165 boardConnected = MDOT_F411RE; 00166 #else 00167 this->AntSwitch.input( ); 00168 wait_ms( 1 ); 00169 if( this->AntSwitch == 1 ) 00170 { 00171 boardConnected = SX1272MB1DCS; 00172 } 00173 else 00174 { 00175 boardConnected = SX1272MB2XAS; 00176 } 00177 this->AntSwitch.output( ); 00178 wait_ms( 1 ); 00179 #endif 00180 } 00181 return ( boardConnected ); 00182 } 00183 00184 void SX1272MB2xAS::IoInit( void ) 00185 { 00186 AntSwInit( ); 00187 SpiInit( ); 00188 } 00189 00190 void SX1272MB2xAS::RadioRegistersInit( ) 00191 { 00192 uint8_t i = 0; 00193 for( i = 0; i < sizeof( RadioRegsInit ) / sizeof( RadioRegisters_t ); i++ ) 00194 { 00195 SetModem( RadioRegsInit[i].Modem ); 00196 Write( RadioRegsInit[i].Addr, RadioRegsInit[i].Value ); 00197 } 00198 } 00199 00200 void SX1272MB2xAS::SpiInit( void ) 00201 { 00202 nss = 1; 00203 spi .format( 8,0 ); 00204 uint32_t frequencyToSet = 8000000; 00205 #if( defined ( TARGET_NUCLEO_L152RE ) || defined ( TARGET_MOTE_L152RC ) || defined ( TARGET_NUCLEO_L476RG ) || defined ( TARGET_LPC11U6X ) || defined ( TARGET_MTS_MDOT_F411RE ) ) 00206 spi .frequency( frequencyToSet ); 00207 #elif( defined ( TARGET_KL25Z ) ) //busclock frequency is halved -> double the spi frequency to compensate 00208 spi .frequency( frequencyToSet * 2 ); 00209 #else 00210 #warning "Check the board's SPI frequency" 00211 #endif 00212 wait(0.1); 00213 } 00214 00215 void SX1272MB2xAS::IoIrqInit( DioIrqHandler *irqHandlers ) 00216 { 00217 #if( defined ( TARGET_NUCLEO_L152RE ) || defined ( TARGET_MOTE_L152RC ) || defined ( TARGET_NUCLEO_L476RG ) || defined ( TARGET_NUCLEO_L476RG ) || defined ( TARGET_LPC11U6X ) ) 00218 dio0.mode( PullDown ); 00219 dio1.mode( PullDown ); 00220 dio2.mode( PullDown ); 00221 dio3.mode( PullDown ); 00222 dio4.mode( PullDown ); 00223 #endif 00224 dio0.rise( this, static_cast< TriggerMB2xAS > ( irqHandlers[0] ) ); 00225 dio1.rise( this, static_cast< TriggerMB2xAS > ( irqHandlers[1] ) ); 00226 dio2.rise( this, static_cast< TriggerMB2xAS > ( irqHandlers[2] ) ); 00227 dio3.rise( this, static_cast< TriggerMB2xAS > ( irqHandlers[3] ) ); 00228 dio4.rise( this, static_cast< TriggerMB2xAS > ( irqHandlers[4] ) ); 00229 } 00230 00231 void SX1272MB2xAS::IoDeInit( void ) 00232 { 00233 //nothing 00234 } 00235 00236 void SX1272MB2xAS::SetRfTxPower( int8_t power ) 00237 { 00238 uint8_t paConfig = 0; 00239 uint8_t paDac = 0; 00240 00241 paConfig = Read( REG_PACONFIG ); 00242 paDac = Read( REG_PADAC ); 00243 00244 #if defined ( TARGET_MOTE_L152RC ) 00245 if( power > 19 ) 00246 { 00247 paConfig = ( paConfig & RF_PACONFIG_PASELECT_MASK ) | RF_PACONFIG_PASELECT_RFO; 00248 paConfig = ( paConfig & RFLR_PACONFIG_OUTPUTPOWER_MASK ) | RfoTable[power - 20]; 00249 } 00250 else 00251 { 00252 paConfig = ( paConfig & RF_PACONFIG_PASELECT_MASK ) | RF_PACONFIG_PASELECT_PABOOST; 00253 paConfig = ( paConfig & RFLR_PACONFIG_OUTPUTPOWER_MASK ) | PaBTable[power]; 00254 } 00255 #else 00256 paConfig = ( paConfig & RF_PACONFIG_PASELECT_MASK ) | GetPaSelect( this->settings.Channel ); 00257 00258 if( ( paConfig & RF_PACONFIG_PASELECT_PABOOST ) == RF_PACONFIG_PASELECT_PABOOST ) 00259 { 00260 if( power > 17 ) 00261 { 00262 paDac = ( paDac & RF_PADAC_20DBM_MASK ) | RF_PADAC_20DBM_ON; 00263 } 00264 else 00265 { 00266 paDac = ( paDac & RF_PADAC_20DBM_MASK ) | RF_PADAC_20DBM_OFF; 00267 } 00268 if( ( paDac & RF_PADAC_20DBM_ON ) == RF_PADAC_20DBM_ON ) 00269 { 00270 if( power < 5 ) 00271 { 00272 power = 5; 00273 } 00274 if( power > 20 ) 00275 { 00276 power = 20; 00277 } 00278 paConfig = ( paConfig & RFLR_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power - 5 ) & 0x0F ); 00279 } 00280 else 00281 { 00282 if( power < 2 ) 00283 { 00284 power = 2; 00285 } 00286 if( power > 17 ) 00287 { 00288 power = 17; 00289 } 00290 paConfig = ( paConfig & RFLR_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power - 2 ) & 0x0F ); 00291 } 00292 } 00293 else 00294 { 00295 if( power < -1 ) 00296 { 00297 power = -1; 00298 } 00299 if( power > 14 ) 00300 { 00301 power = 14; 00302 } 00303 paConfig = ( paConfig & RFLR_PACONFIG_OUTPUTPOWER_MASK ) | ( uint8_t )( ( uint16_t )( power + 1 ) & 0x0F ); 00304 } 00305 #endif 00306 Write( REG_PACONFIG, paConfig ); 00307 Write( REG_PADAC, paDac ); 00308 } 00309 00310 uint8_t SX1272MB2xAS::GetPaSelect( uint32_t channel ) 00311 { 00312 if( boardConnected == SX1272MB1DCS || boardConnected == MDOT_F411RE ) 00313 { 00314 return RF_PACONFIG_PASELECT_PABOOST; 00315 } 00316 else 00317 { 00318 return RF_PACONFIG_PASELECT_RFO; 00319 } 00320 } 00321 00322 void SX1272MB2xAS::SetAntSwLowPower( bool status ) 00323 { 00324 if( isRadioActive != status ) 00325 { 00326 isRadioActive = status; 00327 00328 if( status == false ) 00329 { 00330 AntSwInit( ); 00331 } 00332 else 00333 { 00334 AntSwDeInit( ); 00335 } 00336 } 00337 } 00338 00339 void SX1272MB2xAS::AntSwInit( void ) 00340 { 00341 #if defined ( TARGET_MOTE_L152RC ) 00342 this->RfSwitchCntr1 = 0; 00343 this->RfSwitchCntr2 = 0; 00344 this->PwrAmpCntr = 0; 00345 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00346 this->TxCtl = 0; 00347 this->RxCtl = 0; 00348 #else 00349 this->AntSwitch = 0; 00350 #endif 00351 } 00352 00353 void SX1272MB2xAS::AntSwDeInit( void ) 00354 { 00355 #if defined ( TARGET_MOTE_L152RC ) 00356 this->RfSwitchCntr1 = 0; 00357 this->RfSwitchCntr2 = 0; 00358 this->PwrAmpCntr = 0; 00359 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00360 this->TxCtl = 0; 00361 this->RxCtl = 0; 00362 #else 00363 this->AntSwitch = 0; 00364 #endif 00365 } 00366 00367 void SX1272MB2xAS::SetAntSw( uint8_t opMode ) 00368 { 00369 switch( opMode ) 00370 { 00371 case RFLR_OPMODE_TRANSMITTER: 00372 #if defined ( TARGET_MOTE_L152RC ) 00373 if( ( Read( REG_PACONFIG ) & RF_PACONFIG_PASELECT_PABOOST ) == RF_PACONFIG_PASELECT_PABOOST ) 00374 { 00375 this->RfSwitchCntr1 = 1; 00376 this->RfSwitchCntr2 = 0; 00377 } 00378 else 00379 { 00380 this->RfSwitchCntr1 = 0; 00381 this->RfSwitchCntr2 = 1; 00382 } 00383 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00384 /* SKY13350 */ 00385 this->TxCtl = 1; 00386 this->RxCtl = 0; 00387 #else 00388 this->AntSwitch = 1; 00389 #endif 00390 break; 00391 case RFLR_OPMODE_RECEIVER: 00392 case RFLR_OPMODE_RECEIVER_SINGLE: 00393 case RFLR_OPMODE_CAD: 00394 #if defined ( TARGET_MOTE_L152RC ) 00395 this->RfSwitchCntr1 = 1; 00396 this->RfSwitchCntr2 = 1; 00397 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00398 /* SKY13350 */ 00399 this->TxCtl = 0; 00400 this->RxCtl = 1; 00401 #else 00402 this->AntSwitch = 0; 00403 #endif 00404 break; 00405 default: 00406 #if defined ( TARGET_MOTE_L152RC ) 00407 this->RfSwitchCntr1 = 0; 00408 this->RfSwitchCntr2 = 0; 00409 this->PwrAmpCntr = 0; 00410 #elif defined ( TARGET_MTS_MDOT_F411RE ) 00411 /* SKY13350 */ 00412 this->TxCtl = 0; 00413 this->RxCtl = 0; 00414 #else 00415 this->AntSwitch = 0; 00416 #endif 00417 break; 00418 } 00419 } 00420 00421 bool SX1272MB2xAS::CheckRfFrequency( uint32_t frequency ) 00422 { 00423 // Implement check. Currently all frequencies are supported 00424 return true; 00425 } 00426 00427 void SX1272MB2xAS::Reset( void ) 00428 { 00429 reset.output( ); 00430 reset = 0; 00431 wait_ms( 1 ); 00432 reset.input( ); 00433 wait_ms( 6 ); 00434 } 00435 00436 void SX1272MB2xAS::Write( uint8_t addr, uint8_t data ) 00437 { 00438 Write( addr, &data, 1 ); 00439 } 00440 00441 uint8_t SX1272MB2xAS::Read( uint8_t addr ) 00442 { 00443 uint8_t data; 00444 Read( addr, &data, 1 ); 00445 return data; 00446 } 00447 00448 void SX1272MB2xAS::Write( uint8_t addr, uint8_t *buffer, uint8_t size ) 00449 { 00450 uint8_t i; 00451 00452 nss = 0; 00453 spi .write( addr | 0x80 ); 00454 for( i = 0; i < size; i++ ) 00455 { 00456 spi .write( buffer[i] ); 00457 } 00458 nss = 1; 00459 } 00460 00461 void SX1272MB2xAS::Read( uint8_t addr, uint8_t *buffer, uint8_t size ) 00462 { 00463 uint8_t i; 00464 00465 nss = 0; 00466 spi .write( addr & 0x7F ); 00467 for( i = 0; i < size; i++ ) 00468 { 00469 buffer[i] = spi .write( 0 ); 00470 } 00471 nss = 1; 00472 } 00473 00474 void SX1272MB2xAS::WriteFifo( uint8_t *buffer, uint8_t size ) 00475 { 00476 Write( 0, buffer, size ); 00477 } 00478 00479 void SX1272MB2xAS::ReadFifo( uint8_t *buffer, uint8_t size ) 00480 { 00481 Read( 0, buffer, size ); 00482 }
Generated on Tue Jul 12 2022 18:34:26 by
1.7.2
