[LR11x0] Added GFSK modem support (#679)
This commit is contained in:
parent
4d1157e3a4
commit
6fa4aa3ebb
3 changed files with 698 additions and 35 deletions
153
examples/LR11x0/LR11x0_GFSK_Modem/LR11x0_GFSK_Modem.ino
Normal file
153
examples/LR11x0/LR11x0_GFSK_Modem/LR11x0_GFSK_Modem.ino
Normal file
|
@ -0,0 +1,153 @@
|
||||||
|
/*
|
||||||
|
RadioLib LR11x0 GFSK Modem Example
|
||||||
|
|
||||||
|
This example shows how to use GFSK modem in LR11x0 chips.
|
||||||
|
|
||||||
|
NOTE: The sketch below is just a guide on how to use
|
||||||
|
GFSK modem, so this code should not be run directly!
|
||||||
|
Instead, modify the other examples to use GFSK
|
||||||
|
modem and use the appropriate configuration
|
||||||
|
methods.
|
||||||
|
|
||||||
|
For default module settings, see the wiki page
|
||||||
|
https://github.com/jgromes/RadioLib/wiki/Default-configuration#lr11x0---gfsk-modem
|
||||||
|
|
||||||
|
For full API reference, see the GitHub Pages
|
||||||
|
https://jgromes.github.io/RadioLib/
|
||||||
|
*/
|
||||||
|
|
||||||
|
// include the library
|
||||||
|
#include <RadioLib.h>
|
||||||
|
|
||||||
|
// LR1110 has the following connections:
|
||||||
|
// NSS pin: 10
|
||||||
|
// DIO1 pin: 2
|
||||||
|
// NRST pin: 3
|
||||||
|
// BUSY pin: 9
|
||||||
|
LR1110 radio = new Module(10, 2, 3, 9);
|
||||||
|
|
||||||
|
// or using RadioShield
|
||||||
|
// https://github.com/jgromes/RadioShield
|
||||||
|
//LR1110 radio = RadioShield.ModuleA;
|
||||||
|
|
||||||
|
void setup() {
|
||||||
|
Serial.begin(9600);
|
||||||
|
|
||||||
|
// initialize LR1110 with default settings
|
||||||
|
Serial.print(F("[LR1110] Initializing ... "));
|
||||||
|
int state = radio.beginGFSK();
|
||||||
|
if (state == RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.println(F("success!"));
|
||||||
|
} else {
|
||||||
|
Serial.print(F("failed, code "));
|
||||||
|
Serial.println(state);
|
||||||
|
while (true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// if needed, you can switch between any of the modems
|
||||||
|
//
|
||||||
|
// radio.begin() start LoRa modem (and disable GFSK)
|
||||||
|
// radio.beginGFSK() start GFSK modem (and disable LoRa)
|
||||||
|
|
||||||
|
// the following settings can also
|
||||||
|
// be modified at run-time
|
||||||
|
state = radio.setFrequency(433.5);
|
||||||
|
state = radio.setBitRate(100.0);
|
||||||
|
state = radio.setFrequencyDeviation(10.0);
|
||||||
|
state = radio.setRxBandwidth(250.0);
|
||||||
|
state = radio.setOutputPower(10.0);
|
||||||
|
state = radio.setDataShaping(RADIOLIB_SHAPING_1_0);
|
||||||
|
uint8_t syncWord[] = {0x01, 0x23, 0x45, 0x67,
|
||||||
|
0x89, 0xAB, 0xCD, 0xEF};
|
||||||
|
state = radio.setSyncWord(syncWord, 8);
|
||||||
|
if (state != RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.print(F("Unable to set configuration, code "));
|
||||||
|
Serial.println(state);
|
||||||
|
while (true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// GFSK modem on LR11x0 can handle the sync word setting in bits, not just
|
||||||
|
// whole bytes. The value used is left-justified.
|
||||||
|
// This makes same result as radio.setSyncWord(syncWord, 8):
|
||||||
|
state = radio.setSyncBits(syncWord, 64);
|
||||||
|
// This will use 0x012 as sync word (12 bits only):
|
||||||
|
state = radio.setSyncBits(syncWord, 12);
|
||||||
|
|
||||||
|
// GFSK modem allows advanced CRC configuration
|
||||||
|
// Default is CCIT CRC16 (2 bytes, initial 0x1D0F, polynomial 0x1021, inverted)
|
||||||
|
// Set CRC to IBM CRC (2 bytes, initial 0xFFFF, polynomial 0x8005, non-inverted)
|
||||||
|
state = radio.setCRC(2, 0xFFFF, 0x8005, false);
|
||||||
|
// set CRC length to 0 to disable CRC
|
||||||
|
|
||||||
|
#warning "This sketch is just an API guide! Read the note at line 6."
|
||||||
|
}
|
||||||
|
|
||||||
|
void loop() {
|
||||||
|
// GFSK modem can use the same transmit/receive methods
|
||||||
|
// as the LoRa modem, even their interrupt-driven versions
|
||||||
|
|
||||||
|
// transmit GFSK packet
|
||||||
|
int state = radio.transmit("Hello World!");
|
||||||
|
/*
|
||||||
|
byte byteArr[] = {0x01, 0x23, 0x45, 0x67,
|
||||||
|
0x89, 0xAB, 0xCD, 0xEF};
|
||||||
|
int state = radio.transmit(byteArr, 8);
|
||||||
|
*/
|
||||||
|
if (state == RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.println(F("[LR1110] Packet transmitted successfully!"));
|
||||||
|
} else if (state == RADIOLIB_ERR_PACKET_TOO_LONG) {
|
||||||
|
Serial.println(F("[LR1110] Packet too long!"));
|
||||||
|
} else if (state == RADIOLIB_ERR_TX_TIMEOUT) {
|
||||||
|
Serial.println(F("[LR1110] Timed out while transmitting!"));
|
||||||
|
} else {
|
||||||
|
Serial.println(F("[LR1110] Failed to transmit packet, code "));
|
||||||
|
Serial.println(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
// receive GFSK packet
|
||||||
|
String str;
|
||||||
|
state = radio.receive(str);
|
||||||
|
/*
|
||||||
|
byte byteArr[8];
|
||||||
|
int state = radio.receive(byteArr, 8);
|
||||||
|
*/
|
||||||
|
if (state == RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.println(F("[LR1110] Received packet!"));
|
||||||
|
Serial.print(F("[LR1110] Data:\t"));
|
||||||
|
Serial.println(str);
|
||||||
|
} else if (state == RADIOLIB_ERR_RX_TIMEOUT) {
|
||||||
|
Serial.println(F("[LR1110] Timed out while waiting for packet!"));
|
||||||
|
} else {
|
||||||
|
Serial.print(F("[LR1110] Failed to receive packet, code "));
|
||||||
|
Serial.println(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
// GFSK modem has built-in address filtering system
|
||||||
|
// it can be enabled by setting node address, broadcast
|
||||||
|
// address, or both
|
||||||
|
//
|
||||||
|
// to transmit packet to a particular address,
|
||||||
|
// use the following methods:
|
||||||
|
//
|
||||||
|
// radio.transmit("Hello World!", address);
|
||||||
|
// radio.startTransmit("Hello World!", address);
|
||||||
|
|
||||||
|
// set node address to 0x02
|
||||||
|
state = radio.setNodeAddress(0x02);
|
||||||
|
// set broadcast address to 0xFF
|
||||||
|
state = radio.setBroadcastAddress(0xFF);
|
||||||
|
if (state != RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.println(F("[LR1110] Unable to set address filter, code "));
|
||||||
|
Serial.println(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
// address filtering can also be disabled
|
||||||
|
// NOTE: calling this method will also erase previously set
|
||||||
|
// node and broadcast address
|
||||||
|
/*
|
||||||
|
state = radio.disableAddressFiltering();
|
||||||
|
if (state != RADIOLIB_ERR_NONE) {
|
||||||
|
Serial.println(F("Unable to remove address filter, code "));
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
}
|
|
@ -110,14 +110,47 @@ int16_t LR11x0::beginGFSK(float br, float freqDev, float rxBw, uint16_t preamble
|
||||||
int16_t state = standby();
|
int16_t state = standby();
|
||||||
RADIOLIB_ASSERT(state);
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
// TODO implement GFSK
|
// set TCXO control, if requested
|
||||||
(void)br;
|
if(!this->XTAL && tcxoVoltage > 0.0) {
|
||||||
(void)freqDev;
|
state = setTCXO(tcxoVoltage);
|
||||||
(void)rxBw;
|
RADIOLIB_ASSERT(state);
|
||||||
(void)preambleLength;
|
}
|
||||||
(void)tcxoVoltage;
|
|
||||||
|
|
||||||
return(RADIOLIB_ERR_UNSUPPORTED);
|
// configure settings not accessible by API
|
||||||
|
state = config(RADIOLIB_LR11X0_PACKET_TYPE_GFSK);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// configure publicly accessible settings
|
||||||
|
state = setBitRate(br);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setFrequencyDeviation(freqDev);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setRxBandwidth(rxBw);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setPreambleLength(preambleLength);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set publicly accessible settings that are not a part of begin method
|
||||||
|
uint8_t sync[] = { 0x12, 0xAD };
|
||||||
|
state = setSyncWord(sync, 2);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setDataShaping(RADIOLIB_SHAPING_NONE);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setEncoding(RADIOLIB_ENCODING_NRZ);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = variablePacketLengthMode(RADIOLIB_LR11X0_MAX_PACKET_LENGTH);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setCRC(2);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
return(RADIOLIB_ERR_NONE);
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t LR11x0::reset() {
|
int16_t LR11x0::reset() {
|
||||||
|
@ -267,12 +300,12 @@ int16_t LR11x0::standby(uint8_t mode, bool wakeup) {
|
||||||
// set RF switch (if present)
|
// set RF switch (if present)
|
||||||
this->mod->setRfSwitchState(Module::MODE_IDLE);
|
this->mod->setRfSwitchState(Module::MODE_IDLE);
|
||||||
|
|
||||||
// TODO this will block BUSY forever
|
if(wakeup) {
|
||||||
(void)wakeup;
|
// pull NSS low for a while to wake up
|
||||||
/*if(wakeup) {
|
|
||||||
// pull NSS low to wake up
|
|
||||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||||
}*/
|
this->mod->hal->delay(1);
|
||||||
|
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelHigh);
|
||||||
|
}
|
||||||
|
|
||||||
uint8_t buff[] = { mode };
|
uint8_t buff[] = { mode };
|
||||||
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_SET_STANDBY, true, buff, 1));
|
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_SET_STANDBY, true, buff, 1));
|
||||||
|
@ -577,6 +610,327 @@ int16_t LR11x0::setSyncWord(uint8_t syncWord) {
|
||||||
return(setLoRaSyncWord(syncWord));
|
return(setLoRaSyncWord(syncWord));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setBitRate(float br) {
|
||||||
|
RADIOLIB_CHECK_RANGE(br, 0.6, 300.0, RADIOLIB_ERR_INVALID_BIT_RATE);
|
||||||
|
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set bit rate value
|
||||||
|
// TODO implement fractional bit rate configuration
|
||||||
|
this->bitRate = br * 1000.0;
|
||||||
|
return(setModulationParamsGFSK(this->bitRate, this->pulseShape, this->rxBandwidth, this->frequencyDev));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setFrequencyDeviation(float freqDev) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set frequency deviation to lowest available setting (required for digimodes)
|
||||||
|
float newFreqDev = freqDev;
|
||||||
|
if(freqDev < 0.0) {
|
||||||
|
newFreqDev = 0.6;
|
||||||
|
}
|
||||||
|
|
||||||
|
RADIOLIB_CHECK_RANGE(newFreqDev, 0.6, 200.0, RADIOLIB_ERR_INVALID_FREQUENCY_DEVIATION);
|
||||||
|
this->frequencyDev = freqDev * 1000.0;
|
||||||
|
return(setModulationParamsGFSK(this->bitRate, this->pulseShape, this->rxBandwidth, this->frequencyDev));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setRxBandwidth(float rxBw) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// check modulation parameters
|
||||||
|
/*if(2 * this->frequencyDev + this->bitRate > rxBw * 1000.0) {
|
||||||
|
return(RADIOLIB_ERR_INVALID_MODULATION_PARAMETERS);
|
||||||
|
}*/
|
||||||
|
|
||||||
|
// check allowed receiver bandwidth values
|
||||||
|
if(fabs(rxBw - 4.8) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_4_8;
|
||||||
|
} else if(fabs(rxBw - 5.8) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_5_8;
|
||||||
|
} else if(fabs(rxBw - 7.3) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_7_3;
|
||||||
|
} else if(fabs(rxBw - 9.7) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_9_7;
|
||||||
|
} else if(fabs(rxBw - 11.7) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_11_7;
|
||||||
|
} else if(fabs(rxBw - 14.6) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_14_6;
|
||||||
|
} else if(fabs(rxBw - 19.5) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_19_5;
|
||||||
|
} else if(fabs(rxBw - 23.4) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_23_4;
|
||||||
|
} else if(fabs(rxBw - 29.3) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_29_3;
|
||||||
|
} else if(fabs(rxBw - 39.0) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_39_0;
|
||||||
|
} else if(fabs(rxBw - 46.9) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_46_9;
|
||||||
|
} else if(fabs(rxBw - 58.6) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_58_6;
|
||||||
|
} else if(fabs(rxBw - 78.2) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_78_2;
|
||||||
|
} else if(fabs(rxBw - 93.8) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_93_8;
|
||||||
|
} else if(fabs(rxBw - 117.3) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_117_3;
|
||||||
|
} else if(fabs(rxBw - 156.2) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_156_2;
|
||||||
|
} else if(fabs(rxBw - 187.2) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_187_2;
|
||||||
|
} else if(fabs(rxBw - 234.3) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_234_3;
|
||||||
|
} else if(fabs(rxBw - 312.0) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_312_0;
|
||||||
|
} else if(fabs(rxBw - 373.6) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_373_6;
|
||||||
|
} else if(fabs(rxBw - 467.0) <= 0.001) {
|
||||||
|
this->rxBandwidth = RADIOLIB_LR11X0_GFSK_RX_BW_467_0;
|
||||||
|
} else {
|
||||||
|
return(RADIOLIB_ERR_INVALID_RX_BANDWIDTH);
|
||||||
|
}
|
||||||
|
|
||||||
|
// update modulation parameters
|
||||||
|
return(setModulationParamsGFSK(this->bitRate, this->pulseShape, this->rxBandwidth, this->frequencyDev));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setSyncWord(uint8_t* syncWord, size_t len) {
|
||||||
|
if((!syncWord) || (!len) || (len > RADIOLIB_LR11X0_GFSK_SYNC_WORD_LEN)) {
|
||||||
|
return(RADIOLIB_ERR_INVALID_SYNC_WORD);
|
||||||
|
}
|
||||||
|
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// update sync word length
|
||||||
|
this->syncWordLength = len*8;
|
||||||
|
state = setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// sync word is passed most-significant byte first
|
||||||
|
uint8_t fullSyncWord[RADIOLIB_LR11X0_GFSK_SYNC_WORD_LEN] = { 0 };
|
||||||
|
memcpy(fullSyncWord, syncWord, len);
|
||||||
|
return(setGfskSyncWord(fullSyncWord));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setSyncBits(uint8_t *syncWord, uint8_t bitsLen) {
|
||||||
|
if((!syncWord) || (!bitsLen) || (bitsLen > 8*RADIOLIB_LR11X0_GFSK_SYNC_WORD_LEN)) {
|
||||||
|
return(RADIOLIB_ERR_INVALID_SYNC_WORD);
|
||||||
|
}
|
||||||
|
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t bytesLen = bitsLen / 8;
|
||||||
|
if ((bitsLen % 8) != 0) {
|
||||||
|
bytesLen++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return(setSyncWord(syncWord, bytesLen));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setNodeAddress(uint8_t nodeAddr) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// enable address filtering (node only)
|
||||||
|
this->addrComp = RADIOLIB_LR11X0_GFSK_ADDR_FILTER_NODE;
|
||||||
|
state = setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set node address
|
||||||
|
this->node = nodeAddr;
|
||||||
|
return(setPacketAdrs(this->node, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setBroadcastAddress(uint8_t broadAddr) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// enable address filtering (node and broadcast)
|
||||||
|
this->addrComp = RADIOLIB_LR11X0_GFSK_ADDR_FILTER_NODE_BROADCAST;
|
||||||
|
state = setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set node and broadcast address
|
||||||
|
return(setPacketAdrs(this->node, broadAddr));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::disableAddressFiltering() {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// disable address filterin
|
||||||
|
this->addrComp = RADIOLIB_LR11X0_GFSK_ADDR_FILTER_DISABLED;
|
||||||
|
return(setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setDataShaping(uint8_t sh) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set data shaping
|
||||||
|
switch(sh) {
|
||||||
|
case RADIOLIB_SHAPING_NONE:
|
||||||
|
this->pulseShape = RADIOLIB_LR11X0_GFSK_SHAPING_NONE;
|
||||||
|
break;
|
||||||
|
case RADIOLIB_SHAPING_0_3:
|
||||||
|
this->pulseShape = RADIOLIB_LR11X0_GFSK_SHAPING_GAUSSIAN_BT_0_3;
|
||||||
|
break;
|
||||||
|
case RADIOLIB_SHAPING_0_5:
|
||||||
|
this->pulseShape = RADIOLIB_LR11X0_GFSK_SHAPING_GAUSSIAN_BT_0_5;
|
||||||
|
break;
|
||||||
|
case RADIOLIB_SHAPING_0_7:
|
||||||
|
this->pulseShape = RADIOLIB_LR11X0_GFSK_SHAPING_GAUSSIAN_BT_0_7;
|
||||||
|
break;
|
||||||
|
case RADIOLIB_SHAPING_1_0:
|
||||||
|
this->pulseShape = RADIOLIB_LR11X0_GFSK_SHAPING_GAUSSIAN_BT_1_0;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return(RADIOLIB_ERR_INVALID_DATA_SHAPING);
|
||||||
|
}
|
||||||
|
|
||||||
|
// update modulation parameters
|
||||||
|
return(setModulationParamsGFSK(this->bitRate, this->pulseShape, this->rxBandwidth, this->frequencyDev));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setEncoding(uint8_t encoding) {
|
||||||
|
return(setWhitening(encoding));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::fixedPacketLengthMode(uint8_t len) {
|
||||||
|
return(setPacketMode(RADIOLIB_LR11X0_GFSK_PACKET_LENGTH_FIXED, len));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::variablePacketLengthMode(uint8_t maxLen) {
|
||||||
|
return(setPacketMode(RADIOLIB_LR11X0_GFSK_PACKET_LENGTH_VARIABLE, maxLen));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setWhitening(bool enabled, uint16_t initial) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!enabled) {
|
||||||
|
// disable whitening
|
||||||
|
this->whitening = RADIOLIB_LR11X0_GFSK_WHITENING_DISABLED;
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// enable whitening
|
||||||
|
this->whitening = RADIOLIB_LR11X0_GFSK_WHITENING_ENABLED;
|
||||||
|
|
||||||
|
// write initial whitening value
|
||||||
|
state = setGfskWhitParams(initial);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
return(setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening));
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setDataRate(DataRate_t dr) {
|
||||||
|
// select interpretation based on active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
// set the bit rate
|
||||||
|
state = this->setBitRate(dr.fsk.bitRate);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set the frequency deviation
|
||||||
|
state = this->setFrequencyDeviation(dr.fsk.freqDev);
|
||||||
|
|
||||||
|
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||||
|
// set the spreading factor
|
||||||
|
state = this->setSpreadingFactor(dr.lora.spreadingFactor);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set the bandwidth
|
||||||
|
state = this->setBandwidth(dr.lora.bandwidth);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// set the coding rate
|
||||||
|
state = this->setCodingRate(dr.lora.codingRate);
|
||||||
|
}
|
||||||
|
|
||||||
|
return(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::checkDataRate(DataRate_t dr) {
|
||||||
|
// select interpretation based on active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
RADIOLIB_CHECK_RANGE(dr.fsk.bitRate, 0.6, 300.0, RADIOLIB_ERR_INVALID_BIT_RATE);
|
||||||
|
RADIOLIB_CHECK_RANGE(dr.fsk.freqDev, 0.6, 200.0, RADIOLIB_ERR_INVALID_FREQUENCY_DEVIATION);
|
||||||
|
return(RADIOLIB_ERR_NONE);
|
||||||
|
|
||||||
|
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||||
|
RADIOLIB_CHECK_RANGE(dr.lora.spreadingFactor, 5, 12, RADIOLIB_ERR_INVALID_SPREADING_FACTOR);
|
||||||
|
RADIOLIB_CHECK_RANGE(dr.lora.bandwidth, 0.0, 510.0, RADIOLIB_ERR_INVALID_BANDWIDTH);
|
||||||
|
RADIOLIB_CHECK_RANGE(dr.lora.codingRate, 5, 8, RADIOLIB_ERR_INVALID_CODING_RATE);
|
||||||
|
return(RADIOLIB_ERR_NONE);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return(RADIOLIB_ERR_UNKNOWN);
|
||||||
|
}
|
||||||
|
|
||||||
int16_t LR11x0::setPreambleLength(size_t preambleLength) {
|
int16_t LR11x0::setPreambleLength(size_t preambleLength) {
|
||||||
// check active modem
|
// check active modem
|
||||||
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
@ -585,6 +939,10 @@ int16_t LR11x0::setPreambleLength(size_t preambleLength) {
|
||||||
if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||||
this->preambleLengthLoRa = preambleLength;
|
this->preambleLengthLoRa = preambleLength;
|
||||||
return(setPacketParamsLoRa(this->preambleLengthLoRa, this->headerType, this->implicitLen, this->crcTypeLoRa, (uint8_t)this->invertIQEnabled));
|
return(setPacketParamsLoRa(this->preambleLengthLoRa, this->headerType, this->implicitLen, this->crcTypeLoRa, (uint8_t)this->invertIQEnabled));
|
||||||
|
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
this->preambleLengthGFSK = preambleLength;
|
||||||
|
this->preambleDetLength = RADIOLIB_LR11X0_GFSK_PREAMBLE_DETECT_16_BITS;
|
||||||
|
return(setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening));
|
||||||
}
|
}
|
||||||
|
|
||||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
@ -645,7 +1003,7 @@ int16_t LR11x0::setTCXO(float voltage, uint32_t delay) {
|
||||||
return(setTcxoMode(tune, delayValue));
|
return(setTcxoMode(tune, delayValue));
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t LR11x0::setCRC(uint8_t len, uint16_t initial, uint16_t polynomial, bool inverted) {
|
int16_t LR11x0::setCRC(uint8_t len, uint32_t initial, uint32_t polynomial, bool inverted) {
|
||||||
// check active modem
|
// check active modem
|
||||||
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
int16_t state = getPacketType(&type);
|
int16_t state = getPacketType(&type);
|
||||||
|
@ -653,18 +1011,40 @@ int16_t LR11x0::setCRC(uint8_t len, uint16_t initial, uint16_t polynomial, bool
|
||||||
if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||||
// LoRa CRC doesn't allow to set CRC polynomial, initial value, or inversion
|
// LoRa CRC doesn't allow to set CRC polynomial, initial value, or inversion
|
||||||
this->crcTypeLoRa = len > 0 ? RADIOLIB_LR11X0_LORA_CRC_ENABLED : RADIOLIB_LR11X0_LORA_CRC_DISABLED;
|
this->crcTypeLoRa = len > 0 ? RADIOLIB_LR11X0_LORA_CRC_ENABLED : RADIOLIB_LR11X0_LORA_CRC_DISABLED;
|
||||||
return(setPacketParamsLoRa(this->preambleLengthLoRa, this->crcTypeLoRa, this->implicitLen, this->headerType, (uint8_t)this->invertIQEnabled));
|
state = setPacketParamsLoRa(this->preambleLengthLoRa, this->crcTypeLoRa, this->implicitLen, this->headerType, (uint8_t)this->invertIQEnabled);
|
||||||
|
|
||||||
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
// TODO add GFSK support
|
// update packet parameters
|
||||||
(void)initial;
|
switch(len) {
|
||||||
(void)polynomial;
|
case 0:
|
||||||
(void)inverted;
|
this->crcTypeGFSK = RADIOLIB_LR11X0_GFSK_CRC_DISABLED;
|
||||||
return(RADIOLIB_ERR_UNSUPPORTED);
|
break;
|
||||||
|
case 1:
|
||||||
|
if(inverted) {
|
||||||
|
this->crcTypeGFSK = RADIOLIB_LR11X0_GFSK_CRC_1_BYTE_INV;
|
||||||
|
} else {
|
||||||
|
this->crcTypeGFSK = RADIOLIB_LR11X0_GFSK_CRC_1_BYTE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
if(inverted) {
|
||||||
|
this->crcTypeGFSK = RADIOLIB_LR11X0_GFSK_CRC_2_BYTE_INV;
|
||||||
|
} else {
|
||||||
|
this->crcTypeGFSK = RADIOLIB_LR11X0_GFSK_CRC_2_BYTE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return(RADIOLIB_ERR_INVALID_CRC_CONFIGURATION);
|
||||||
|
}
|
||||||
|
|
||||||
|
state = setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, this->packetType, RADIOLIB_LR11X0_MAX_PACKET_LENGTH, this->crcTypeGFSK, this->whitening);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
state = setGfskCrcParams(initial, polynomial);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
return(state);
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t LR11x0::invertIQ(bool enable) {
|
int16_t LR11x0::invertIQ(bool enable) {
|
||||||
|
@ -793,7 +1173,7 @@ uint32_t LR11x0::getTimeOnAir(size_t len) {
|
||||||
return(((uint32_t(1) << this->spreadingFactor) / this->bandwidthKhz) * N_symbol * 1000.0);
|
return(((uint32_t(1) << this->spreadingFactor) / this->bandwidthKhz) * N_symbol * 1000.0);
|
||||||
|
|
||||||
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
return(((uint32_t)len * 8 * 1000) / this->bitRateKbps);
|
return(((uint32_t)len * 8 * 1000000UL) / this->bitRate);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -911,6 +1291,24 @@ int16_t LR11x0::config(uint8_t modem) {
|
||||||
return(state);
|
return(state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int16_t LR11x0::setPacketMode(uint8_t mode, uint8_t len) {
|
||||||
|
// check active modem
|
||||||
|
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||||
|
int16_t state = getPacketType(&type);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||||
|
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||||
|
}
|
||||||
|
|
||||||
|
// set requested packet mode
|
||||||
|
state = setPacketParamsGFSK(this->preambleLengthGFSK, this->preambleDetLength, this->syncWordLength, this->addrComp, mode, len, this->crcTypeGFSK, this->whitening);
|
||||||
|
RADIOLIB_ASSERT(state);
|
||||||
|
|
||||||
|
// update cached value
|
||||||
|
this->packetType = mode;
|
||||||
|
return(state);
|
||||||
|
}
|
||||||
|
|
||||||
Module* LR11x0::getMod() {
|
Module* LR11x0::getMod() {
|
||||||
return(this->mod);
|
return(this->mod);
|
||||||
}
|
}
|
||||||
|
@ -1311,9 +1709,8 @@ int16_t LR11x0::getPacketStatusGFSK(float* rssiSync, float* rssiAvg, uint8_t* rx
|
||||||
int16_t state = this->SPIcommand(RADIOLIB_LR11X0_CMD_GET_PACKET_STATUS, false, buff, sizeof(buff));
|
int16_t state = this->SPIcommand(RADIOLIB_LR11X0_CMD_GET_PACKET_STATUS, false, buff, sizeof(buff));
|
||||||
|
|
||||||
// pass the replies
|
// pass the replies
|
||||||
// TODO do the value conversion for RSSI (fixed point?)
|
if(rssiSync) { *rssiSync = (float)buff[0] / -2.0f; }
|
||||||
if(rssiSync) { *rssiSync = (float)buff[0]; }
|
if(rssiAvg) { *rssiAvg = (float)buff[1] / -2.0f; }
|
||||||
if(rssiAvg) { *rssiAvg = (float)buff[1]; }
|
|
||||||
if(rxLen) { *rxLen = buff[2]; }
|
if(rxLen) { *rxLen = buff[2]; }
|
||||||
if(stat) { *stat = buff[3]; }
|
if(stat) { *stat = buff[3]; }
|
||||||
|
|
||||||
|
@ -1334,7 +1731,7 @@ int16_t LR11x0::setGfskSyncWord(uint8_t* sync) {
|
||||||
if(!sync) {
|
if(!sync) {
|
||||||
return(RADIOLIB_ERR_MEMORY_ALLOCATION_FAILED);
|
return(RADIOLIB_ERR_MEMORY_ALLOCATION_FAILED);
|
||||||
}
|
}
|
||||||
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_SET_GFSK_SYNC_WORD, false, sync, RADIOLIB_LR11X0_GFSK_SYNC_WORD_LEN));
|
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_SET_GFSK_SYNC_WORD, true, sync, RADIOLIB_LR11X0_GFSK_SYNC_WORD_LEN));
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t LR11x0::setLoRaPublicNetwork(bool pub) {
|
int16_t LR11x0::setLoRaPublicNetwork(bool pub) {
|
||||||
|
|
|
@ -752,8 +752,121 @@ class LR11x0: public PhysicalLayer {
|
||||||
int16_t setSyncWord(uint8_t syncWord);
|
int16_t setSyncWord(uint8_t syncWord);
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\brief Sets preamble length for LoRa or FSK modem. Allowed values range from 1 to 65535.
|
\brief Sets GFSK bit rate. Allowed values range from 0.6 to 300.0 kbps.
|
||||||
\param preambleLength Preamble length to be set in symbols (LoRa) or bits (FSK).
|
\param br FSK bit rate to be set in kbps.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setBitRate(float br);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets GFSK frequency deviation. Allowed values range from 0.0 to 200.0 kHz.
|
||||||
|
\param freqDev GFSK frequency deviation to be set in kHz.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setFrequencyDeviation(float freqDev) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets GFSK receiver bandwidth. Allowed values are 4.8, 5.8, 7.3, 9.7, 11.7, 14.6, 19.5,
|
||||||
|
23.4, 29.3, 39.0, 46.9, 58.6, 78.2, 93.8, 117.3, 156.2, 187.2, 234.3, 312.0, 373.6 and 467.0 kHz.
|
||||||
|
\param rxBw GFSK receiver bandwidth to be set in kHz.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setRxBandwidth(float rxBw);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets GFSK sync word in the form of array of up to 8 bytes.
|
||||||
|
\param syncWord GFSK sync word to be set.
|
||||||
|
\param len GFSK sync word length in bytes.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setSyncWord(uint8_t* syncWord, size_t len) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets GFSK sync word in the form of array of up to 8 bytes.
|
||||||
|
\param syncWord GFSK sync word to be set.
|
||||||
|
\param bitsLen GFSK sync word length in bits. If length is not divisible by 8,
|
||||||
|
least significant bits of syncWord will be ignored.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setSyncBits(uint8_t *syncWord, uint8_t bitsLen);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets node address. Calling this method will also enable address filtering for node address only.
|
||||||
|
\param nodeAddr Node address to be set.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setNodeAddress(uint8_t nodeAddr);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets broadcast address. Calling this method will also enable address
|
||||||
|
filtering for node and broadcast address.
|
||||||
|
\param broadAddr Node address to be set.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setBroadcastAddress(uint8_t broadAddr);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Disables address filtering. Calling this method will also erase previously set addresses.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t disableAddressFiltering();
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets time-bandwidth product of Gaussian filter applied for shaping.
|
||||||
|
Allowed values are RADIOLIB_SHAPING_0_3, RADIOLIB_SHAPING_0_5, RADIOLIB_SHAPING_0_7 or RADIOLIB_SHAPING_1_0.
|
||||||
|
Set to RADIOLIB_SHAPING_NONE to disable data shaping.
|
||||||
|
\param sh Time-bandwidth product of Gaussian filter to be set.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setDataShaping(uint8_t sh) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets transmission encoding. Available in GFSK mode only. Serves only as alias for PhysicalLayer compatibility.
|
||||||
|
\param encoding Encoding to be used. Set to 0 for NRZ, and 2 for whitening.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setEncoding(uint8_t encoding) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Set modem in fixed packet length mode. Available in GFSK mode only.
|
||||||
|
\param len Packet length.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t fixedPacketLengthMode(uint8_t len = RADIOLIB_LR11X0_MAX_PACKET_LENGTH);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Set modem in variable packet length mode. Available in GFSK mode only.
|
||||||
|
\param maxLen Maximum packet length.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t variablePacketLengthMode(uint8_t maxLen = RADIOLIB_LR11X0_MAX_PACKET_LENGTH);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets GFSK whitening parameters.
|
||||||
|
\param enabled True = Whitening enabled
|
||||||
|
\param initial Initial value used for the whitening LFSR in GFSK mode.
|
||||||
|
By default set to 0x01FF for compatibility with SX127x and LoRaWAN.
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setWhitening(bool enabled, uint16_t initial = 0x01FF);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Set data.
|
||||||
|
\param dr Data rate struct. Interpretation depends on currently active modem (GFSK or LoRa).
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t setDataRate(DataRate_t dr) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Check the data rate can be configured by this module.
|
||||||
|
\param dr Data rate struct. Interpretation depends on currently active modem (GFSK or LoRa).
|
||||||
|
\returns \ref status_codes
|
||||||
|
*/
|
||||||
|
int16_t checkDataRate(DataRate_t dr) override;
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sets preamble length for LoRa or GFSK modem. Allowed values range from 1 to 65535.
|
||||||
|
\param preambleLength Preamble length to be set in symbols (LoRa) or bits (GFSK).
|
||||||
\returns \ref status_codes
|
\returns \ref status_codes
|
||||||
*/
|
*/
|
||||||
int16_t setPreambleLength(size_t preambleLength) override;
|
int16_t setPreambleLength(size_t preambleLength) override;
|
||||||
|
@ -771,12 +884,12 @@ class LR11x0: public PhysicalLayer {
|
||||||
/*!
|
/*!
|
||||||
\brief Sets CRC configuration.
|
\brief Sets CRC configuration.
|
||||||
\param len CRC length in bytes, Allowed values are 1 or 2, set to 0 to disable CRC.
|
\param len CRC length in bytes, Allowed values are 1 or 2, set to 0 to disable CRC.
|
||||||
\param initial Initial CRC value. FSK only. Defaults to 0x1D0F (CCIT CRC).
|
\param initial Initial CRC value. GFSK only. Defaults to 0x1D0F (CCIT CRC).
|
||||||
\param polynomial Polynomial for CRC calculation. FSK only. Defaults to 0x1021 (CCIT CRC).
|
\param polynomial Polynomial for CRC calculation. GFSK only. Defaults to 0x1021 (CCIT CRC).
|
||||||
\param inverted Invert CRC bytes. FSK only. Defaults to true (CCIT CRC).
|
\param inverted Invert CRC bytes. GFSK only. Defaults to true (CCIT CRC).
|
||||||
\returns \ref status_codes
|
\returns \ref status_codes
|
||||||
*/
|
*/
|
||||||
int16_t setCRC(uint8_t len, uint16_t initial = 0x1D0F, uint16_t polynomial = 0x1021, bool inverted = true);
|
int16_t setCRC(uint8_t len, uint32_t initial = 0x00001D0FUL, uint32_t polynomial = 0x00001021UL, bool inverted = true);
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\brief Enable/disable inversion of the I and Q signals
|
\brief Enable/disable inversion of the I and Q signals
|
||||||
|
@ -995,9 +1108,8 @@ class LR11x0: public PhysicalLayer {
|
||||||
bool invertIQEnabled = false;
|
bool invertIQEnabled = false;
|
||||||
|
|
||||||
// cached GFSK parameters
|
// cached GFSK parameters
|
||||||
float bitRateKbps = 0;
|
uint32_t bitRate = 0, frequencyDev = 0;
|
||||||
uint8_t bitRate = 0;
|
uint8_t preambleDetLength = 0, rxBandwidth = 0, pulseShape = 0, crcTypeGFSK = 0, syncWordLength = 0, addrComp = 0, whitening = 0, packetType = 0, node = 0;
|
||||||
uint8_t preambleDetLength = 0, rxBandwidth = 0, pulseShape = 0, crcTypeGFSK = 0, syncWordLength = 0, addrComp = 0, whitening = 0, packetType = 0;
|
|
||||||
uint16_t preambleLengthGFSK = 0;
|
uint16_t preambleLengthGFSK = 0;
|
||||||
|
|
||||||
float dataRateMeasured = 0;
|
float dataRateMeasured = 0;
|
||||||
|
@ -1006,6 +1118,7 @@ class LR11x0: public PhysicalLayer {
|
||||||
static int16_t SPIcheckStatus(Module* mod);
|
static int16_t SPIcheckStatus(Module* mod);
|
||||||
bool findChip(uint8_t ver);
|
bool findChip(uint8_t ver);
|
||||||
int16_t config(uint8_t modem);
|
int16_t config(uint8_t modem);
|
||||||
|
int16_t setPacketMode(uint8_t mode, uint8_t len);
|
||||||
|
|
||||||
// common methods to avoid some copy-paste
|
// common methods to avoid some copy-paste
|
||||||
int16_t bleBeaconCommon(uint16_t cmd, uint8_t chan, uint8_t* payload, size_t len);
|
int16_t bleBeaconCommon(uint16_t cmd, uint8_t chan, uint8_t* payload, size_t len);
|
||||||
|
|
Loading…
Add table
Reference in a new issue