diff --git a/sx127x.cpp b/sx127x.cpp index 0fa8f5e..aef035b 100644 --- a/sx127x.cpp +++ b/sx127x.cpp @@ -19,166 +19,149 @@ #endif // Registers -#define REG_FIFO_7X 0x00 -#define REG_OP_MODE_7X 0x01 -#define REG_FRF_MSB_7X 0x06 -#define REG_FRF_MID_7X 0x07 -#define REG_FRF_LSB_7X 0x08 -#define REG_PA_CONFIG_7X 0x09 -#define REG_OCP_7X 0x0b -#define REG_LNA_7X 0x0c -#define REG_FIFO_ADDR_PTR_7X 0x0d -#define REG_FIFO_TX_BASE_ADDR_7X 0x0e -#define REG_FIFO_RX_BASE_ADDR_7X 0x0f -#define REG_FIFO_RX_CURRENT_ADDR_7X 0x10 -#define REG_IRQ_FLAGS_7X 0x12 -#define REG_RX_NB_BYTES_7X 0x13 -#define REG_MODEM_STAT_7X 0x18 -#define REG_PKT_SNR_VALUE_7X 0x19 -#define REG_PKT_RSSI_VALUE_7X 0x1a -#define REG_RSSI_VALUE_7X 0x1b -#define REG_MODEM_CONFIG_1_7X 0x1d -#define REG_MODEM_CONFIG_2_7X 0x1e -#define REG_PREAMBLE_MSB_7X 0x20 -#define REG_PREAMBLE_LSB_7X 0x21 -#define REG_PAYLOAD_LENGTH_7X 0x22 -#define REG_MODEM_CONFIG_3_7X 0x26 -#define REG_FREQ_ERROR_MSB_7X 0x28 -#define REG_FREQ_ERROR_MID_7X 0x29 -#define REG_FREQ_ERROR_LSB_7X 0x2a -#define REG_RSSI_WIDEBAND_7X 0x2c -#define REG_DETECTION_OPTIMIZE_7X 0x31 -#define REG_HIGH_BW_OPTIMIZE_1_7X 0x36 -#define REG_DETECTION_THRESHOLD_7X 0x37 -#define REG_SYNC_WORD_7X 0x39 -#define REG_HIGH_BW_OPTIMIZE_2_7X 0x3a -#define REG_DIO_MAPPING_1_7X 0x40 -#define REG_VERSION_7X 0x42 -#define REG_TCXO_7X 0x4b -#define REG_PA_DAC_7X 0x4d +#define REG_FIFO_7X 0x00 +#define REG_OP_MODE_7X 0x01 +#define REG_FRF_MSB_7X 0x06 +#define REG_FRF_MID_7X 0x07 +#define REG_FRF_LSB_7X 0x08 +#define REG_PA_CONFIG_7X 0x09 +#define REG_OCP_7X 0x0b +#define REG_LNA_7X 0x0c +#define REG_FIFO_ADDR_PTR_7X 0x0d +#define REG_FIFO_TX_BASE_ADDR_7X 0x0e +#define REG_FIFO_RX_BASE_ADDR_7X 0x0f +#define REG_FIFO_RX_CURRENT_ADDR_7X 0x10 +#define REG_IRQ_FLAGS_7X 0x12 +#define REG_RX_NB_BYTES_7X 0x13 +#define REG_MODEM_STAT_7X 0x18 +#define REG_PKT_SNR_VALUE_7X 0x19 +#define REG_PKT_RSSI_VALUE_7X 0x1a +#define REG_RSSI_VALUE_7X 0x1b +#define REG_MODEM_CONFIG_1_7X 0x1d +#define REG_MODEM_CONFIG_2_7X 0x1e +#define REG_PREAMBLE_MSB_7X 0x20 +#define REG_PREAMBLE_LSB_7X 0x21 +#define REG_PAYLOAD_LENGTH_7X 0x22 +#define REG_MODEM_CONFIG_3_7X 0x26 +#define REG_FREQ_ERROR_MSB_7X 0x28 +#define REG_FREQ_ERROR_MID_7X 0x29 +#define REG_FREQ_ERROR_LSB_7X 0x2a +#define REG_RSSI_WIDEBAND_7X 0x2c +#define REG_DETECTION_OPTIMIZE_7X 0x31 +#define REG_HIGH_BW_OPTIMIZE_1_7X 0x36 +#define REG_DETECTION_THRESHOLD_7X 0x37 +#define REG_SYNC_WORD_7X 0x39 +#define REG_HIGH_BW_OPTIMIZE_2_7X 0x3a +#define REG_DIO_MAPPING_1_7X 0x40 +#define REG_VERSION_7X 0x42 +#define REG_TCXO_7X 0x4b +#define REG_PA_DAC_7X 0x4d // Modes -#define MODE_LONG_RANGE_MODE_7X 0x80 -#define MODE_SLEEP_7X 0x00 -#define MODE_STDBY_7X 0x01 -#define MODE_TX_7X 0x03 -#define MODE_RX_CONTINUOUS_7X 0x05 -#define MODE_RX_SINGLE_7X 0x06 +#define MODE_LONG_RANGE_MODE_7X 0x80 +#define MODE_SLEEP_7X 0x00 +#define MODE_STDBY_7X 0x01 +#define MODE_TX_7X 0x03 +#define MODE_RX_CONTINUOUS_7X 0x05 +#define MODE_RX_SINGLE_7X 0x06 // PA config -#define PA_BOOST_7X 0x80 +#define PA_BOOST_7X 0x80 // IRQ masks -#define IRQ_TX_DONE_MASK_7X 0x08 +#define IRQ_TX_DONE_MASK_7X 0x08 +#define IRQ_RX_DONE_MASK_7X 0x40 #define IRQ_PAYLOAD_CRC_ERROR_MASK_7X 0x20 -#define IRQ_RX_DONE_MASK_7X 0x40 - -extern SPIClass SPI; #define MAX_PKT_LENGTH 255 #define SYNC_WORD_7X 0x12 +extern SPIClass SPI; + sx127x::sx127x() : _spiSettings(8E6, MSBFIRST, SPI_MODE0), _ss(LORA_DEFAULT_SS_PIN), _reset(LORA_DEFAULT_RESET_PIN), _dio0(LORA_DEFAULT_DIO0_PIN), _frequency(0), _packetIndex(0), _preinit_done(false), - _onReceive(NULL) -{ - // overide Stream timeout value - setTimeout(0); -} + _onReceive(NULL) { setTimeout(0); } + +void sx127x::setSPIFrequency(uint32_t frequency) { _spiSettings = SPISettings(frequency, MSBFIRST, SPI_MODE0); } +void sx127x::setPins(int ss, int reset, int dio0, int busy) { _ss = ss; _reset = reset; _dio0 = dio0; _busy = busy; } +uint8_t ISR_VECT sx127x::readRegister(uint8_t address) { return singleTransfer(address & 0x7f, 0x00); } +void sx127x::writeRegister(uint8_t address, uint8_t value) { singleTransfer(address | 0x80, value); } +void sx127x::idle() { writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_STDBY_7X); } +void sx127x::sleep() { writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_SLEEP_7X); } +uint8_t sx127x::modemStatus() { return readRegister(REG_MODEM_STAT_7X); } +void sx127x::setSyncWord(uint8_t sw) { writeRegister(REG_SYNC_WORD_7X, sw); } +void sx127x::enableCrc() { writeRegister(REG_MODEM_CONFIG_2_7X, readRegister(REG_MODEM_CONFIG_2_7X) | 0x04); } +void sx127x::disableCrc() { writeRegister(REG_MODEM_CONFIG_2_7X, readRegister(REG_MODEM_CONFIG_2_7X) & 0xfb); } +void sx127x::enableTCXO() { uint8_t tcxo_reg = readRegister(REG_TCXO_7X); writeRegister(REG_TCXO_7X, tcxo_reg | 0x10); } +void sx127x::disableTCXO() { uint8_t tcxo_reg = readRegister(REG_TCXO_7X); writeRegister(REG_TCXO_7X, tcxo_reg & 0xEF); } +void sx127x::explicitHeaderMode() { _implicitHeaderMode = 0; writeRegister(REG_MODEM_CONFIG_1_7X, readRegister(REG_MODEM_CONFIG_1_7X) & 0xfe); } +void sx127x::implicitHeaderMode() { _implicitHeaderMode = 1; writeRegister(REG_MODEM_CONFIG_1_7X, readRegister(REG_MODEM_CONFIG_1_7X) | 0x01); } +byte sx127x::random() { return readRegister(REG_RSSI_WIDEBAND_7X); } +void sx127x::flush() { } bool sx127x::preInit() { - // setup pins pinMode(_ss, OUTPUT); - // set SS high digitalWrite(_ss, HIGH); - SPI.begin(); - // check version (retry for up to 2 seconds) + // Check modem version uint8_t version; long start = millis(); - while (((millis() - start) < 2000) && (millis() >= start)) { + while (((millis() - start) < 500) && (millis() >= start)) { version = readRegister(REG_VERSION_7X); - if (version == 0x12) { - break; - } + if (version == 0x12) { break; } delay(100); } - if (version != 0x12) { - return false; - } + + if (version != 0x12) { return false; } _preinit_done = true; return true; } -uint8_t ISR_VECT sx127x::readRegister(uint8_t address) -{ - return singleTransfer(address & 0x7f, 0x00); -} - -void sx127x::writeRegister(uint8_t address, uint8_t value) -{ - singleTransfer(address | 0x80, value); -} - -uint8_t ISR_VECT sx127x::singleTransfer(uint8_t address, uint8_t value) -{ +uint8_t ISR_VECT sx127x::singleTransfer(uint8_t address, uint8_t value) { uint8_t response; digitalWrite(_ss, LOW); - SPI.beginTransaction(_spiSettings); SPI.transfer(address); response = SPI.transfer(value); SPI.endTransaction(); - digitalWrite(_ss, HIGH); return response; } - -int sx127x::begin(long frequency) -{ +int sx127x::begin(long frequency) { if (_reset != -1) { pinMode(_reset, OUTPUT); - // perform reset + // Perform reset digitalWrite(_reset, LOW); delay(10); digitalWrite(_reset, HIGH); delay(10); } - if (_busy != -1) { - pinMode(_busy, INPUT); - } + if (_busy != -1) { pinMode(_busy, INPUT); } if (!_preinit_done) { - if (!preInit()) { - return false; - } + if (!preInit()) { return false; } } - // put in sleep mode sleep(); - - // set frequency setFrequency(frequency); // set base addresses writeRegister(REG_FIFO_TX_BASE_ADDR_7X, 0); writeRegister(REG_FIFO_RX_BASE_ADDR_7X, 0); - // set LNA boost + // set LNA boost and auto AGC writeRegister(REG_LNA_7X, readRegister(REG_LNA_7X) | 0x03); - - // set auto AGC writeRegister(REG_MODEM_CONFIG_3_7X, 0x04); setSyncWord(SYNC_WORD_7X); @@ -190,20 +173,13 @@ int sx127x::begin(long frequency) return 1; } -void sx127x::end() -{ - // put in sleep mode +void sx127x::end() { sleep(); - - // stop SPI SPI.end(); - _preinit_done = false; } -int sx127x::beginPacket(int implicitHeader) -{ - // put in standby mode +int sx127x::beginPacket(int implicitHeader) { idle(); if (implicitHeader) { @@ -212,33 +188,27 @@ int sx127x::beginPacket(int implicitHeader) explicitHeaderMode(); } - // reset FIFO address and payload length + // Reset FIFO address and payload length writeRegister(REG_FIFO_ADDR_PTR_7X, 0); writeRegister(REG_PAYLOAD_LENGTH_7X, 0); return 1; } -int sx127x::endPacket() -{ - // put in TX mode +int sx127x::endPacket() { + // Enter TX mode writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_TX_7X); - // wait for TX done + // Wait for TX completion while ((readRegister(REG_IRQ_FLAGS_7X) & IRQ_TX_DONE_MASK_7X) == 0) { yield(); } - // clear IRQ's + // Clear TX complete IRQ writeRegister(REG_IRQ_FLAGS_7X, IRQ_TX_DONE_MASK_7X); return 1; } -uint8_t sx127x::modemStatus() { - return readRegister(REG_MODEM_STAT_7X); -} - - uint8_t sx127x::currentRssiRaw() { uint8_t rssi = readRegister(REG_RSSI_VALUE_7X); return rssi; @@ -280,8 +250,7 @@ float ISR_VECT sx127x::packetSnr() { return ((int8_t)readRegister(REG_PKT_SNR_VALUE_7X)) * 0.25; } -long sx127x::packetFrequencyError() -{ +long sx127x::packetFrequencyError() { int32_t freqError = 0; freqError = static_cast(readRegister(REG_FREQ_ERROR_MSB_7X) & B111); freqError <<= 8L; @@ -294,158 +263,99 @@ long sx127x::packetFrequencyError() } const float fXtal = 32E6; // FXOSC: crystal oscillator (XTAL) frequency (2.5. Chip Specification, p. 14) - const float fError = ((static_cast(freqError) * (1L << 24)) / fXtal) * (getSignalBandwidth() / 500000.0f); // p. 37 + const float fError = ((static_cast(freqError) * (1L << 24)) / fXtal) * (getSignalBandwidth() / 500000.0f); return static_cast(fError); } -size_t sx127x::write(uint8_t byte) -{ - return write(&byte, sizeof(byte)); -} +size_t sx127x::write(uint8_t byte) { return write(&byte, sizeof(byte)); } -size_t sx127x::write(const uint8_t *buffer, size_t size) -{ +size_t sx127x::write(const uint8_t *buffer, size_t size) { int currentLength = readRegister(REG_PAYLOAD_LENGTH_7X); - - // check size if ((currentLength + size) > MAX_PKT_LENGTH) { size = MAX_PKT_LENGTH - currentLength; } - // write data for (size_t i = 0; i < size; i++) { writeRegister(REG_FIFO_7X, buffer[i]); } - // update length writeRegister(REG_PAYLOAD_LENGTH_7X, currentLength + size); return size; } -int ISR_VECT sx127x::available() -{ - return (readRegister(REG_RX_NB_BYTES_7X) - _packetIndex); -} - -int ISR_VECT sx127x::read() -{ - if (!available()) { - return -1; - } +int ISR_VECT sx127x::available() { return (readRegister(REG_RX_NB_BYTES_7X) - _packetIndex); } +int ISR_VECT sx127x::read() { + if (!available()) { return -1; } _packetIndex++; return readRegister(REG_FIFO_7X); } -int sx127x::peek() -{ - if (!available()) { - return -1; - } +int sx127x::peek() { + if (!available()) { return -1; } - // store current FIFO address + // Remember current FIFO address, read, and then reset address int currentAddress = readRegister(REG_FIFO_ADDR_PTR_7X); - - // read uint8_t b = readRegister(REG_FIFO_7X); - - // restore FIFO address writeRegister(REG_FIFO_ADDR_PTR_7X, currentAddress); return b; } -void sx127x::flush() -{ -} - -void sx127x::onReceive(void(*callback)(int)) -{ +void sx127x::onReceive(void(*callback)(int)) { _onReceive = callback; if (callback) { pinMode(_dio0, INPUT); - writeRegister(REG_DIO_MAPPING_1_7X, 0x00); -#ifdef SPI_HAS_NOTUSINGINTERRUPT - SPI.usingInterrupt(digitalPinToInterrupt(_dio0)); -#endif + + #ifdef SPI_HAS_NOTUSINGINTERRUPT + SPI.usingInterrupt(digitalPinToInterrupt(_dio0)); + #endif + attachInterrupt(digitalPinToInterrupt(_dio0), sx127x::onDio0Rise, RISING); + } else { detachInterrupt(digitalPinToInterrupt(_dio0)); -#ifdef SPI_HAS_NOTUSINGINTERRUPT - SPI.notUsingInterrupt(digitalPinToInterrupt(_dio0)); -#endif + + #ifdef SPI_HAS_NOTUSINGINTERRUPT + SPI.notUsingInterrupt(digitalPinToInterrupt(_dio0)); + #endif } } -void sx127x::receive(int size) -{ - if (size > 0) { - implicitHeaderMode(); +void sx127x::receive(int size) { + if (size > 0) { + implicitHeaderMode(); + writeRegister(REG_PAYLOAD_LENGTH_7X, size & 0xff); + } else { explicitHeaderMode(); } - writeRegister(REG_PAYLOAD_LENGTH_7X, size & 0xff); - } else { - explicitHeaderMode(); - } - - writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_RX_CONTINUOUS_7X); -} - -void sx127x::idle() -{ - writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_STDBY_7X); -} - -void sx127x::sleep() -{ - writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_SLEEP_7X); -} - -void sx127x::enableTCXO() { - uint8_t tcxo_reg = readRegister(REG_TCXO_7X); - writeRegister(REG_TCXO_7X, tcxo_reg | 0x10); -} - -void sx127x::disableTCXO() { - uint8_t tcxo_reg = readRegister(REG_TCXO_7X); - writeRegister(REG_TCXO_7X, tcxo_reg & 0xEF); + writeRegister(REG_OP_MODE_7X, MODE_LONG_RANGE_MODE_7X | MODE_RX_CONTINUOUS_7X); } void sx127x::setTxPower(int level, int outputPin) { - if (PA_OUTPUT_RFO_PIN == outputPin) { - // RFO - if (level < 0) { - level = 0; - } else if (level > 14) { - level = 14; - } + // Setup according to RFO or PA_BOOST output pin + if (PA_OUTPUT_RFO_PIN == outputPin) { + if (level < 0) { level = 0; } + else if (level > 14) { level = 14; } - writeRegister(REG_PA_DAC_7X, 0x84); - writeRegister(REG_PA_CONFIG_7X, 0x70 | level); + writeRegister(REG_PA_DAC_7X, 0x84); + writeRegister(REG_PA_CONFIG_7X, 0x70 | level); - } else { - // PA BOOST - if (level < 2) { - level = 2; - } else if (level > 17) { - level = 17; - } + } else { + if (level < 2) { level = 2; } + else if (level > 17) { level = 17; } - writeRegister(REG_PA_DAC_7X, 0x84); - writeRegister(REG_PA_CONFIG_7X, PA_BOOST_7X | (level - 2)); - } + writeRegister(REG_PA_DAC_7X, 0x84); + writeRegister(REG_PA_CONFIG_7X, PA_BOOST_7X | (level - 2)); + } } -uint8_t sx127x::getTxPower() { - byte txp = readRegister(REG_PA_CONFIG_7X); - return txp; -} +uint8_t sx127x::getTxPower() { byte txp = readRegister(REG_PA_CONFIG_7X); return txp; } void sx127x::setFrequency(unsigned long frequency) { _frequency = frequency; - uint32_t frf = ((uint64_t)frequency << 19) / 32000000; writeRegister(REG_FRF_MSB_7X, (uint8_t)(frf >> 16)); @@ -456,221 +366,132 @@ void sx127x::setFrequency(unsigned long frequency) { } uint32_t sx127x::getFrequency() { - uint8_t msb = readRegister(REG_FRF_MSB_7X); - uint8_t mid = readRegister(REG_FRF_MID_7X); - uint8_t lsb = readRegister(REG_FRF_LSB_7X); + uint8_t msb = readRegister(REG_FRF_MSB_7X); + uint8_t mid = readRegister(REG_FRF_MID_7X); + uint8_t lsb = readRegister(REG_FRF_LSB_7X); - uint32_t frf = ((uint32_t)msb << 16) | ((uint32_t)mid << 8) | (uint32_t)lsb; - uint64_t frm = (uint64_t)frf*32000000; - uint32_t frequency = (frm >> 19); + uint32_t frf = ((uint32_t)msb << 16) | ((uint32_t)mid << 8) | (uint32_t)lsb; + uint64_t frm = (uint64_t)frf*32000000; + uint32_t frequency = (frm >> 19); - return frequency; + return frequency; } -void sx127x::setSpreadingFactor(int sf) -{ - if (sf < 6) { - sf = 6; - } else if (sf > 12) { - sf = 12; - } +void sx127x::setSpreadingFactor(int sf) { + if (sf < 6) { sf = 6; } + else if (sf > 12) { sf = 12; } if (sf == 6) { - writeRegister(REG_DETECTION_OPTIMIZE_7X, 0xc5); - writeRegister(REG_DETECTION_THRESHOLD_7X, 0x0c); + writeRegister(REG_DETECTION_OPTIMIZE_7X, 0xc5); + writeRegister(REG_DETECTION_THRESHOLD_7X, 0x0c); } else { - writeRegister(REG_DETECTION_OPTIMIZE_7X, 0xc3); - writeRegister(REG_DETECTION_THRESHOLD_7X, 0x0a); + writeRegister(REG_DETECTION_OPTIMIZE_7X, 0xc3); + writeRegister(REG_DETECTION_THRESHOLD_7X, 0x0a); } writeRegister(REG_MODEM_CONFIG_2_7X, (readRegister(REG_MODEM_CONFIG_2_7X) & 0x0f) | ((sf << 4) & 0xf0)); handleLowDataRate(); } -long sx127x::getSignalBandwidth() -{ - byte bw = (readRegister(REG_MODEM_CONFIG_1_7X) >> 4); - switch (bw) { - case 0: return 7.8E3; - case 1: return 10.4E3; - case 2: return 15.6E3; - case 3: return 20.8E3; - case 4: return 31.25E3; - case 5: return 41.7E3; - case 6: return 62.5E3; - case 7: return 125E3; - case 8: return 250E3; - case 9: return 500E3; - } +long sx127x::getSignalBandwidth() { + byte bw = (readRegister(REG_MODEM_CONFIG_1_7X) >> 4); + switch (bw) { + case 0: return 7.8E3; + case 1: return 10.4E3; + case 2: return 15.6E3; + case 3: return 20.8E3; + case 4: return 31.25E3; + case 5: return 41.7E3; + case 6: return 62.5E3; + case 7: return 125E3; + case 8: return 250E3; + case 9: return 500E3; } + return 0; } -void sx127x::handleLowDataRate(){ - int sf = (readRegister(REG_MODEM_CONFIG_2_7X) >> 4); - if ( long( (1< 16) { - // set auto AGC and LowDataRateOptimize - writeRegister(REG_MODEM_CONFIG_3_7X, (1<<3)|(1<<2)); - } else { - // set auto AGC - writeRegister(REG_MODEM_CONFIG_3_7X, (1<<2)); - } -} - -void sx127x::optimizeModemSensitivity(){ - byte bw = (readRegister(REG_MODEM_CONFIG_1_7X) >> 4); - uint32_t freq = getFrequency(); - - if (bw == 9 && (410E6 <= freq) && (freq <= 525E6)) { - writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x02); - writeRegister(REG_HIGH_BW_OPTIMIZE_2_7X, 0x7f); - } else if (bw == 9 && (820E6 <= freq) && (freq <= 1020E6)) { - writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x02); - writeRegister(REG_HIGH_BW_OPTIMIZE_2_7X, 0x64); - } else { - writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x03); - } -} - -void sx127x::setSignalBandwidth(long sbw) -{ - int bw; - - if (sbw <= 7.8E3) { - bw = 0; - } else if (sbw <= 10.4E3) { - bw = 1; - } else if (sbw <= 15.6E3) { - bw = 2; - } else if (sbw <= 20.8E3) { - bw = 3; - } else if (sbw <= 31.25E3) { - bw = 4; - } else if (sbw <= 41.7E3) { - bw = 5; - } else if (sbw <= 62.5E3) { - bw = 6; - } else if (sbw <= 125E3) { - bw = 7; - } else if (sbw <= 250E3) { - bw = 8; - } else /*if (sbw <= 250E3)*/ { - bw = 9; - } - - writeRegister(REG_MODEM_CONFIG_1_7X, (readRegister(REG_MODEM_CONFIG_1_7X) & 0x0f) | (bw << 4)); - +void sx127x::setSignalBandwidth(long sbw) { + int bw; + if (sbw <= 7.8E3) { + bw = 0; + } else if (sbw <= 10.4E3) { + bw = 1; + } else if (sbw <= 15.6E3) { + bw = 2; + } else if (sbw <= 20.8E3) { + bw = 3; + } else if (sbw <= 31.25E3) { + bw = 4; + } else if (sbw <= 41.7E3) { + bw = 5; + } else if (sbw <= 62.5E3) { + bw = 6; + } else if (sbw <= 125E3) { + bw = 7; + } else if (sbw <= 250E3) { + bw = 8; + } else /*if (sbw <= 250E3)*/ { + bw = 9; + } + writeRegister(REG_MODEM_CONFIG_1_7X, (readRegister(REG_MODEM_CONFIG_1_7X) & 0x0f) | (bw << 4)); handleLowDataRate(); optimizeModemSensitivity(); } -void sx127x::setCodingRate4(int denominator) -{ - if (denominator < 5) { - denominator = 5; - } else if (denominator > 8) { - denominator = 8; - } - +void sx127x::setCodingRate4(int denominator) { + if (denominator < 5) { denominator = 5; } + else if (denominator > 8) { denominator = 8; } int cr = denominator - 4; - writeRegister(REG_MODEM_CONFIG_1_7X, (readRegister(REG_MODEM_CONFIG_1_7X) & 0xf1) | (cr << 1)); } -void sx127x::setPreambleLength(long length) -{ +void sx127x::setPreambleLength(long length) { writeRegister(REG_PREAMBLE_MSB_7X, (uint8_t)(length >> 8)); writeRegister(REG_PREAMBLE_LSB_7X, (uint8_t)(length >> 0)); } -void sx127x::setSyncWord(uint8_t sw) -{ - writeRegister(REG_SYNC_WORD_7X, sw); -} - -void sx127x::enableCrc() -{ - writeRegister(REG_MODEM_CONFIG_2_7X, readRegister(REG_MODEM_CONFIG_2_7X) | 0x04); -} - -void sx127x::disableCrc() -{ - writeRegister(REG_MODEM_CONFIG_2_7X, readRegister(REG_MODEM_CONFIG_2_7X) & 0xfb); -} - -byte sx127x::random() -{ - return readRegister(REG_RSSI_WIDEBAND_7X); -} - -void sx127x::setPins(int ss, int reset, int dio0, int busy) -{ - _ss = ss; - _reset = reset; - _dio0 = dio0; - _busy = busy; -} - -void sx127x::setSPIFrequency(uint32_t frequency) -{ - _spiSettings = SPISettings(frequency, MSBFIRST, SPI_MODE0); -} - -void sx127x::dumpRegisters(Stream& out) -{ - for (int i = 0; i < 128; i++) { - out.print("0x"); - out.print(i, HEX); - out.print(": 0x"); - out.println(readRegister(i), HEX); +void sx127x::handleLowDataRate() { + int sf = (readRegister(REG_MODEM_CONFIG_2_7X) >> 4); + if ( long( (1< 16) { + // Set auto AGC and LowDataRateOptimize + writeRegister(REG_MODEM_CONFIG_3_7X, (1<<3)|(1<<2)); + } else { + // Only set auto AGC + writeRegister(REG_MODEM_CONFIG_3_7X, (1<<2)); } } -void sx127x::explicitHeaderMode() -{ - _implicitHeaderMode = 0; +void sx127x::optimizeModemSensitivity() { + byte bw = (readRegister(REG_MODEM_CONFIG_1_7X) >> 4); + uint32_t freq = getFrequency(); - writeRegister(REG_MODEM_CONFIG_1_7X, readRegister(REG_MODEM_CONFIG_1_7X) & 0xfe); + if (bw == 9 && (410E6 <= freq) && (freq <= 525E6)) { + writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x02); + writeRegister(REG_HIGH_BW_OPTIMIZE_2_7X, 0x7f); + } else if (bw == 9 && (820E6 <= freq) && (freq <= 1020E6)) { + writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x02); + writeRegister(REG_HIGH_BW_OPTIMIZE_2_7X, 0x64); + } else { + writeRegister(REG_HIGH_BW_OPTIMIZE_1_7X, 0x03); + } } -void sx127x::implicitHeaderMode() -{ - _implicitHeaderMode = 1; +void ISR_VECT sx127x::handleDio0Rise() { + int irqFlags = readRegister(REG_IRQ_FLAGS_7X); - writeRegister(REG_MODEM_CONFIG_1_7X, readRegister(REG_MODEM_CONFIG_1_7X) | 0x01); + // Clear IRQs + writeRegister(REG_IRQ_FLAGS_7X, irqFlags); + if ((irqFlags & IRQ_PAYLOAD_CRC_ERROR_MASK_7X) == 0) { + _packetIndex = 0; + int packetLength = _implicitHeaderMode ? readRegister(REG_PAYLOAD_LENGTH_7X) : readRegister(REG_RX_NB_BYTES_7X); + writeRegister(REG_FIFO_ADDR_PTR_7X, readRegister(REG_FIFO_RX_CURRENT_ADDR_7X)); + if (_onReceive) { _onReceive(packetLength); } + writeRegister(REG_FIFO_ADDR_PTR_7X, 0); + } } - -void ISR_VECT sx127x::handleDio0Rise() -{ - int irqFlags = readRegister(REG_IRQ_FLAGS_7X); - - // clear IRQ's - writeRegister(REG_IRQ_FLAGS_7X, irqFlags); - if ((irqFlags & IRQ_PAYLOAD_CRC_ERROR_MASK_7X) == 0) { - - // received a packet - _packetIndex = 0; - - // read packet length - int packetLength = _implicitHeaderMode ? readRegister(REG_PAYLOAD_LENGTH_7X) : readRegister(REG_RX_NB_BYTES_7X); - - // set FIFO address to current RX address - writeRegister(REG_FIFO_ADDR_PTR_7X, readRegister(REG_FIFO_RX_CURRENT_ADDR_7X)); - - if (_onReceive) { - _onReceive(packetLength); - } - - // reset FIFO address - writeRegister(REG_FIFO_ADDR_PTR_7X, 0); - } -} - -void ISR_VECT sx127x::onDio0Rise() -{ - sx127x_modem.handleDio0Rise(); -} +void ISR_VECT sx127x::onDio0Rise() { sx127x_modem.handleDio0Rise(); } sx127x sx127x_modem; diff --git a/sx127x.h b/sx127x.h index b12002f..a43620d 100644 --- a/sx127x.h +++ b/sx127x.h @@ -78,8 +78,6 @@ public: void setPins(int ss = LORA_DEFAULT_SS_PIN, int reset = LORA_DEFAULT_RESET_PIN, int dio0 = LORA_DEFAULT_DIO0_PIN, int busy = LORA_DEFAULT_BUSY_PIN); void setSPIFrequency(uint32_t frequency); - void dumpRegisters(Stream& out); - private: void explicitHeaderMode(); void implicitHeaderMode();