RadioLib update to v7.1.2
This commit is contained in:
parent
f2d3d995cb
commit
24815c6cdc
93 changed files with 1143 additions and 1305 deletions
|
|
@ -7,8 +7,8 @@ assignees: ''
|
|||
|
||||
---
|
||||
|
||||
**IMPORTANT: Check the wiki**
|
||||
Before submitting new issue, please check the [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and the [API documentation](https://jgromes.github.io/RadioLib/). You might find a solution to your issue there.
|
||||
**IMPORTANT: Check the docs**
|
||||
Before submitting new issue, please check the [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and the [API documentation](https://jgromes.github.io/RadioLib/). If you are seeing an error code, we have [online status code decoder](https://radiolib-org.github.io/status_decoder/decode.html).
|
||||
|
||||
**Describe the bug**
|
||||
A clear and concise description of what the bug is. When applicable, please include [debug mode output](https://github.com/jgromes/RadioLib/wiki/Debug-mode) **using the appropriate debug mode**.
|
||||
|
|
|
|||
|
|
@ -7,8 +7,8 @@ assignees: ''
|
|||
|
||||
---
|
||||
|
||||
**IMPORTANT: Check the wiki**
|
||||
Before submitting new issue, please check the [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and the [API documentation](https://jgromes.github.io/RadioLib/). You might find a solution to your issue there.
|
||||
**IMPORTANT: Check the docs**
|
||||
Before submitting new issue, please check the [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and the [API documentation](https://jgromes.github.io/RadioLib/). If you are seeing an error code, we have [online status code decoder](https://radiolib-org.github.io/status_decoder/decode.html).
|
||||
|
||||
**Is your feature request related to a problem? Please describe.**
|
||||
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ assignees: ''
|
|||
|
||||
**IMPORTANT: Before submitting an issue, please check the following:**
|
||||
1. **Read [CONTRIBUTING.md](https://github.com/jgromes/RadioLib/blob/master/CONTRIBUTING.md)!** Issues that do not follow this document will be closed/locked/deleted/ignored.
|
||||
2. RadioLib has a [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and an extensive [API documentation](https://jgromes.github.io/RadioLib/). You might find a solution to your issue there.
|
||||
2. RadioLib has a [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and an extensive [API documentation](https://jgromes.github.io/RadioLib/). If you are seeing an error code, we have [online status code decoder](https://radiolib-org.github.io/status_decoder/decode.html).
|
||||
3. Make sure you're using the latest release of the library! Releases can be found [here](https://github.com/jgromes/RadioLib/releases).
|
||||
4. Use [Arduino forums](https://forum.arduino.cc/) to ask generic questions about wireless modules, wiring, usage, etc. Only create issues for problems specific to RadioLib!
|
||||
5. Error codes, their meaning and how to fix them can be found on [this page](https://jgromes.github.io/RadioLib/group__status__codes.html).
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ assignees: ''
|
|||
|
||||
**IMPORTANT: Before submitting an issue, please check the following:**
|
||||
1. **Read [CONTRIBUTING.md](https://github.com/jgromes/RadioLib/blob/master/CONTRIBUTING.md)!** Issues that do not follow this document will be closed/locked/deleted/ignored.
|
||||
2. RadioLib has a [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and an extensive [API documentation](https://jgromes.github.io/RadioLib/). You might find a solution to your issue there.
|
||||
2. RadioLib has a [Troubleshooting Guide](https://github.com/jgromes/RadioLib/wiki/Troubleshooting-Guide) Wiki page and an extensive [API documentation](https://jgromes.github.io/RadioLib/). If you are seeing an error code, we have [online status code decoder](https://radiolib-org.github.io/status_decoder/decode.html).
|
||||
3. Make sure you're using the latest release of the library! Releases can be found [here](https://github.com/jgromes/RadioLib/releases).
|
||||
4. Use [Arduino forums](https://forum.arduino.cc/) to ask generic questions about wireless modules, wiring, usage, etc. Only create issues for problems specific to RadioLib!
|
||||
5. Error codes, their meaning and how to fix them can be found on [this page](https://jgromes.github.io/RadioLib/group__status__codes.html).
|
||||
|
|
|
|||
84
lib/RadioLib/.github/workflows/main.yml
vendored
84
lib/RadioLib/.github/workflows/main.yml
vendored
|
|
@ -36,6 +36,7 @@ on:
|
|||
- MegaCore:avr:1281
|
||||
- teensy:avr:teensy41
|
||||
- arduino:renesas_uno:minima
|
||||
- SiliconLabs:silabs:xg24explorerkit
|
||||
|
||||
jobs:
|
||||
build:
|
||||
|
|
@ -89,7 +90,7 @@ jobs:
|
|||
- id: STMicroelectronics:stm32:Nucleo_64:pnum=NUCLEO_WL55JC1
|
||||
run: |
|
||||
# Do *not* skip STM32WL examples
|
||||
echo "skip-pattern='LR11x0_Firmware_Update'" >> $GITHUB_OUTPUT
|
||||
echo "skip-pattern=(LR11x0_Firmware_Update)" >> $GITHUB_OUTPUT
|
||||
echo "index-url=--additional-urls https://raw.githubusercontent.com/stm32duino/BoardManagerFiles/main/package_stmicroelectronics_index.json" >> $GITHUB_OUTPUT
|
||||
- id: stm32duino:STM32F1:mapleMini
|
||||
run: |
|
||||
|
|
@ -118,6 +119,9 @@ jobs:
|
|||
- id: arduino:renesas_uno:minima
|
||||
run: |
|
||||
echo "skip-pattern=(STM32WL|LoRaWAN|LR11x0_Firmware_Update)" >> $GITHUB_OUTPUT
|
||||
- id: SiliconLabs:silabs:xg24explorerkit
|
||||
run: |
|
||||
echo "index-url=--additional-urls https://siliconlabs.github.io/arduino/package_arduinosilabs_index.json" >> $GITHUB_OUTPUT
|
||||
|
||||
runs-on: ubuntu-latest
|
||||
name: ${{ matrix.id }}
|
||||
|
|
@ -176,28 +180,62 @@ jobs:
|
|||
if: ${{ env.run-build == 'true' }}
|
||||
run:
|
||||
|
|
||||
for example in $(find $PWD/examples -name '*.ino' | sort); do
|
||||
# check whether to skip this sketch
|
||||
if [ ! -z '${{ steps.prep.outputs.skip-pattern }}' ] && [[ ${example} =~ ${{ steps.prep.outputs.skip-pattern }} ]]; then
|
||||
# skip sketch
|
||||
echo -e "\n\033[1;33mSkipped ${example##*/} (matched with ${{ steps.prep.outputs.skip-pattern }})\033[0m";
|
||||
else
|
||||
# apply special flags for LoRaWAN
|
||||
if [[ ${example} =~ "LoRaWAN" ]]; then
|
||||
flags="-DRADIOLIB_LORAWAN_DEV_ADDR=0 -DRADIOLIB_LORAWAN_FNWKSINT_KEY=0 -DRADIOLIB_LORAWAN_SNWKSINT_KEY=0 -DRADIOLIB_LORAWAN_NWKSENC_KEY=0 -DRADIOLIB_LORAWAN_APPS_KEY=0 -DRADIOLIB_LORAWAN_APP_KEY=0 -DRADIOLIB_LORAWAN_NWK_KEY=0 -DRADIOLIB_LORAWAN_DEV_EUI=0 -DARDUINO_TTGO_LORA32_V1"
|
||||
fi
|
||||
cd $PWD/extras/test/ci
|
||||
./build_examples.sh ${{ matrix.id }} "${{ steps.prep.outputs.skip-pattern }}" ${{ steps.prep.outputs.options }}
|
||||
|
||||
- name: Parse sizes
|
||||
if: ${{ env.run-build == 'true' }}
|
||||
run:
|
||||
|
|
||||
cd $PWD/extras/test/ci
|
||||
./parse_size.sh ${{ matrix.id }}
|
||||
|
||||
- name: Extract short commit hash
|
||||
id: short-hash
|
||||
run: echo "::set-output name=short_sha::$(git rev-parse --short HEAD)"
|
||||
|
||||
- name: Upload size report as artifact
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: size-file-${{ steps.split.outputs._0 }}-${{ steps.split.outputs._1 }}-${{ steps.split.outputs._2 }}
|
||||
path: extras/test/ci/size_${{ steps.short-hash.outputs.short_sha }}_${{ steps.split.outputs._0 }}-${{ steps.split.outputs._1 }}-${{ steps.split.outputs._2 }}.csv
|
||||
|
||||
# build sketch
|
||||
echo -e "\n\033[1;33mBuilding ${example##*/} ... \033[0m";
|
||||
arduino-cli compile --libraries /home/runner/work/RadioLib --fqbn ${{ matrix.id }}${{ steps.prep.outputs.options }} --build-property compiler.cpp.extra_flags="$flags" $example --warnings=${{ steps.prep.outputs.warnings }}
|
||||
if [ $? -ne 0 ]; then
|
||||
echo -e "\033[1;31m${example##*/} build FAILED\033[0m\n";
|
||||
exit 1;
|
||||
else
|
||||
echo -e "\033[1;32m${example##*/} build PASSED\033[0m\n";
|
||||
fi
|
||||
fi
|
||||
done
|
||||
metrics:
|
||||
runs-on: ubuntu-latest
|
||||
needs: build
|
||||
steps:
|
||||
- name: Set up SSH
|
||||
run: |
|
||||
mkdir -p ~/.ssh
|
||||
echo "${{ secrets.ACTIONS_METRICS_DEPLOY_KEY }}" > ~/.ssh/id_rsa
|
||||
chmod 600 ~/.ssh/id_rsa
|
||||
ssh-keyscan github.com >> ~/.ssh/known_hosts
|
||||
|
||||
- name: Clone artifact repo
|
||||
run:
|
||||
|
|
||||
cd $PWD/..
|
||||
git clone git@github.com:radiolib-org/artifacts.git
|
||||
cd artifacts
|
||||
git config --global user.name "${{ github.actor }}"
|
||||
git config --global user.email "${{ github.actor }}@users.noreply.github.com"
|
||||
|
||||
- name: Download size artifacts
|
||||
uses: actions/download-artifact@v3
|
||||
with:
|
||||
path: aggregated-sizes
|
||||
|
||||
- name: Push size files
|
||||
run:
|
||||
|
|
||||
ls -R aggregated-sizes
|
||||
mkdir -p $PWD/../artifacts/radiolib-ci/l0
|
||||
cp aggregated-sizes/*/size_*.csv $PWD/../artifacts/radiolib-ci/l0/.
|
||||
cd $PWD/../artifacts/radiolib-ci
|
||||
git add .
|
||||
COMMIT_URL="https://github.com/jgromes/RadioLib/commit/$GITHUB_SHA"
|
||||
git commit -m "Push artifacts from $COMMIT_URL"
|
||||
git push origin main
|
||||
|
||||
esp-build:
|
||||
runs-on: ubuntu-latest
|
||||
|
|
@ -247,7 +285,7 @@ jobs:
|
|||
run: |
|
||||
cd $PWD/examples/NonArduino/Tock
|
||||
git clone https://github.com/tock/libtock-c.git
|
||||
cd libtock-c; git checkout dbee65a56d74b4bad166317f199e80b959f7c82c; cd ../
|
||||
cd libtock-c; git checkout c0202f9ab78da4a6e95f136cf5250701e3778f63; cd ../
|
||||
LIBTOCK_C_DIRECTORY="$(pwd)/libtock-c" ./build.sh
|
||||
|
||||
rpi-build:
|
||||
|
|
|
|||
37
lib/RadioLib/.github/workflows/release.yml
vendored
Normal file
37
lib/RadioLib/.github/workflows/release.yml
vendored
Normal file
|
|
@ -0,0 +1,37 @@
|
|||
name: "Release"
|
||||
|
||||
on: workflow_dispatch
|
||||
|
||||
jobs:
|
||||
release:
|
||||
name: Release RadioLib update
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- name: Checkout repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Checkout latest tag
|
||||
run: git checkout $(git describe --tags $(git rev-list --tags --max-count=1))
|
||||
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v4
|
||||
with:
|
||||
python-version: '3.9'
|
||||
|
||||
- name: Install PlatformIO and ESP-IDF
|
||||
run: |
|
||||
pip install --upgrade platformio
|
||||
pip install --upgrade idf-component-manager
|
||||
|
||||
- name: PlatformIO publish
|
||||
env:
|
||||
PLATFORMIO_AUTH_TOKEN: ${{ secrets.PLATFORMIO_AUTH_TOKEN }}
|
||||
run: pio pkg publish --no-interactive
|
||||
|
||||
- name: ESP-IDF publish
|
||||
env:
|
||||
IDF_COMPONENT_API_TOKEN: ${{ secrets.IDF_COMPONENT_API_TOKEN }}
|
||||
run: compote component upload --name RadioLib --namespace jgromes
|
||||
27
lib/RadioLib/.github/workflows/unit-test.yml
vendored
Normal file
27
lib/RadioLib/.github/workflows/unit-test.yml
vendored
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
name: "Unit test"
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [master]
|
||||
pull_request:
|
||||
branches: [master]
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
unit-test:
|
||||
name: Build and run unit test
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- name: Checkout repository
|
||||
uses: actions/checkout@v4
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
sudo apt-get update
|
||||
sudo apt-get install -y libboost-all-dev libfmt-dev
|
||||
|
||||
- name: Run unit test
|
||||
run: |
|
||||
cd extras/test/unit
|
||||
./test.sh
|
||||
|
|
@ -4,8 +4,6 @@
|
|||
|
||||
## Universal wireless communication library for embedded devices
|
||||
|
||||
## See the [Wiki](https://github.com/jgromes/RadioLib/wiki) and [FAQ](https://github.com/jgromes/RadioLib/wiki/Frequently-Asked-Questions) for further information. See the [GitHub Pages](https://jgromes.github.io/RadioLib) for detailed and up-to-date API reference.
|
||||
|
||||
RadioLib allows its users to integrate all sorts of different wireless communication modules, protocols and even digital modes into a single consistent system.
|
||||
Want to add a Bluetooth interface to your LoRa network? Sure thing! Do you just want to go really old-school and play around with radio teletype, slow-scan TV, or even Hellschreiber using nothing but a cheap radio module? Why not!
|
||||
|
||||
|
|
@ -13,6 +11,13 @@ RadioLib natively supports Arduino, but can run in non-Arduino environments as w
|
|||
|
||||
RadioLib was originally created as a driver for [__RadioShield__](https://github.com/jgromes/RadioShield), but it can be used to control as many different wireless modules as you like - or at least as many as your microcontroller can handle!
|
||||
|
||||
### Quick links:
|
||||
* [__Wiki__](https://github.com/jgromes/RadioLib/wiki) - contains useful general information on using this library
|
||||
* [__FAQ__](https://github.com/jgromes/RadioLib/wiki/Frequently-Asked-Questions) - frequently asked questions, and answers
|
||||
* [__API Reference__](https://jgromes.github.io/RadioLib) - full API reference, automatically generated from the source code
|
||||
* [__Status Code Decoder__](https://radiolib-org.github.io/status_decoder/decode.html) - decoder for status codes returned by RadioLib methods
|
||||
* [__Debug Log Decoder__](https://radiolib-org.github.io/debug_decoder/decode.html) - decoder for RadioLib SPI debug logs
|
||||
|
||||
### Supported modules:
|
||||
* __CC1101__ FSK radio module
|
||||
* __LLCC68__ LoRa module
|
||||
|
|
@ -43,7 +48,7 @@ SX127x, RFM9x, SX126x, RF69, SX1231, CC1101, nRF24L01, RFM2x, Si443x, LR11x0 and
|
|||
SX127x, RFM9x, SX126x, RF69, SX1231, CC1101, nRF24L01, RFM2x, Si443x and SX128x
|
||||
* [__POCSAG__](https://www.sigidwiki.com/wiki/POCSAG) using 2-FSK for modules:
|
||||
SX127x, RFM9x, RF69, SX1231, CC1101, nRF24L01, RFM2x and Si443x
|
||||
* [__LoRaWAN__](https://lora-alliance.org/) using LoRa for modules:
|
||||
* [__LoRaWAN__](https://lora-alliance.org/) using LoRa and FSK for modules:
|
||||
SX127x, RFM9x, SX126x, LR11x0 and SX128x
|
||||
|
||||
### Supported Arduino platforms:
|
||||
|
|
@ -89,4 +94,7 @@ SX127x, RFM9x, SX126x, LR11x0 and SX128x
|
|||
* __PJRC__
|
||||
* [__Teensy__](https://github.com/PaulStoffregen/cores) - Teensy 2.x, 3.x and 4.x boards
|
||||
|
||||
* __Silicon Labs__
|
||||
* [__EFR32__](https://github.com/SiliconLabs/arduino) - Silicon Labs xG24, xG27 and other boards
|
||||
|
||||
The list above is by no means exhaustive - RadioLib code is independent of the used platform! Compilation of all examples is tested for all platforms officially supported prior to releasing new version. In addition, RadioLib includes an internal hardware abstraction layer, which allows it to be easily ported even to non-Arduino environments.
|
||||
|
|
|
|||
|
|
@ -37,6 +37,21 @@ CC1101 radio = new Module(10, 2, RADIOLIB_NC, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -76,21 +91,6 @@ void setup() {
|
|||
// radio.readData();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -82,10 +82,10 @@ void setup() {
|
|||
void loop() {
|
||||
Serial.print(F("[CC1101] Transmitting packet ... "));
|
||||
|
||||
// you can transmit C-string or Arduino string up to 63 characters long
|
||||
// you can transmit C-string or Arduino string up to 64 characters long
|
||||
int state = radio.transmit("Hello World!");
|
||||
|
||||
// you can also transmit byte array up to 63 bytes long
|
||||
// you can also transmit byte array up to 64 bytes long
|
||||
/*
|
||||
byte byteArr[] = {0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF};
|
||||
int state = radio.transmit(byteArr, 8);
|
||||
|
|
|
|||
|
|
@ -57,11 +57,11 @@ int count = 0;
|
|||
void loop() {
|
||||
Serial.print(F("[CC1101] Transmitting packet ... "));
|
||||
|
||||
// you can transmit C-string or Arduino string up to 63 characters long
|
||||
// you can transmit C-string or Arduino string up to 64 characters long
|
||||
String str = "Hello World! #" + String(count++);
|
||||
int state = radio.transmit(str);
|
||||
|
||||
// you can also transmit byte array up to 63 bytes long
|
||||
// you can also transmit byte array up to 64 bytes long
|
||||
/*
|
||||
byte byteArr[] = {0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF};
|
||||
int state = radio.transmit(byteArr, 8);
|
||||
|
|
|
|||
|
|
@ -36,6 +36,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -69,21 +84,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
@ -119,11 +119,11 @@ void loop() {
|
|||
Serial.print(F("[CC1101] Sending another packet ... "));
|
||||
|
||||
// you can transmit C-string or Arduino string up to
|
||||
// 256 characters long
|
||||
// 64 characters long
|
||||
String str = "Hello World! #" + String(count++);
|
||||
transmissionState = radio.startTransmit(str);
|
||||
|
||||
// you can also transmit byte array up to 256 bytes long
|
||||
// you can also transmit byte array up to 64 bytes long
|
||||
/*
|
||||
byte byteArr[] = {0x01, 0x23, 0x45, 0x67,
|
||||
0x89, 0xAB, 0xCD, 0xEF};
|
||||
|
|
|
|||
|
|
@ -57,6 +57,21 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
END_OF_MODE_TABLE,
|
||||
};
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -89,21 +104,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -62,7 +62,8 @@ void setup() {
|
|||
3, // header count
|
||||
0x13A); // hopping sequence seed
|
||||
state = radio.setOutputPower(10.0);
|
||||
state = radio.setSyncWord(0x12345678);
|
||||
uint8_t syncWord[] = {0x01, 0x23, 0x45, 0x67};
|
||||
state = radio.setSyncWord(syncWord, 4);
|
||||
if (state != RADIOLIB_ERR_NONE) {
|
||||
Serial.print(F("Unable to set configuration, code "));
|
||||
Serial.println(state);
|
||||
|
|
|
|||
|
|
@ -63,6 +63,21 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
END_OF_MODE_TABLE,
|
||||
};
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -105,21 +120,6 @@ void setup() {
|
|||
// radio.scanChannel();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -62,6 +62,21 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -98,21 +113,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -60,6 +60,20 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
END_OF_MODE_TABLE,
|
||||
};
|
||||
|
||||
// flag to indicate that a scan was completed
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a scan is completed
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// scan is complete, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -92,20 +106,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a scan was completed
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a scan is completed
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// scan is complete, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -68,7 +68,7 @@ void setup() {
|
|||
// Manages uplink intervals to the TTN Fair Use Policy
|
||||
node.setDutyCycle(true, 1250);
|
||||
|
||||
// Enable the dwell time limits - 400ms is the limit for the US
|
||||
// Update dwell time limits - 400ms is the limit for the US
|
||||
node.setDwellTime(true, 400);
|
||||
|
||||
Serial.println(F("Ready!\n"));
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ You are making your own device using a third party LoRaWAN stack so there will n
|
|||
|
||||
Choose the Frequency plan appropriate for your region. Consider that almost all countries have laws relating to what frequencies you use so don't get creative. For Europe please use the recommended option. For other regions use the entry marked 'used by TTN'.
|
||||
|
||||
Choose LoRaWAN 1.1.0 - the last one in the list - the latest specfication. RadioLib uses RP001 Regional Parameters 1.1 revision A.
|
||||
Choose LoRaWAN 1.1.0 - the last one in the list - the latest specfication. RadioLib uses RP001 Regional Parameters 1.1 revision B.
|
||||
|
||||
At this point you will be asked for your JoinEUI. As this is a DIY device and we are using RadioLib, you can use all zero's as recommended by The LoRa Alliance TR007 Technical Recommendations document. Once you've put in all zeros and clicked confirm you will be asked for a DevEUI, AppKey and NwkKey. It is preferable to have the console generate them so they are properly formatted.
|
||||
|
||||
|
|
|
|||
|
|
@ -6,17 +6,17 @@ RadioLib LoRaWAN examples.
|
|||
* [LoRaWAN_ABP](https://github.com/jgromes/RadioLib/tree/master/examples/LoRaWAN/LoRaWAN_ABP): if you wish to use ABP instead of OTAA (but why?), this example shows how you can do this using RadioLib.
|
||||
|
||||
## LoRaWAN versions & regional parameters
|
||||
RadioLib implements both LoRaWAN v1.1 and v1.0.4. Confusingly, v1.0.4 is newer than v1.1, but v1.1 includes more security checks and as such **LoRaWAN v1.1 is preferred**.
|
||||
The catch is in the Regional Parameters: as v1.0.4 is newer, it is more up to date regarding local laws & regulations. Therefore, RadioLib implements 1.0.4 as baseline and 1.1 as fallback, but **Regional Parameters v1.0.4 is preferred**.
|
||||
_Note: the CN500 band is implemented as specified in RP v1.1, as the RP v1.0.4 version is much too complex._
|
||||
RadioLib implements both LoRaWAN Specification 1.1 and 1.0.4. Confusingly, 1.0.4 is newer than 1.1, but 1.1 includes more security checks and as such **LoRaWAN 1.1 is preferred**.
|
||||
The catch is in the Regional Parameters: as RP002 1.0.4 is newer than RP001 1.1, it is more up to date regarding local laws & regulations. Therefore, RadioLib implements 1.0.4 as baseline and 1.1 (revision B) as fallback, and as such **RP002 Regional Parameters 1.0.4 is preferred**.
|
||||
_Note: the CN500 band is implemented as specified in RP001 1.1 revision B, as the RP002 1.0.4 version is much too complex._
|
||||
|
||||
To activate a LoRaWAN v1.1 session, supply all the required keys:
|
||||
To activate a LoRaWAN 1.1 session, supply all the required keys:
|
||||
```cpp
|
||||
node.beginOTAA(joinEUI, devEUI, nwkKey, appKey);
|
||||
node.beginABP(devAddr, fNwkSIntKey, sNwkSIntKey, nwkSEncKey, appSKey);
|
||||
```
|
||||
|
||||
To activate a LoRaWAN v1.0.4 session, set the keys that are not available to `NULL`:
|
||||
To activate a LoRaWAN 1.0.4 session, set the keys that are not available to `NULL`:
|
||||
```cpp
|
||||
node.beginOTAA(joinEUI, devEUI, NULL, appKey);
|
||||
node.beginABP(devAddr, NULL, NULL, nwkSEncKey, appSKey);
|
||||
|
|
@ -26,9 +26,9 @@ The device doesn't need to know the Regional Parameters version - that is of imp
|
|||
|
||||
## LoRaWAN persistence
|
||||
> [!WARNING]
|
||||
> These examples do not actually comply with LoRaWAN v1.0.4/v1.1: for that, persistent storage is necessary. As the implementation of persistent storage differs between different platforms, these are not given here, but in a separate repository, see below:
|
||||
> These examples do not actually comply with LoRaWAN 1.0.4/1.1: for that, persistent storage is necessary. As the implementation of persistent storage differs between different platforms, these are not given here, but in a separate repository, see below:
|
||||
|
||||
In [this repository](https://github.com/radiolib-org/radiolib-persistence), examples are provided that do comply with the required persistence of certain parameters for LoRaWAN v1.1. Examples are (or will become) available for some of the most popular platforms. **These examples assume you have successfully used the Starter sketch and understood (most of) the accompanying notes!**
|
||||
In [this repository](https://github.com/radiolib-org/radiolib-persistence), examples are provided that do comply with the required persistence of certain parameters for LoRaWAN 1.1. Examples are (or will become) available for some of the most popular platforms. **These examples assume you have successfully used the Starter sketch and understood (most of) the accompanying notes!**
|
||||
Currently, examples are available for the following platforms:
|
||||
|
||||
* [LoRaWAN for ESP32](https://github.com/radiolib-org/radiolib-persistence/tree/main/examples/LoRaWAN_ESP32)
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@
|
|||
// this example only works on ESP32 and is unlikely to work on ESP32S2/S3 etc.
|
||||
// if you need high portability, you should probably use Arduino anyway ...
|
||||
#if CONFIG_IDF_TARGET_ESP32 == 0
|
||||
#error Target is not ESP32!
|
||||
#error This example HAL only supports ESP32 targets. Support for ESP32S2/S3 etc. can be added by adjusting this file to user needs.
|
||||
#endif
|
||||
|
||||
// include all the dependencies
|
||||
|
|
@ -17,7 +17,7 @@
|
|||
#include <RadioLib.h>
|
||||
|
||||
// include the hardware abstraction layer
|
||||
#include "hal/ESP-IDF/EspHal.h"
|
||||
#include "EspHal.h"
|
||||
|
||||
// create a new instance of the HAL class
|
||||
EspHal* hal = new EspHal(5, 19, 27);
|
||||
|
|
|
|||
|
|
@ -50,7 +50,21 @@ add_executable(${PROJECT_NAME} main.cpp)
|
|||
# The build system for libtock-c is a bit odd and the version of libraries
|
||||
# built changes based on compiler version.
|
||||
if (RISCV_BUILD)
|
||||
if(EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-13.2.0")
|
||||
if(EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0")
|
||||
target_link_libraries(${PROJECT_NAME} PUBLIC
|
||||
RadioLib
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock/build/rv32imc/libtock.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock-sync/build/rv32imc/libtocksync.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0/riscv/lib/gcc/riscv64-unknown-elf/14.1.0/rv32i/ilp32/libgcc.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0/riscv/riscv64-unknown-elf/lib/rv32i/ilp32/libstdc++.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-newlib-4.4.0.20231231/riscv/riscv64-unknown-elf/lib/rv32i/ilp32/libc.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-newlib-4.4.0.20231231/riscv/riscv64-unknown-elf/lib/rv32i/ilp32/libm.a
|
||||
)
|
||||
|
||||
target_include_directories(RadioLib AFTER PUBLIC
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-newlib-4.3.0.20230120/riscv/riscv64-unknown-elf/include/
|
||||
)
|
||||
elseif(EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-13.2.0")
|
||||
target_link_libraries(${PROJECT_NAME} PUBLIC
|
||||
RadioLib
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock/build/rv32imc/libtock.a
|
||||
|
|
@ -80,7 +94,17 @@ if (RISCV_BUILD)
|
|||
)
|
||||
endif()
|
||||
else()
|
||||
if(EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-13.2.0")
|
||||
if (EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0")
|
||||
target_link_libraries(${PROJECT_NAME} PUBLIC
|
||||
RadioLib
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock/build/cortex-m4/libtock.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock-sync/build/cortex-m4/libtocksync.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0/arm/lib/gcc/arm-none-eabi/14.1.0/libgcc.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-14.1.0/arm/arm-none-eabi/lib/libstdc++.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-newlib-4.4.0.20231231/arm/arm-none-eabi/lib/libc.a
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-newlib-4.4.0.20231231/arm/arm-none-eabi/lib/libm.a
|
||||
)
|
||||
elseif(EXISTS "$ENV{LIBTOCK_C_DIRECTORY}/lib/libtock-libc++-13.2.0")
|
||||
target_link_libraries(${PROJECT_NAME} PUBLIC
|
||||
RadioLib
|
||||
$ENV{LIBTOCK_C_DIRECTORY}/libtock/build/cortex-m4/libtock.a
|
||||
|
|
|
|||
|
|
@ -23,7 +23,7 @@ The RadioLib example can be built with:
|
|||
$ git clone https://github.com/jgromes/RadioLib.git
|
||||
$ cd RadioLib/examples/NonArduino/Tock/
|
||||
$ git clone https://github.com/tock/libtock-c.git
|
||||
$ cd libtock-c; git checkout dbee65a56d74b4bad166317f199e80b959f7c82c; cd ../
|
||||
$ cd libtock-c; git checkout c0202f9ab78da4a6e95f136cf5250701e3778f63; cd ../
|
||||
$ LIBTOCK_C_DIRECTORY="$(pwd)/libtock-c" ./build.sh
|
||||
```
|
||||
|
||||
|
|
|
|||
|
|
@ -3,9 +3,9 @@ set -e
|
|||
|
||||
rm -rf ./build-*
|
||||
|
||||
cd libtock-c/examples/cxx_hello
|
||||
pushd ${LIBTOCK_C_DIRECTORY}/examples/cxx_hello
|
||||
make -j4
|
||||
cd ../../../
|
||||
popd
|
||||
|
||||
mkdir -p build-arm
|
||||
cd build-arm
|
||||
|
|
|
|||
|
|
@ -28,14 +28,14 @@
|
|||
#include <RadioLib.h>
|
||||
|
||||
// include the hardware abstraction layer
|
||||
#include "hal/Tock/libtockHal.h"
|
||||
#include "RadioLib/libtockHal.h"
|
||||
|
||||
// the entry point for the program
|
||||
int main(void) {
|
||||
printf("[SX1261] Initialising Radio ... \r\n");
|
||||
|
||||
// create a new instance of the HAL class
|
||||
TockHal* hal = new TockHal();
|
||||
TockRadioLibHal* hal = new TockRadioLibHal();
|
||||
|
||||
// now we can create the radio module
|
||||
// pinout corresponds to the SparkFun LoRa Thing Plus - expLoRaBLE
|
||||
|
|
@ -43,7 +43,7 @@ int main(void) {
|
|||
// DIO1 pin: 2
|
||||
// NRST pin: 4
|
||||
// BUSY pin: 1
|
||||
Module* tock_module = new Module(hal, RADIO_NSS, RADIO_DIO_1, RADIO_RESET, RADIO_BUSY);
|
||||
Module* tock_module = new Module(hal, RADIOLIB_RADIO_NSS, RADIOLIB_RADIO_DIO_1, RADIOLIB_RADIO_RESET, RADIOLIB_RADIO_BUSY);
|
||||
SX1262* radio = new SX1262(tock_module);
|
||||
|
||||
// Setup the radio
|
||||
|
|
|
|||
|
|
@ -29,6 +29,21 @@ RF69 radio = new Module(10, 2, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -68,21 +83,6 @@ void setup() {
|
|||
// radio.readData();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -35,6 +35,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -85,21 +100,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -33,6 +33,18 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
END_OF_MODE_TABLE,
|
||||
};
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -66,18 +78,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -43,6 +43,18 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
END_OF_MODE_TABLE,
|
||||
};
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -97,18 +109,6 @@ void setup() {
|
|||
// radio.scanChannel();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -38,6 +38,18 @@ static const Module::RfSwitchMode_t rfswitch_table[] = {
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -85,18 +97,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -33,6 +33,21 @@ SX1262 radio = new Module(10, 2, 3, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -62,21 +77,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -35,6 +35,24 @@ SX1262 radio = new Module(10, 2, 3, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// whether we are receiving, or scanning
|
||||
bool receiving = false;
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -64,23 +82,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
bool receiving = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -126,33 +126,4 @@ void loop() {
|
|||
Serial.println(F("[SX1262] Failed to receive packet, code "));
|
||||
Serial.println(state);
|
||||
}
|
||||
|
||||
// FSK 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("[SX1262] 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 "));
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
|
|
|||
|
|
@ -62,7 +62,8 @@ void setup() {
|
|||
3, // header count
|
||||
0x13A); // hopping sequence seed
|
||||
state = radio.setOutputPower(10.0);
|
||||
state = radio.setSyncWord(0x12345678);
|
||||
uint8_t syncWord[] = {0x01, 0x23, 0x45, 0x67};
|
||||
state = radio.setSyncWord(syncWord, 4);
|
||||
if (state != RADIOLIB_ERR_NONE) {
|
||||
Serial.print(F("Unable to set configuration, code "));
|
||||
Serial.println(state);
|
||||
|
|
|
|||
|
|
@ -39,6 +39,21 @@ SX1262 radio = new Module(10, 2, 3, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -78,21 +93,6 @@ void setup() {
|
|||
// radio.scanChannel();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -38,6 +38,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -71,21 +86,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -34,6 +34,36 @@ SX1278 radio = new Module(10, 2, 9, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a preamble was not detected
|
||||
volatile bool timeoutFlag = false;
|
||||
|
||||
// flag to indicate that a preamble was detected
|
||||
volatile bool detectedFlag = false;
|
||||
|
||||
// this function is called when no preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagTimeout(void) {
|
||||
// we timed out, set the flag
|
||||
timeoutFlag = true;
|
||||
}
|
||||
|
||||
// this function is called when LoRa preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagDetected(void) {
|
||||
// we got a preamble, set the flag
|
||||
detectedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
// Serial port speed must be high enough for this example
|
||||
Serial.begin(115200);
|
||||
|
|
@ -68,36 +98,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a preamble was not detected
|
||||
volatile bool timeoutFlag = false;
|
||||
|
||||
// flag to indicate that a preamble was detected
|
||||
volatile bool detectedFlag = false;
|
||||
|
||||
// this function is called when no preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagTimeout(void) {
|
||||
// we timed out, set the flag
|
||||
timeoutFlag = true;
|
||||
}
|
||||
|
||||
// this function is called when LoRa preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagDetected(void) {
|
||||
// we got a preamble, set the flag
|
||||
detectedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if we need to restart channel activity detection
|
||||
if(detectedFlag || timeoutFlag) {
|
||||
|
|
|
|||
|
|
@ -39,6 +39,39 @@ SX1278 radio = new Module(10, 2, 9, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a preamble was not detected
|
||||
volatile bool timeoutFlag = false;
|
||||
|
||||
// flag to indicate that a preamble was detected
|
||||
volatile bool detectedFlag = false;
|
||||
|
||||
// flag to indicate if we are currently receiving
|
||||
bool receiving = false;
|
||||
|
||||
// this function is called when no preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagTimeout(void) {
|
||||
// we timed out, set the flag
|
||||
timeoutFlag = true;
|
||||
}
|
||||
|
||||
// this function is called when LoRa preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagDetected(void) {
|
||||
// we got a preamble, set the flag
|
||||
detectedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
// Serial port speed must be high enough for this example
|
||||
Serial.begin(115200);
|
||||
|
|
@ -74,39 +107,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a preamble was not detected
|
||||
volatile bool timeoutFlag = false;
|
||||
|
||||
// flag to indicate that a preamble was detected
|
||||
volatile bool detectedFlag = false;
|
||||
|
||||
// flag to indicate if we are currently receiving
|
||||
bool receiving = false;
|
||||
|
||||
// this function is called when no preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagTimeout(void) {
|
||||
// we timed out, set the flag
|
||||
timeoutFlag = true;
|
||||
}
|
||||
|
||||
// this function is called when LoRa preamble
|
||||
// is detected within timeout period
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlagDetected(void) {
|
||||
// we got a preamble, set the flag
|
||||
detectedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if we need to restart channel activity detection
|
||||
if(detectedFlag || timeoutFlag) {
|
||||
|
|
|
|||
|
|
@ -32,6 +32,12 @@ const int pin = 5;
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// this function is called when a new bit is received
|
||||
void readBit(void) {
|
||||
// read the data bit
|
||||
radio.readBit(pin);
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -59,12 +65,6 @@ void setup() {
|
|||
radio.receiveDirect();
|
||||
}
|
||||
|
||||
// this function is called when a new bit is received
|
||||
void readBit(void) {
|
||||
// read the data bit
|
||||
radio.readBit(pin);
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// we expect the packet to contain the string "Hello World!",
|
||||
// a length byte and 2 CRC bytes, that's 15 bytes in total
|
||||
|
|
|
|||
|
|
@ -39,6 +39,21 @@ SX1278 radio = new Module(10, 2, 9, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -78,21 +93,6 @@ void setup() {
|
|||
// radio.scanChannel();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -38,6 +38,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -71,21 +86,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -31,6 +31,21 @@ SX1280 radio = new Module(10, 2, 3, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -60,21 +75,6 @@ void setup() {
|
|||
}
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was detected or CAD timed out
|
||||
volatile bool scanFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// something happened, set the flag
|
||||
scanFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(scanFlag) {
|
||||
|
|
|
|||
|
|
@ -39,6 +39,21 @@ SX1280 radio = new Module(10, 2, 3, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -79,21 +94,6 @@ void setup() {
|
|||
// radio.scanChannel();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -38,6 +38,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -71,21 +86,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -31,6 +31,21 @@ Si4432 radio = new Module(10, 2, 9);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -70,21 +85,6 @@ void setup() {
|
|||
// radio.readData();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -36,6 +36,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -69,21 +84,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -34,6 +34,21 @@ nRF24 radio = new Module(10, 2, 3);
|
|||
Radio radio = new RadioModule();
|
||||
*/
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -88,21 +103,6 @@ void setup() {
|
|||
// radio.readData();
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was received
|
||||
volatile bool receivedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is received by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we got a packet, set the flag
|
||||
receivedFlag = true;
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// check if the flag is set
|
||||
if(receivedFlag) {
|
||||
|
|
|
|||
|
|
@ -36,6 +36,21 @@ Radio radio = new RadioModule();
|
|||
// save transmission state between loops
|
||||
int transmissionState = RADIOLIB_ERR_NONE;
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(9600);
|
||||
|
||||
|
|
@ -84,21 +99,6 @@ void setup() {
|
|||
*/
|
||||
}
|
||||
|
||||
// flag to indicate that a packet was sent
|
||||
volatile bool transmittedFlag = false;
|
||||
|
||||
// this function is called when a complete packet
|
||||
// is transmitted by the module
|
||||
// IMPORTANT: this function MUST be 'void' type
|
||||
// and MUST NOT have any arguments!
|
||||
#if defined(ESP8266) || defined(ESP32)
|
||||
ICACHE_RAM_ATTR
|
||||
#endif
|
||||
void setFlag(void) {
|
||||
// we sent a packet, set the flag
|
||||
transmittedFlag = true;
|
||||
}
|
||||
|
||||
// counter to keep track of transmitted packets
|
||||
int count = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
version: "7.1.0"
|
||||
version: "7.1.2"
|
||||
description: "Universal wireless communication library. User-friendly library for sub-GHz radio modules (SX1278, RF69, CC1101, SX1268, and many others), as well as ham radio digital modes (RTTY, SSTV, AX.25 etc.) and other protocols (Pagers, LoRaWAN)."
|
||||
tags:
|
||||
- radio
|
||||
|
|
|
|||
|
|
@ -197,6 +197,7 @@ randomByte KEYWORD2
|
|||
getPacketLength KEYWORD2
|
||||
setFifoEmptyAction KEYWORD2
|
||||
clearFifoEmptyAction KEYWORD2
|
||||
setFifoThreshold KEYWORD2
|
||||
setFifoFullAction KEYWORD2
|
||||
clearFifoFullAction KEYWORD2
|
||||
fifoAdd KEYWORD2
|
||||
|
|
@ -221,6 +222,7 @@ setGdo2Action KEYWORD2
|
|||
clearGdo0Action KEYWORD2
|
||||
clearGdo2Action KEYWORD2
|
||||
setCrcFiltering KEYWORD2
|
||||
beginFSK4 KEYWORD2
|
||||
|
||||
# SX126x-specific
|
||||
setTCXO KEYWORD2
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
{
|
||||
"name": "RadioLib",
|
||||
"version": "7.1.0",
|
||||
"version": "7.1.2",
|
||||
"description": "Universal wireless communication library. User-friendly library for sub-GHz radio modules (SX1278, RF69, CC1101, SX1268, and many others), as well as ham radio digital modes (RTTY, SSTV, AX.25 etc.) and other protocols (Pagers, LoRaWAN).",
|
||||
"keywords": "radio, communication, morse, cc1101, aprs, sx1276, sx1278, sx1272, rtty, ax25, afsk, nrf24, rf69, sx1231, rfm96, rfm98, sstv, sx1280, sx1281, sx1282, sx1261, sx1262, sx1268, si4432, rfm22, llcc68, pager, pocsag, lorawan, lr1110, lr1120, lr1121",
|
||||
"homepage": "https://github.com/jgromes/RadioLib",
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
name=RadioLib
|
||||
version=7.1.0
|
||||
version=7.1.2
|
||||
author=Jan Gromes <gromes.jan@gmail.com>
|
||||
maintainer=Jan Gromes <gromes.jan@gmail.com>
|
||||
sentence=Universal wireless communication library
|
||||
|
|
|
|||
|
|
@ -133,11 +133,9 @@
|
|||
* RADIOLIB_DEFAULT_SPI - default SPIClass instance to use.
|
||||
* RADIOLIB_NONVOLATILE - macro to place variable into program storage (usually Flash).
|
||||
* RADIOLIB_NONVOLATILE_READ_BYTE - function/macro to read variables saved in program storage (usually Flash).
|
||||
* RADIOLIB_TYPE_ALIAS - construct to create an alias for a type, usually vai the `using` keyword.
|
||||
* RADIOLIB_TYPE_ALIAS - construct to create an alias for a type, usually via the `using` keyword.
|
||||
* RADIOLIB_TONE_UNSUPPORTED - some platforms do not have tone()/noTone(), which is required for AFSK.
|
||||
*
|
||||
* In addition, some platforms may require RadioLib to disable specific drivers (such as ESP8266).
|
||||
*
|
||||
* Users may also specify their own configuration by uncommenting the RADIOLIB_CUSTOM_ARDUINO,
|
||||
* and then specifying all platform parameters in the section below. This will override automatic
|
||||
* platform detection.
|
||||
|
|
@ -365,6 +363,13 @@
|
|||
#define RADIOLIB_ARDUINOHAL_PIN_STATUS_CAST (PinStatus)
|
||||
#define RADIOLIB_ARDUINOHAL_INTERRUPT_MODE_CAST (PinStatus)
|
||||
|
||||
#elif defined(ARDUINO_ARCH_SILABS)
|
||||
// Silicon Labs Arduino
|
||||
#define RADIOLIB_PLATFORM "Arduino Silicon Labs"
|
||||
#define RADIOLIB_ARDUINOHAL_PIN_MODE_CAST (PinMode)
|
||||
#define RADIOLIB_ARDUINOHAL_PIN_STATUS_CAST (PinStatus)
|
||||
#define RADIOLIB_ARDUINOHAL_INTERRUPT_MODE_CAST (PinStatus)
|
||||
|
||||
#else
|
||||
// other Arduino platforms not covered by the above list - this may or may not work
|
||||
#define RADIOLIB_PLATFORM "Unknown Arduino"
|
||||
|
|
@ -578,7 +583,7 @@
|
|||
// version definitions
|
||||
#define RADIOLIB_VERSION_MAJOR 7
|
||||
#define RADIOLIB_VERSION_MINOR 1
|
||||
#define RADIOLIB_VERSION_PATCH 0
|
||||
#define RADIOLIB_VERSION_PATCH 2
|
||||
#define RADIOLIB_VERSION_EXTRA 0
|
||||
|
||||
#define RADIOLIB_VERSION (((RADIOLIB_VERSION_MAJOR) << 24) | ((RADIOLIB_VERSION_MINOR) << 16) | ((RADIOLIB_VERSION_PATCH) << 8) | (RADIOLIB_VERSION_EXTRA))
|
||||
|
|
|
|||
|
|
@ -56,13 +56,21 @@ int16_t Module::SPIgetRegValue(uint32_t reg, uint8_t msb, uint8_t lsb) {
|
|||
return(maskedValue);
|
||||
}
|
||||
|
||||
int16_t Module::SPIsetRegValue(uint32_t reg, uint8_t value, uint8_t msb, uint8_t lsb, uint8_t checkInterval, uint8_t checkMask) {
|
||||
int16_t Module::SPIsetRegValue(uint32_t reg, uint8_t value, uint8_t msb, uint8_t lsb, uint8_t checkInterval, uint8_t checkMask, bool force) {
|
||||
if((msb > 7) || (lsb > 7) || (lsb > msb)) {
|
||||
return(RADIOLIB_ERR_INVALID_BIT_RANGE);
|
||||
}
|
||||
|
||||
// read the current value
|
||||
uint8_t currentValue = SPIreadRegister(reg);
|
||||
uint8_t mask = ~((0b11111111 << (msb + 1)) | (0b11111111 >> (8 - lsb)));
|
||||
|
||||
// check if we actually need to update the register
|
||||
if((currentValue & mask) == (value & mask) && !force) {
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
// update the register
|
||||
uint8_t newValue = (currentValue & ~mask) | (value & mask);
|
||||
SPIwriteRegister(reg, newValue);
|
||||
|
||||
|
|
|
|||
|
|
@ -272,9 +272,10 @@ class Module {
|
|||
\param lsb Least significant bit of the register variable. Bits below this one will not be affected by the write operation.
|
||||
\param checkInterval Number of milliseconds between register writing and verification reading. Some registers need up to 10ms to process the change.
|
||||
\param checkMask Mask of bits to check, only bits set to 1 will be verified.
|
||||
\param force Write new value even if the old value is the same.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t SPIsetRegValue(uint32_t reg, uint8_t value, uint8_t msb = 7, uint8_t lsb = 0, uint8_t checkInterval = 2, uint8_t checkMask = 0xFF);
|
||||
int16_t SPIsetRegValue(uint32_t reg, uint8_t value, uint8_t msb = 7, uint8_t lsb = 0, uint8_t checkInterval = 2, uint8_t checkMask = 0xFF, bool force = false);
|
||||
|
||||
/*!
|
||||
\brief SPI burst read method.
|
||||
|
|
@ -382,12 +383,9 @@ class Module {
|
|||
int16_t SPItransferStream(const uint8_t* cmd, uint8_t cmdLen, bool write, uint8_t* dataOut, uint8_t* dataIn, size_t numBytes, bool waitForGpio);
|
||||
|
||||
// pin number access methods
|
||||
|
||||
/*!
|
||||
\brief Access method to get the pin number of SPI chip select.
|
||||
\returns Pin number of SPI chip select configured in the constructor.
|
||||
*/
|
||||
uint32_t getCs() const { return(csPin); }
|
||||
// getCs is omitted on purpose, as it can interfere when accessing the SPI in a concurrent environment
|
||||
// so it is considered to be part of the SPI pins and hence not accessible from outside
|
||||
// see https://github.com/jgromes/RadioLib/discussions/1364
|
||||
|
||||
/*!
|
||||
\brief Access method to get the pin number of interrupt/GPIO.
|
||||
|
|
|
|||
|
|
@ -4,11 +4,15 @@
|
|||
/*!
|
||||
\mainpage RadioLib Documentation
|
||||
|
||||
Universal wireless communication library for Arduino.
|
||||
Universal wireless communication library for embedded devices.
|
||||
|
||||
\par Currently Supported Wireless Modules and Protocols
|
||||
- CC1101 FSK module
|
||||
- LLCC68 LoRa/FSK module
|
||||
- LR11x0 LoRa/FSK/LR-FHSS module
|
||||
- nRF24 FSK module
|
||||
- RF69 FSK module
|
||||
- RFM2x FSK module
|
||||
- Si443x FSK module
|
||||
- SX126x LoRa/FSK module
|
||||
- SX127x LoRa/FSK module
|
||||
|
|
@ -22,6 +26,8 @@
|
|||
- Hellschreiber (HellClient)
|
||||
- 4-FSK (FSK4Client)
|
||||
- APRS (APRSClient)
|
||||
- POCSAG (PagerClient)
|
||||
- LoRaWAN (LoRaWANNode)
|
||||
|
||||
\par Quick Links
|
||||
Documentation for most common methods can be found in its reference page (see the list above).\n
|
||||
|
|
|
|||
|
|
@ -1,225 +0,0 @@
|
|||
/*
|
||||
RadioLib Non-Arduino Tock Library helper functions
|
||||
|
||||
Licensed under the MIT License
|
||||
|
||||
Copyright (c) 2023 Alistair Francis <alistair@alistair23.me>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifndef TOCK_HAL_H
|
||||
#define TOCK_HAL_H
|
||||
|
||||
// include RadioLib
|
||||
#include <RadioLib.h>
|
||||
|
||||
// include all the dependencies
|
||||
#include "libtock/net/lora_phy.h"
|
||||
#include "libtock/net/syscalls/lora_phy_syscalls.h"
|
||||
#include "libtock-sync/net/lora_phy.h"
|
||||
#include "libtock/peripherals/gpio.h"
|
||||
#include "libtock-sync/services/alarm.h"
|
||||
#include "libtock/kernel/read_only_state.h"
|
||||
|
||||
#define RADIO_BUSY 1
|
||||
#define RADIO_DIO_1 2
|
||||
#define RADIO_DIO_3 3
|
||||
#define RADIO_RESET 4
|
||||
// Skip the chips select as Tock handles this for us
|
||||
#define RADIO_NSS RADIOLIB_NC
|
||||
|
||||
// define Arduino-style macros
|
||||
#define PIN_LOW (0x0)
|
||||
#define PIN_HIGH (0x1)
|
||||
#define PIN_INPUT (0x01)
|
||||
#define PIN_OUTPUT (0x03)
|
||||
#define PIN_RISING (0x01)
|
||||
#define PIN_FALLING (0x02)
|
||||
|
||||
typedef void (*gpioIrqFn)(void);
|
||||
|
||||
gpioIrqFn gpio_funcs[4] = { NULL, NULL, NULL, NULL};
|
||||
uint32_t frequency = 0;
|
||||
|
||||
/*
|
||||
* Get the the timer frequency in Hz.
|
||||
*/
|
||||
int alarm_internal_frequency(uint32_t* frequency) {
|
||||
syscall_return_t rval = command(0x0, 1, 0, 0);
|
||||
return tock_command_return_u32_to_returncode(rval, frequency);
|
||||
}
|
||||
|
||||
int alarm_internal_read(uint32_t* time) {
|
||||
syscall_return_t rval = command(0x0, 2, 0, 0);
|
||||
return tock_command_return_u32_to_returncode(rval, time);
|
||||
}
|
||||
|
||||
static void lora_phy_gpio_Callback (int gpioPin,
|
||||
__attribute__ ((unused)) int arg2,
|
||||
__attribute__ ((unused)) int arg3,
|
||||
void* userdata)
|
||||
{
|
||||
gpioIrqFn fn = gpio_funcs[gpioPin - 1];
|
||||
|
||||
if (fn != NULL ) {
|
||||
fn();
|
||||
}
|
||||
}
|
||||
|
||||
class TockHal : public RadioLibHal {
|
||||
public:
|
||||
// default constructor - initializes the base HAL and any needed private members
|
||||
TockHal()
|
||||
: RadioLibHal(PIN_INPUT, PIN_OUTPUT, PIN_LOW, PIN_HIGH, PIN_RISING, PIN_FALLING) {
|
||||
}
|
||||
|
||||
void init() override {
|
||||
}
|
||||
|
||||
void term() override {
|
||||
}
|
||||
|
||||
// GPIO-related methods (pinMode, digitalWrite etc.) should check
|
||||
// RADIOLIB_NC as an alias for non-connected pins
|
||||
void pinMode(uint32_t pin, uint32_t mode) override {
|
||||
if(pin == RADIOLIB_NC) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mode == PIN_OUTPUT) {
|
||||
libtock_lora_phy_gpio_enable_output(pin);
|
||||
} else if (mode == PIN_INPUT) {
|
||||
libtock_lora_phy_gpio_enable_input(pin, libtock_pull_down);
|
||||
}
|
||||
}
|
||||
|
||||
void digitalWrite(uint32_t pin, uint32_t value) override {
|
||||
if(pin == RADIOLIB_NC) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (value) {
|
||||
libtock_lora_phy_gpio_set(pin);
|
||||
} else {
|
||||
libtock_lora_phy_gpio_clear(pin);
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t digitalRead(uint32_t pin) override {
|
||||
int value;
|
||||
|
||||
if(pin == RADIOLIB_NC) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
libtock_lora_phy_gpio_read(pin, &value);
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
void attachInterrupt(uint32_t interruptNum, gpioIrqFn interruptCb, uint32_t mode) override {
|
||||
if(interruptNum == RADIOLIB_NC) {
|
||||
return;
|
||||
}
|
||||
|
||||
gpio_funcs[interruptNum - 1] = interruptCb;
|
||||
libtock_lora_phy_gpio_command_interrupt_callback(lora_phy_gpio_Callback, NULL);
|
||||
|
||||
// set GPIO as input and enable interrupts on it
|
||||
libtock_lora_phy_gpio_enable_input(interruptNum, libtock_pull_down);
|
||||
libtock_lora_phy_gpio_enable_interrupt(interruptNum, libtock_change);
|
||||
}
|
||||
|
||||
void detachInterrupt(uint32_t interruptNum) override {
|
||||
if(interruptNum == RADIOLIB_NC) {
|
||||
return;
|
||||
}
|
||||
|
||||
gpio_funcs[interruptNum - 1] = NULL;
|
||||
libtock_lora_phy_gpio_disable_interrupt(interruptNum);
|
||||
}
|
||||
|
||||
void delay(unsigned long ms) override {
|
||||
#if !defined(RADIOLIB_CLOCK_DRIFT_MS)
|
||||
libtocksync_alarm_delay_ms(ms);
|
||||
#else
|
||||
libtocksync_alarm_delay_ms(ms * 1000 / (1000 + RADIOLIB_CLOCK_DRIFT_MS));
|
||||
#endif
|
||||
}
|
||||
|
||||
void delayMicroseconds(unsigned long us) override {
|
||||
#if !defined(RADIOLIB_CLOCK_DRIFT_MS)
|
||||
libtocksync_alarm_delay_ms(us / 1000);
|
||||
#else
|
||||
libtocksync_alarm_delay_ms((us * 1000 / (1000 + RADIOLIB_CLOCK_DRIFT_MS)) / 1000);
|
||||
#endif
|
||||
}
|
||||
|
||||
unsigned long millis() override {
|
||||
uint32_t now;
|
||||
unsigned long ms;
|
||||
|
||||
if (frequency == 0) {
|
||||
alarm_internal_frequency(&frequency);
|
||||
}
|
||||
|
||||
alarm_internal_read(&now);
|
||||
|
||||
ms = now / (frequency / 1000);
|
||||
|
||||
#if !defined(RADIOLIB_CLOCK_DRIFT_MS)
|
||||
return ms;
|
||||
#else
|
||||
return ms * 1000 / (1000 + RADIOLIB_CLOCK_DRIFT_MS);
|
||||
#endif
|
||||
}
|
||||
|
||||
unsigned long micros() override {
|
||||
return millis() / 1000;
|
||||
}
|
||||
|
||||
long pulseIn(uint32_t pin, uint32_t state, unsigned long timeout) override {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void spiBegin() {
|
||||
}
|
||||
|
||||
void spiBeginTransaction() {
|
||||
}
|
||||
|
||||
void spiTransfer(uint8_t* out, size_t len, uint8_t* in) {
|
||||
libtocksync_lora_phy_read_write(out, in, len);
|
||||
}
|
||||
|
||||
void spiEndTransaction() {
|
||||
}
|
||||
|
||||
void spiEnd() {
|
||||
}
|
||||
|
||||
void yield() {
|
||||
::yield_no_wait();
|
||||
}
|
||||
|
||||
private:
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
@ -7,94 +7,19 @@ CC1101::CC1101(Module* module) : PhysicalLayer(RADIOLIB_CC1101_FREQUENCY_STEP_SI
|
|||
}
|
||||
|
||||
int16_t CC1101::begin(float freq, float br, float freqDev, float rxBw, int8_t pwr, uint8_t preambleLength) {
|
||||
// set module properties
|
||||
this->mod->spiConfig.cmds[RADIOLIB_MODULE_SPI_COMMAND_READ] = RADIOLIB_CC1101_CMD_READ;
|
||||
this->mod->spiConfig.cmds[RADIOLIB_MODULE_SPI_COMMAND_WRITE] = RADIOLIB_CC1101_CMD_WRITE;
|
||||
this->mod->init();
|
||||
this->mod->hal->pinMode(this->mod->getIrq(), this->mod->hal->GpioModeInput);
|
||||
// set the modulation and execute the common part
|
||||
this->modulation = RADIOLIB_CC1101_MOD_FORMAT_2_FSK;
|
||||
return(this->beginCommon(freq, br, freqDev, rxBw, pwr, preambleLength));
|
||||
}
|
||||
|
||||
// try to find the CC1101 chip
|
||||
uint8_t i = 0;
|
||||
bool flagFound = false;
|
||||
while((i < 10) && !flagFound) {
|
||||
int16_t version = getChipVersion();
|
||||
if((version == RADIOLIB_CC1101_VERSION_CURRENT) || (version == RADIOLIB_CC1101_VERSION_LEGACY) || (version == RADIOLIB_CC1101_VERSION_CLONE)) {
|
||||
flagFound = true;
|
||||
} else {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("CC1101 not found! (%d of 10 tries) RADIOLIB_CC1101_REG_VERSION == 0x%04X, expected 0x0004/0x0014", i + 1, version);
|
||||
this->mod->hal->delay(10);
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
if(!flagFound) {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("No CC1101 found!");
|
||||
this->mod->term();
|
||||
return(RADIOLIB_ERR_CHIP_NOT_FOUND);
|
||||
} else {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("M\tCC1101");
|
||||
}
|
||||
|
||||
// configure settings not accessible by API
|
||||
int16_t state = config();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure publicly accessible settings
|
||||
state = setFrequency(freq);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure bitrate
|
||||
state = setBitRate(br);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default RX bandwidth
|
||||
state = setRxBandwidth(rxBw);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default frequency deviation
|
||||
state = setFrequencyDeviation(freqDev);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default TX output power
|
||||
state = setOutputPower(pwr);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default packet length mode
|
||||
state = variablePacketLengthMode();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default preamble length
|
||||
state = setPreambleLength(preambleLength, preambleLength - 4);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default data shaping
|
||||
state = setDataShaping(RADIOLIB_SHAPING_NONE);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default encoding
|
||||
state = setEncoding(RADIOLIB_ENCODING_NRZ);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default sync word
|
||||
uint8_t sw[RADIOLIB_CC1101_DEFAULT_SW_LEN] = RADIOLIB_CC1101_DEFAULT_SW;
|
||||
state = setSyncWord(sw[0], sw[1], 0, false);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// flush FIFOs
|
||||
SPIsendCommand(RADIOLIB_CC1101_CMD_FLUSH_RX);
|
||||
SPIsendCommand(RADIOLIB_CC1101_CMD_FLUSH_TX);
|
||||
|
||||
return(state);
|
||||
int16_t CC1101::beginFSK4(float freq, float br, float freqDev, float rxBw, int8_t pwr, uint8_t preambleLength) {
|
||||
// set the modulation and execute the common part
|
||||
this->modulation = RADIOLIB_CC1101_MOD_FORMAT_4_FSK;
|
||||
return(this->beginCommon(freq, br, freqDev, rxBw, pwr, preambleLength));
|
||||
}
|
||||
|
||||
void CC1101::reset() {
|
||||
// this is the manual power-on-reset sequence
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
this->mod->hal->delayMicroseconds(5);
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelHigh);
|
||||
this->mod->hal->delayMicroseconds(40);
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
this->mod->hal->delay(10);
|
||||
// just send the command, the reset sequence as described in datasheet seems unnecessary in our usage
|
||||
SPIsendCommand(RADIOLIB_CC1101_CMD_RESET);
|
||||
}
|
||||
|
||||
|
|
@ -922,7 +847,7 @@ int16_t CC1101::setDataShaping(uint8_t sh) {
|
|||
// set data shaping
|
||||
switch(sh) {
|
||||
case RADIOLIB_SHAPING_NONE:
|
||||
state = SPIsetRegValue(RADIOLIB_CC1101_REG_MDMCFG2, RADIOLIB_CC1101_MOD_FORMAT_2_FSK, 6, 4);
|
||||
state = SPIsetRegValue(RADIOLIB_CC1101_REG_MDMCFG2, this->modulation, 6, 4);
|
||||
break;
|
||||
case RADIOLIB_SHAPING_0_5:
|
||||
state = SPIsetRegValue(RADIOLIB_CC1101_REG_MDMCFG2, RADIOLIB_CC1101_MOD_FORMAT_GFSK, 6, 4);
|
||||
|
|
@ -1006,6 +931,87 @@ int16_t CC1101::setDIOMapping(uint32_t pin, uint32_t value) {
|
|||
return(SPIsetRegValue(RADIOLIB_CC1101_REG_IOCFG0 - pin, value));
|
||||
}
|
||||
|
||||
int16_t CC1101::beginCommon(float freq, float br, float freqDev, float rxBw, int8_t pwr, uint8_t preambleLength) {
|
||||
// set module properties
|
||||
this->mod->spiConfig.cmds[RADIOLIB_MODULE_SPI_COMMAND_READ] = RADIOLIB_CC1101_CMD_READ;
|
||||
this->mod->spiConfig.cmds[RADIOLIB_MODULE_SPI_COMMAND_WRITE] = RADIOLIB_CC1101_CMD_WRITE;
|
||||
this->mod->init();
|
||||
this->mod->hal->pinMode(this->mod->getIrq(), this->mod->hal->GpioModeInput);
|
||||
|
||||
// try to find the CC1101 chip
|
||||
uint8_t i = 0;
|
||||
bool flagFound = false;
|
||||
while((i < 10) && !flagFound) {
|
||||
int16_t version = getChipVersion();
|
||||
if((version == RADIOLIB_CC1101_VERSION_CURRENT) || (version == RADIOLIB_CC1101_VERSION_LEGACY) || (version == RADIOLIB_CC1101_VERSION_CLONE)) {
|
||||
flagFound = true;
|
||||
} else {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("CC1101 not found! (%d of 10 tries) RADIOLIB_CC1101_REG_VERSION == 0x%04X, expected 0x0004/0x0014", i + 1, version);
|
||||
this->mod->hal->delay(10);
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
if(!flagFound) {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("No CC1101 found!");
|
||||
this->mod->term();
|
||||
return(RADIOLIB_ERR_CHIP_NOT_FOUND);
|
||||
} else {
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("M\tCC1101");
|
||||
}
|
||||
|
||||
// configure settings not accessible by API
|
||||
int16_t state = config();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure publicly accessible settings
|
||||
state = setFrequency(freq);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure bitrate
|
||||
state = setBitRate(br);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default RX bandwidth
|
||||
state = setRxBandwidth(rxBw);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default frequency deviation
|
||||
state = setFrequencyDeviation(freqDev);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default TX output power
|
||||
state = setOutputPower(pwr);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default packet length mode
|
||||
state = variablePacketLengthMode();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure default preamble length
|
||||
state = setPreambleLength(preambleLength, preambleLength - 4);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default data shaping
|
||||
state = setDataShaping(RADIOLIB_SHAPING_NONE);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default encoding
|
||||
state = setEncoding(RADIOLIB_ENCODING_NRZ);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set default sync word
|
||||
uint8_t sw[RADIOLIB_CC1101_DEFAULT_SW_LEN] = RADIOLIB_CC1101_DEFAULT_SW;
|
||||
state = setSyncWord(sw[0], sw[1], 0, false);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// flush FIFOs
|
||||
SPIsendCommand(RADIOLIB_CC1101_CMD_FLUSH_RX);
|
||||
SPIsendCommand(RADIOLIB_CC1101_CMD_FLUSH_TX);
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t CC1101::config() {
|
||||
// Reset the radio. Registers may be dirty from previous usage.
|
||||
reset();
|
||||
|
|
@ -1154,21 +1160,7 @@ void CC1101::SPIwriteRegisterBurst(uint8_t reg, uint8_t* data, size_t len) {
|
|||
}
|
||||
|
||||
void CC1101::SPIsendCommand(uint8_t cmd) {
|
||||
// pull NSS low
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
|
||||
// start transfer
|
||||
this->mod->hal->spiBeginTransaction();
|
||||
|
||||
// send the command byte
|
||||
uint8_t status = 0;
|
||||
this->mod->hal->spiTransfer(&cmd, 1, &status);
|
||||
|
||||
// stop transfer
|
||||
this->mod->hal->spiEndTransaction();
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelHigh);
|
||||
RADIOLIB_DEBUG_SPI_PRINTLN("CMD\tW\t%02X\t%02X", cmd, status);
|
||||
(void)status;
|
||||
this->mod->SPItransferStream(&cmd, 1, true, NULL, NULL, 0, false);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@
|
|||
|
||||
// CC1101 physical layer properties
|
||||
#define RADIOLIB_CC1101_FREQUENCY_STEP_SIZE 396.7285156
|
||||
#define RADIOLIB_CC1101_MAX_PACKET_LENGTH 63
|
||||
#define RADIOLIB_CC1101_MAX_PACKET_LENGTH 64
|
||||
#define RADIOLIB_CC1101_CRYSTAL_FREQ 26.0
|
||||
#define RADIOLIB_CC1101_DIV_EXPONENT 16
|
||||
|
||||
|
|
@ -191,9 +191,6 @@
|
|||
// RADIOLIB_CC1101_REG_SYNC0
|
||||
#define RADIOLIB_CC1101_SYNC_WORD_LSB 0x91 // 7 0 sync word LSB
|
||||
|
||||
// RADIOLIB_CC1101_REG_PKTLEN
|
||||
#define RADIOLIB_CC1101_PACKET_LENGTH 0xFF // 7 0 packet length in bytes
|
||||
|
||||
// RADIOLIB_CC1101_REG_PKTCTRL1
|
||||
#define RADIOLIB_CC1101_PQT 0x00 // 7 5 preamble quality threshold
|
||||
#define RADIOLIB_CC1101_CRC_AUTOFLUSH_OFF 0b00000000 // 3 3 automatic Rx FIFO flush on CRC check fail: disabled (default)
|
||||
|
|
@ -562,6 +559,24 @@ class CC1101: public PhysicalLayer {
|
|||
int8_t pwr = RADIOLIB_CC1101_DEFAULT_POWER,
|
||||
uint8_t preambleLength = RADIOLIB_CC1101_DEFAULT_PREAMBLELEN);
|
||||
|
||||
/*!
|
||||
\brief Initialization method for 4-FSK modulation.
|
||||
\param freq Carrier frequency in MHz. Defaults to 434 MHz.
|
||||
\param br Bit rate to be used in kbps. Defaults to 4.8 kbps.
|
||||
\param freqDev Frequency deviation from carrier frequency in kHz Defaults to 5.0 kHz.
|
||||
\param rxBw Receiver bandwidth in kHz. Defaults to 135.0 kHz.
|
||||
\param pwr Output power in dBm. Defaults to 10 dBm.
|
||||
\param preambleLength Preamble Length in bits. Defaults to 16 bits.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t beginFSK4(
|
||||
float freq = RADIOLIB_CC1101_DEFAULT_FREQ,
|
||||
float br = RADIOLIB_CC1101_DEFAULT_BR,
|
||||
float freqDev = RADIOLIB_CC1101_DEFAULT_FREQDEV,
|
||||
float rxBw = RADIOLIB_CC1101_DEFAULT_RXBW,
|
||||
int8_t pwr = RADIOLIB_CC1101_DEFAULT_POWER,
|
||||
uint8_t preambleLength = RADIOLIB_CC1101_DEFAULT_PREAMBLELEN);
|
||||
|
||||
/*!
|
||||
\brief Reset method - resets the chip using manual reset sequence (without RESET pin).
|
||||
*/
|
||||
|
|
@ -1014,6 +1029,7 @@ class CC1101: public PhysicalLayer {
|
|||
|
||||
int8_t power = RADIOLIB_CC1101_DEFAULT_POWER;
|
||||
|
||||
int16_t beginCommon(float freq, float br, float freqDev, float rxBw, int8_t pwr, uint8_t preambleLength);
|
||||
int16_t config();
|
||||
int16_t transmitDirect(bool sync, uint32_t frf);
|
||||
int16_t receiveDirect(bool sync);
|
||||
|
|
|
|||
|
|
@ -9,6 +9,13 @@ LLCC68::LLCC68(Module* mod) : SX1262(mod) {
|
|||
int16_t LLCC68::begin(float freq, float bw, uint8_t sf, uint8_t cr, uint8_t syncWord, int8_t pwr, uint16_t preambleLength, float tcxoVoltage, bool useRegulatorLDO) {
|
||||
// execute common part
|
||||
int16_t state = SX126x::begin(cr, syncWord, preambleLength, tcxoVoltage, useRegulatorLDO);
|
||||
if(state == RADIOLIB_ERR_CHIP_NOT_FOUND) {
|
||||
// bit of a hack, but some LLCC68 chips report as "SX1261", try that
|
||||
// for full discussion, see https://github.com/jgromes/RadioLib/issues/1329
|
||||
chipType = RADIOLIB_SX1261_CHIP_TYPE;
|
||||
state = SX126x::begin(cr, syncWord, preambleLength, tcxoVoltage, useRegulatorLDO);
|
||||
RADIOLIB_DEBUG_PRINTLN("LLCC68 version string not found, using SX1261 instead");
|
||||
}
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// configure publicly accessible settings
|
||||
|
|
@ -118,13 +125,13 @@ int16_t LLCC68::checkDataRate(DataRate_t dr) {
|
|||
|
||||
int16_t LLCC68::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
return(this->beginLRFHSS());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@
|
|||
|
||||
#include "../../Module.h"
|
||||
#include "../SX126x/SX1262.h"
|
||||
#include "../SX126x/SX1261.h"
|
||||
|
||||
//RADIOLIB_SX126X_REG_VERSION_STRING
|
||||
#define RADIOLIB_LLCC68_CHIP_TYPE "LLCC68"
|
||||
|
|
|
|||
|
|
@ -113,13 +113,13 @@ int16_t LR1110::checkOutputPower(int8_t power, int8_t* clipped, bool forceHighPo
|
|||
|
||||
int16_t LR1110::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginGFSK());
|
||||
} break;
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
return(this->beginLRFHSS());
|
||||
} break;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -133,13 +133,13 @@ int16_t LR1120::checkOutputPower(int8_t power, int8_t* clipped, bool forceHighPo
|
|||
|
||||
int16_t LR1120::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginGFSK());
|
||||
} break;
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
return(this->beginLRFHSS());
|
||||
} break;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -110,7 +110,8 @@ int16_t LR11x0::beginLRFHSS(uint8_t bw, uint8_t cr, bool narrowGrid, float tcxoV
|
|||
state = setLrFhssConfig(bw, cr);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
state = setSyncWord(0x12AD101B);
|
||||
uint8_t syncWord[] = { 0x12, 0xAD, 0x10, 0x1B };
|
||||
state = setSyncWord(syncWord, 4);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
state = setRegulatorLDO();
|
||||
|
|
@ -128,6 +129,8 @@ int16_t LR11x0::beginGNSS(uint8_t constellations, float tcxoVoltage) {
|
|||
state = this->clearErrors();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set GNSS flag to reserve DIO11 for LF clock
|
||||
this->gnss = true;
|
||||
state = this->configLfClock(RADIOLIB_LR11X0_LF_BUSY_RELEASE_DISABLED | RADIOLIB_LR11X0_LF_CLK_XOSC);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
|
|
@ -353,10 +356,9 @@ int16_t LR11x0::standby(uint8_t mode, bool wakeup) {
|
|||
this->mod->setRfSwitchState(Module::MODE_IDLE);
|
||||
|
||||
if(wakeup) {
|
||||
// pull NSS low for a while to wake up
|
||||
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);
|
||||
// send a NOP command - this pulls the NSS low to exit the sleep mode,
|
||||
// while preventing interference with possible other SPI transactions
|
||||
(void)this->mod->SPIwriteStream((uint16_t)RADIOLIB_LR11X0_CMD_NOP, NULL, 0, false, false);
|
||||
}
|
||||
|
||||
uint8_t buff[] = { mode };
|
||||
|
|
@ -758,20 +760,16 @@ int16_t LR11x0::setCodingRate(uint8_t cr, bool longInterleave) {
|
|||
return(setModulationParamsLoRa(this->spreadingFactor, this->bandwidth, this->codingRate, this->ldrOptimize));
|
||||
}
|
||||
|
||||
int16_t LR11x0::setSyncWord(uint32_t syncWord) {
|
||||
int16_t LR11x0::setSyncWord(uint8_t syncWord) {
|
||||
// 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_LORA) {
|
||||
return(setLoRaSyncWord(syncWord & 0xFF));
|
||||
|
||||
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_LR_FHSS) {
|
||||
return(lrFhssSetSyncWord(syncWord));
|
||||
|
||||
if(type != RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
return(setLoRaSyncWord(syncWord));
|
||||
}
|
||||
|
||||
int16_t LR11x0::setBitRate(float br) {
|
||||
|
|
@ -885,27 +883,36 @@ int16_t LR11x0::setSyncWord(uint8_t* syncWord, size_t len) {
|
|||
uint8_t type = RADIOLIB_LR11X0_PACKET_TYPE_NONE;
|
||||
int16_t state = getPacketType(&type);
|
||||
RADIOLIB_ASSERT(state);
|
||||
if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||
if(type == RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||
// 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));
|
||||
|
||||
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_LORA) {
|
||||
// with length set to 1 and LoRa modem active, assume it is the LoRa sync word
|
||||
if(len > 1) {
|
||||
return(RADIOLIB_ERR_INVALID_SYNC_WORD);
|
||||
}
|
||||
return(setSyncWord(syncWord[0]));
|
||||
|
||||
} else if(type != RADIOLIB_LR11X0_PACKET_TYPE_GFSK) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
} else if(type == RADIOLIB_LR11X0_PACKET_TYPE_LR_FHSS) {
|
||||
// with length set to 4 and LR-FHSS modem active, assume it is the LR-FHSS sync word
|
||||
if(len != sizeof(uint32_t)) {
|
||||
return(RADIOLIB_ERR_INVALID_SYNC_WORD);
|
||||
}
|
||||
uint32_t sync = 0;
|
||||
memcpy(&sync, syncWord, sizeof(uint32_t));
|
||||
return(lrFhssSetSyncWord(sync));
|
||||
|
||||
}
|
||||
|
||||
// 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));
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
int16_t LR11x0::setSyncBits(uint8_t *syncWord, uint8_t bitsLen) {
|
||||
|
|
@ -2032,13 +2039,13 @@ int16_t LR11x0::getModem(ModemType_t* modem) {
|
|||
|
||||
switch(packetType) {
|
||||
case(RADIOLIB_LR11X0_PACKET_TYPE_LORA):
|
||||
*modem = ModemType_t::LoRa;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_LR11X0_PACKET_TYPE_GFSK):
|
||||
*modem = ModemType_t::FSK;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_LR11X0_PACKET_TYPE_LR_FHSS):
|
||||
*modem = ModemType_t::LRFHSS;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LRFHSS;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
|
|
@ -2060,6 +2067,7 @@ int16_t LR11x0::modSetup(float tcxoVoltage, uint8_t modem) {
|
|||
this->mod->spiConfig.stream = true;
|
||||
this->mod->spiConfig.parseStatusCb = SPIparseStatus;
|
||||
this->mod->spiConfig.checkStatusCb = SPIcheckStatus;
|
||||
this->gnss = false;
|
||||
|
||||
// try to find the LR11x0 chip - this will also reset the module at least once
|
||||
if(!LR11x0::findChip(this->chipType)) {
|
||||
|
|
@ -2446,7 +2454,7 @@ int16_t LR11x0::setDioIrqParams(uint32_t irq1, uint32_t irq2) {
|
|||
}
|
||||
|
||||
int16_t LR11x0::setDioIrqParams(uint32_t irq) {
|
||||
return(setDioIrqParams(irq,irq));
|
||||
return(setDioIrqParams(irq, this->gnss ? 0 : irq));
|
||||
}
|
||||
|
||||
int16_t LR11x0::clearIrq(uint32_t irq) {
|
||||
|
|
@ -2457,7 +2465,7 @@ int16_t LR11x0::clearIrq(uint32_t irq) {
|
|||
}
|
||||
|
||||
int16_t LR11x0::configLfClock(uint8_t setup) {
|
||||
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_CONFIG_LF_LOCK, true, &setup, 1));
|
||||
return(this->SPIcommand(RADIOLIB_LR11X0_CMD_CONFIG_LF_CLOCK, true, &setup, 1));
|
||||
}
|
||||
|
||||
int16_t LR11x0::setTcxoMode(uint8_t tune, uint32_t delay) {
|
||||
|
|
|
|||
|
|
@ -33,7 +33,7 @@
|
|||
#define RADIOLIB_LR11X0_CMD_SET_DIO_AS_RF_SWITCH (0x0112)
|
||||
#define RADIOLIB_LR11X0_CMD_SET_DIO_IRQ_PARAMS (0x0113)
|
||||
#define RADIOLIB_LR11X0_CMD_CLEAR_IRQ (0x0114)
|
||||
#define RADIOLIB_LR11X0_CMD_CONFIG_LF_LOCK (0x0116)
|
||||
#define RADIOLIB_LR11X0_CMD_CONFIG_LF_CLOCK (0x0116)
|
||||
#define RADIOLIB_LR11X0_CMD_SET_TCXO_MODE (0x0117)
|
||||
#define RADIOLIB_LR11X0_CMD_REBOOT (0x0118)
|
||||
#define RADIOLIB_LR11X0_CMD_GET_VBAT (0x0119)
|
||||
|
|
@ -281,7 +281,7 @@
|
|||
#define RADIOLIB_LR11X0_IRQ_ALL (0x1BF80FFCUL) // 31 0 all interrupts
|
||||
#define RADIOLIB_LR11X0_IRQ_NONE (0x00UL << 0) // 31 0 no interrupts
|
||||
|
||||
// RADIOLIB_LR11X0_CMD_CONFIG_LF_LOCK
|
||||
// RADIOLIB_LR11X0_CMD_CONFIG_LF_CLOCK
|
||||
#define RADIOLIB_LR11X0_LF_CLK_RC (0x00UL << 0) // 1 0 32.768 kHz source: RC oscillator
|
||||
#define RADIOLIB_LR11X0_LF_CLK_XOSC (0x01UL << 0) // 1 0 crystal oscillator
|
||||
#define RADIOLIB_LR11X0_LF_CLK_EXT (0x02UL << 0) // 1 0 external signal on DIO11
|
||||
|
|
@ -1176,11 +1176,11 @@ class LR11x0: public PhysicalLayer {
|
|||
int16_t setCodingRate(uint8_t cr, bool longInterleave = false);
|
||||
|
||||
/*!
|
||||
\brief Sets LoRa or LR-FHSS sync word.
|
||||
\param syncWord LoRa or LR-FHSS sync word to be set. For LoRa, only 8 least significant bits will be used
|
||||
\brief Sets LoRa sync word.
|
||||
\param syncWord LoRa sync word to be set.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t setSyncWord(uint32_t syncWord);
|
||||
int16_t setSyncWord(uint8_t syncWord);
|
||||
|
||||
/*!
|
||||
\brief Sets GFSK bit rate. Allowed values range from 0.6 to 300.0 kbps.
|
||||
|
|
@ -1828,6 +1828,7 @@ class LR11x0: public PhysicalLayer {
|
|||
float dataRateMeasured = 0;
|
||||
|
||||
uint8_t wifiScanMode = 0;
|
||||
bool gnss = false;
|
||||
|
||||
int16_t modSetup(float tcxoVoltage, uint8_t modem);
|
||||
static int16_t SPIparseStatus(uint8_t in);
|
||||
|
|
|
|||
|
|
@ -321,6 +321,10 @@ void RF69::clearFifoEmptyAction() {
|
|||
clearDio1Action();
|
||||
}
|
||||
|
||||
void RF69::setFifoThreshold(uint8_t threshold) {
|
||||
this->mod->SPIsetRegValue(RADIOLIB_RF69_REG_FIFO_THRESH, threshold, 6, 0);
|
||||
}
|
||||
|
||||
void RF69::setFifoFullAction(void (*func)(void)) {
|
||||
// set the interrupt
|
||||
this->mod->SPIsetRegValue(RADIOLIB_RF69_REG_FIFO_THRESH, RADIOLIB_RF69_FIFO_THRESH, 6, 0);
|
||||
|
|
|
|||
|
|
@ -648,6 +648,14 @@ class RF69: public PhysicalLayer {
|
|||
*/
|
||||
void clearFifoEmptyAction();
|
||||
|
||||
/*!
|
||||
\brief Set FIFO threshold level.
|
||||
Be aware that threshold is also set in setFifoFullAction method.
|
||||
setFifoThreshold method must be called AFTER calling setFifoFullAction!
|
||||
\param threshold Threshold level in bytes.
|
||||
*/
|
||||
void setFifoThreshold(uint8_t threshold);
|
||||
|
||||
/*!
|
||||
\brief Set interrupt service routine function to call when FIFO is full.
|
||||
\param func Pointer to interrupt service routine.
|
||||
|
|
|
|||
|
|
@ -16,11 +16,19 @@ int16_t SX1261::setOutputPower(int8_t power) {
|
|||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set PA config
|
||||
state = SX126x::setPaConfig(0x04, RADIOLIB_SX126X_PA_CONFIG_SX1261, 0x00);
|
||||
uint8_t paDutyCycle = 0x04;
|
||||
int8_t txPwr = power;
|
||||
if(power == 15) {
|
||||
// for 15 dBm, increase the duty cycle and lowe the power to set
|
||||
// SX1261/2 datasheet, DS.SX1261-2.W.APP Rev. 2.1 page 78
|
||||
paDutyCycle = 0x06;
|
||||
txPwr--;
|
||||
}
|
||||
state = SX126x::setPaConfig(paDutyCycle, RADIOLIB_SX126X_PA_CONFIG_SX1261, 0x00);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set output power with default 200us ramp
|
||||
state = SX126x::setTxParams(power, RADIOLIB_SX126X_PA_RAMP_200U);
|
||||
state = SX126x::setTxParams(txPwr, RADIOLIB_SX126X_PA_RAMP_200U);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// restore OCP configuration
|
||||
|
|
@ -29,9 +37,9 @@ int16_t SX1261::setOutputPower(int8_t power) {
|
|||
|
||||
int16_t SX1261::checkOutputPower(int8_t power, int8_t* clipped) {
|
||||
if(clipped) {
|
||||
*clipped = RADIOLIB_MAX(-17, RADIOLIB_MIN(14, power));
|
||||
*clipped = RADIOLIB_MAX(-17, RADIOLIB_MIN(15, power));
|
||||
}
|
||||
RADIOLIB_CHECK_RANGE(power, -17, 14, RADIOLIB_ERR_INVALID_OUTPUT_POWER);
|
||||
RADIOLIB_CHECK_RANGE(power, -17, 15, RADIOLIB_ERR_INVALID_OUTPUT_POWER);
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ class SX1261 : public SX1262 {
|
|||
SX1261(Module* mod); // cppcheck-suppress noExplicitConstructor
|
||||
|
||||
/*!
|
||||
\brief Sets output power. Allowed values are in range from -17 to 14 dBm.
|
||||
\brief Sets output power. Allowed values are in range from -17 to 15 dBm.
|
||||
\param power Output power to be set in dBm.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
|
|
|
|||
|
|
@ -116,13 +116,13 @@ int16_t SX1262::checkOutputPower(int8_t power, int8_t* clipped) {
|
|||
|
||||
int16_t SX1262::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
return(this->beginLRFHSS());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -117,13 +117,13 @@ int16_t SX1268::checkOutputPower(int8_t power, int8_t* clipped) {
|
|||
|
||||
int16_t SX1268::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
return(this->beginLRFHSS());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -74,7 +74,6 @@ int16_t SX126x::beginFSK(float br, float freqDev, float rxBw, uint16_t preambleL
|
|||
this->pulseShape = RADIOLIB_SX126X_GFSK_FILTER_GAUSS_0_5;
|
||||
this->crcTypeFSK = RADIOLIB_SX126X_GFSK_CRC_2_BYTE_INV; // CCITT CRC configuration
|
||||
this->preambleLengthFSK = preambleLength;
|
||||
this->addrComp = RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF;
|
||||
|
||||
// set module properties and perform initial setup
|
||||
int16_t state = this->modSetup(tcxoVoltage, useRegulatorLDO, RADIOLIB_SX126X_PACKET_TYPE_GFSK);
|
||||
|
|
@ -203,8 +202,8 @@ int16_t SX126x::transmit(const uint8_t* data, size_t len, uint8_t addr) {
|
|||
return(RADIOLIB_ERR_PACKET_TOO_LONG);
|
||||
}
|
||||
|
||||
// calculate timeout in ms (500% of expected time-on-air)
|
||||
RadioLibTime_t timeout = (getTimeOnAir(len) * 5) / 1000;
|
||||
// calculate timeout in ms (5ms + 500 % of expected time-on-air)
|
||||
RadioLibTime_t timeout = 5 + (getTimeOnAir(len) * 5) / 1000;
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("Timeout in %lu ms", timeout);
|
||||
|
||||
// start transmission
|
||||
|
|
@ -468,8 +467,10 @@ int16_t SX126x::standby(uint8_t mode, bool wakeup) {
|
|||
this->mod->setRfSwitchState(Module::MODE_IDLE);
|
||||
|
||||
if(wakeup) {
|
||||
// pull NSS low to wake up
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
// send a NOP command - this pulls the NSS low to exit the sleep mode,
|
||||
// while preventing interference with possible other SPI transactions
|
||||
// see https://github.com/jgromes/RadioLib/discussions/1364
|
||||
(void)this->mod->SPIwriteStream((uint16_t)RADIOLIB_SX126X_CMD_NOP, NULL, 0, false, false);
|
||||
}
|
||||
|
||||
uint8_t data[] = { mode };
|
||||
|
|
@ -509,13 +510,15 @@ void SX126x::clearChannelScanAction() {
|
|||
}
|
||||
|
||||
int16_t SX126x::startTransmit(const uint8_t* data, size_t len, uint8_t addr) {
|
||||
(void)addr;
|
||||
|
||||
// check packet length
|
||||
if(len > RADIOLIB_SX126X_MAX_PACKET_LENGTH) {
|
||||
return(RADIOLIB_ERR_PACKET_TOO_LONG);
|
||||
}
|
||||
|
||||
// maximum packet length is decreased by 1 when address filtering is active
|
||||
if((this->addrComp != RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF) && (len > RADIOLIB_SX126X_MAX_PACKET_LENGTH - 1)) {
|
||||
if((RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF != RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF) && (len > RADIOLIB_SX126X_MAX_PACKET_LENGTH - 1)) {
|
||||
return(RADIOLIB_ERR_PACKET_TOO_LONG);
|
||||
}
|
||||
|
||||
|
|
@ -526,13 +529,7 @@ int16_t SX126x::startTransmit(const uint8_t* data, size_t len, uint8_t addr) {
|
|||
state = setPacketParams(this->preambleLengthLoRa, this->crcTypeLoRa, len, this->headerType, this->invertIQEnabled);
|
||||
|
||||
} else if(modem == RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType, len);
|
||||
|
||||
// address is taken from the register
|
||||
if(this->addrComp != RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF) {
|
||||
RADIOLIB_ASSERT(state);
|
||||
state = writeRegister(RADIOLIB_SX126X_REG_NODE_ADDRESS, &addr, 1);
|
||||
}
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType, len);
|
||||
|
||||
} else if(modem != RADIOLIB_SX126X_PACKET_TYPE_LR_FHSS) {
|
||||
return(RADIOLIB_ERR_UNKNOWN);
|
||||
|
|
@ -626,12 +623,6 @@ int16_t SX126x::finishTransmit() {
|
|||
int16_t state = clearIrqStatus();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// restore the original node address
|
||||
if(getPacketType() == RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
state = writeRegister(RADIOLIB_SX126X_REG_NODE_ADDRESS, &this->nodeAddr, 1);
|
||||
RADIOLIB_ASSERT(state);
|
||||
}
|
||||
|
||||
// set mode to standby to disable transmitter/RF switch
|
||||
return(standby());
|
||||
}
|
||||
|
|
@ -641,7 +632,12 @@ int16_t SX126x::startReceive() {
|
|||
}
|
||||
|
||||
int16_t SX126x::startReceive(uint32_t timeout, RadioLibIrqFlags_t irqFlags, RadioLibIrqFlags_t irqMask, size_t len) {
|
||||
(void)len;
|
||||
// in implicit header mode, use the provided length if it is nonzero
|
||||
// otherwise we trust the user has previously set the payload length manually
|
||||
if((this->headerType == RADIOLIB_SX126X_LORA_HEADER_IMPLICIT) && (len != 0)) {
|
||||
this->implicitLen = len;
|
||||
}
|
||||
|
||||
int16_t state = startReceiveCommon(timeout, irqFlags, irqMask);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
|
|
@ -743,7 +739,7 @@ int16_t SX126x::startReceiveCommon(uint32_t timeout, RadioLibIrqFlags_t irqFlags
|
|||
if(modem == RADIOLIB_SX126X_PACKET_TYPE_LORA) {
|
||||
state = setPacketParams(this->preambleLengthLoRa, this->crcTypeLoRa, this->implicitLen, this->headerType, this->invertIQEnabled);
|
||||
} else if(modem == RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType);
|
||||
} else {
|
||||
return(RADIOLIB_ERR_UNKNOWN);
|
||||
}
|
||||
|
|
@ -968,12 +964,15 @@ int16_t SX126x::setPreambleLength(size_t preambleLength) {
|
|||
return(setPacketParams(this->preambleLengthLoRa, this->crcTypeLoRa, this->implicitLen, this->headerType, this->invertIQEnabled));
|
||||
} else if(modem == RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
this->preambleLengthFSK = preambleLength;
|
||||
this->preambleDetLength = preambleLength >= 32 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_32 :
|
||||
preambleLength >= 24 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_24 :
|
||||
preambleLength >= 16 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_16 :
|
||||
preambleLength > 0 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_8 :
|
||||
// maximum preamble detector length is limited by sync word length
|
||||
// for details, see the note in SX1261 datasheet, Rev 2.1, section 6.2.2.1, page 45
|
||||
uint8_t maxDetLen = RADIOLIB_MIN(this->syncWordLength, this->preambleLengthFSK);
|
||||
this->preambleDetLength = maxDetLen >= 32 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_32 :
|
||||
maxDetLen >= 24 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_24 :
|
||||
maxDetLen >= 16 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_16 :
|
||||
maxDetLen > 0 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_8 :
|
||||
RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_OFF;
|
||||
return(setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType));
|
||||
return(setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType));
|
||||
}
|
||||
|
||||
return(RADIOLIB_ERR_UNKNOWN);
|
||||
|
|
@ -1209,7 +1208,16 @@ int16_t SX126x::setSyncWord(uint8_t* syncWord, size_t len) {
|
|||
|
||||
// update packet parameters
|
||||
this->syncWordLength = len * 8;
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
|
||||
// maximum preamble detector length is limited by sync word length
|
||||
// for details, see the note in SX1261 datasheet, Rev 2.1, section 6.2.2.1, page 45
|
||||
uint8_t maxDetLen = RADIOLIB_MIN(this->syncWordLength, this->preambleLengthFSK);
|
||||
this->preambleDetLength = maxDetLen >= 32 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_32 :
|
||||
maxDetLen >= 24 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_24 :
|
||||
maxDetLen >= 16 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_16 :
|
||||
maxDetLen > 0 ? RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_8 :
|
||||
RADIOLIB_SX126X_GFSK_PREAMBLE_DETECT_OFF;
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType);
|
||||
|
||||
return(state);
|
||||
|
||||
|
|
@ -1251,52 +1259,6 @@ int16_t SX126x::setSyncBits(uint8_t *syncWord, uint8_t bitsLen) {
|
|||
return(setSyncWord(syncWord, bytesLen));
|
||||
}
|
||||
|
||||
int16_t SX126x::setNodeAddress(uint8_t addr) {
|
||||
// check active modem
|
||||
if(getPacketType() != RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// enable address filtering (node only)
|
||||
this->addrComp = RADIOLIB_SX126X_GFSK_ADDRESS_FILT_NODE;
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set node address
|
||||
this->nodeAddr = addr;
|
||||
state = writeRegister(RADIOLIB_SX126X_REG_NODE_ADDRESS, &addr, 1);
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX126x::setBroadcastAddress(uint8_t broadAddr) {
|
||||
// check active modem
|
||||
if(getPacketType() != RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// enable address filtering (node and broadcast)
|
||||
this->addrComp = RADIOLIB_SX126X_GFSK_ADDRESS_FILT_NODE_BROADCAST;
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set broadcast address
|
||||
state = writeRegister(RADIOLIB_SX126X_REG_BROADCAST_ADDRESS, &broadAddr, 1);
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX126x::disableAddressFiltering() {
|
||||
// check active modem
|
||||
if(getPacketType() != RADIOLIB_SX126X_PACKET_TYPE_GFSK) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// disable address filtering
|
||||
this->addrComp = RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF;
|
||||
return(setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening));
|
||||
}
|
||||
|
||||
int16_t SX126x::setCRC(uint8_t len, uint16_t initial, uint16_t polynomial, bool inverted) {
|
||||
// check active modem
|
||||
uint8_t modem = getPacketType();
|
||||
|
|
@ -1325,7 +1287,7 @@ int16_t SX126x::setCRC(uint8_t len, uint16_t initial, uint16_t polynomial, bool
|
|||
return(RADIOLIB_ERR_INVALID_CRC_CONFIGURATION);
|
||||
}
|
||||
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// write initial CRC value
|
||||
|
|
@ -1367,7 +1329,7 @@ int16_t SX126x::setWhitening(bool enabled, uint16_t initial) {
|
|||
// disable whitening
|
||||
this->whitening = RADIOLIB_SX126X_GFSK_WHITENING_OFF;
|
||||
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
} else {
|
||||
|
|
@ -1387,7 +1349,7 @@ int16_t SX126x::setWhitening(bool enabled, uint16_t initial) {
|
|||
state = writeRegister(RADIOLIB_SX126X_REG_WHITENING_INITIAL_MSB, data, 2);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, this->packetType);
|
||||
state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, this->packetType);
|
||||
RADIOLIB_ASSERT(state);
|
||||
}
|
||||
return(state);
|
||||
|
|
@ -1682,13 +1644,13 @@ int16_t SX126x::getModem(ModemType_t* modem) {
|
|||
uint8_t packetType = getPacketType();
|
||||
switch(packetType) {
|
||||
case(RADIOLIB_SX126X_PACKET_TYPE_LORA):
|
||||
*modem = ModemType_t::LoRa;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_SX126X_PACKET_TYPE_GFSK):
|
||||
*modem = ModemType_t::FSK;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_SX126X_PACKET_TYPE_LR_FHSS):
|
||||
*modem = ModemType_t::LRFHSS;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LRFHSS;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
|
|
@ -2049,7 +2011,7 @@ int16_t SX126x::setPacketMode(uint8_t mode, uint8_t len) {
|
|||
}
|
||||
|
||||
// set requested packet mode
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, this->addrComp, this->whitening, mode, len);
|
||||
int16_t state = setPacketParamsFSK(this->preambleLengthFSK, this->preambleDetLength, this->crcTypeFSK, this->syncWordLength, RADIOLIB_SX126X_GFSK_ADDRESS_FILT_OFF, this->whitening, mode, len);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// update cached value
|
||||
|
|
|
|||
|
|
@ -823,6 +823,10 @@ class SX126x: public PhysicalLayer {
|
|||
/*!
|
||||
\brief Sets preamble length for LoRa or FSK modem. Allowed values range from 1 to 65535.
|
||||
\param preambleLength Preamble length to be set in symbols (LoRa) or bits (FSK).
|
||||
NOTE: In FSK mode, sync word length limits the preamble detector length
|
||||
(the number of preamble bits that must be detected to start receiving packet).
|
||||
For details, see the note in SX1261 datasheet, Rev 2.1, section 6.2.2.1, page 45.
|
||||
Preamble detector length is adjusted automatically each time this method is called.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t setPreambleLength(size_t preambleLength) override;
|
||||
|
|
@ -887,6 +891,10 @@ class SX126x: public PhysicalLayer {
|
|||
Can also set LR-FHSS sync word, but its length must be 4 bytes.
|
||||
\param syncWord FSK sync word to be set.
|
||||
\param len FSK sync word length in bytes.
|
||||
NOTE: In FSK mode, sync word length limits the preamble detector length
|
||||
(the number of preamble bits that must be detected to start receiving packet).
|
||||
For details, see the note in SX1261 datasheet, Rev 2.1, section 6.2.2.1, page 45.
|
||||
Preamble detector length is adjusted automatically each time this method is called.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t setSyncWord(uint8_t* syncWord, size_t len) override;
|
||||
|
|
@ -1278,10 +1286,9 @@ class SX126x: public PhysicalLayer {
|
|||
bool ldroAuto = true;
|
||||
|
||||
uint32_t bitRate = 0, frequencyDev = 0;
|
||||
uint8_t preambleDetLength = 0, rxBandwidth = 0, pulseShape = 0, crcTypeFSK = 0, syncWordLength = 0, addrComp = 0, whitening = 0, packetType = 0;
|
||||
uint8_t preambleDetLength = 0, rxBandwidth = 0, pulseShape = 0, crcTypeFSK = 0, syncWordLength = 0, whitening = 0, packetType = 0;
|
||||
uint16_t preambleLengthFSK = 0;
|
||||
float rxBandwidthKhz = 0;
|
||||
uint8_t nodeAddr = 0;
|
||||
|
||||
float dataRateMeasured = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -497,11 +497,13 @@ int16_t SX1272::autoLDRO() {
|
|||
}
|
||||
|
||||
int16_t SX1272::implicitHeader(size_t len) {
|
||||
return(setHeaderType(RADIOLIB_SX1272_HEADER_IMPL_MODE, len));
|
||||
this->implicitHdr = true;
|
||||
return(setHeaderType(RADIOLIB_SX1272_HEADER_IMPL_MODE, 2, len));
|
||||
}
|
||||
|
||||
int16_t SX1272::explicitHeader() {
|
||||
return(setHeaderType(RADIOLIB_SX1272_HEADER_EXPL_MODE));
|
||||
this->implicitHdr = false;
|
||||
return(setHeaderType(RADIOLIB_SX1272_HEADER_EXPL_MODE, 2));
|
||||
}
|
||||
|
||||
int16_t SX1272::setBandwidthRaw(uint8_t newBandwidth) {
|
||||
|
|
@ -521,11 +523,13 @@ int16_t SX1272::setSpreadingFactorRaw(uint8_t newSpreadingFactor) {
|
|||
// write registers
|
||||
Module* mod = this->getMod();
|
||||
if(newSpreadingFactor == RADIOLIB_SX127X_SF_6) {
|
||||
this->implicitHdr = true;
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, RADIOLIB_SX1272_HEADER_IMPL_MODE | (SX127x::crcEnabled ? RADIOLIB_SX1272_RX_CRC_MODE_ON : RADIOLIB_SX1272_RX_CRC_MODE_OFF), 2, 1);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_2, RADIOLIB_SX127X_SF_6 | RADIOLIB_SX127X_TX_MODE_SINGLE, 7, 3);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECT_OPTIMIZE, RADIOLIB_SX127X_DETECT_OPTIMIZE_SF_6, 2, 0);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECTION_THRESHOLD, RADIOLIB_SX127X_DETECTION_THRESHOLD_SF_6);
|
||||
} else {
|
||||
this->implicitHdr = false;
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, RADIOLIB_SX1272_HEADER_EXPL_MODE | (SX127x::crcEnabled ? RADIOLIB_SX1272_RX_CRC_MODE_ON : RADIOLIB_SX1272_RX_CRC_MODE_OFF), 2, 1);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_2, newSpreadingFactor | RADIOLIB_SX127X_TX_MODE_SINGLE, 7, 3);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECT_OPTIMIZE, RADIOLIB_SX127X_DETECT_OPTIMIZE_SF_7_12, 2, 0);
|
||||
|
|
@ -544,27 +548,6 @@ int16_t SX1272::setCodingRateRaw(uint8_t newCodingRate) {
|
|||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX1272::setHeaderType(uint8_t headerType, size_t len) {
|
||||
// check active modem
|
||||
if(getActiveModem() != RADIOLIB_SX127X_LORA) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// set requested packet mode
|
||||
Module* mod = this->getMod();
|
||||
int16_t state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, headerType, 2, 2);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set length to register
|
||||
state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_PAYLOAD_LENGTH, len);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// update cached value
|
||||
SX127x::packetLength = len;
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX1272::configFSK() {
|
||||
// configure common registers
|
||||
int16_t state = SX127x::configFSK();
|
||||
|
|
@ -587,10 +570,10 @@ void SX1272::errataFix(bool rx) {
|
|||
|
||||
int16_t SX1272::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -316,7 +316,6 @@ class SX1272: public SX127x {
|
|||
int16_t setBandwidthRaw(uint8_t newBandwidth);
|
||||
int16_t setSpreadingFactorRaw(uint8_t newSpreadingFactor);
|
||||
int16_t setCodingRateRaw(uint8_t newCodingRate);
|
||||
int16_t setHeaderType(uint8_t headerType, size_t len = 0xFF);
|
||||
|
||||
int16_t configFSK();
|
||||
void errataFix(bool rx) override;
|
||||
|
|
|
|||
|
|
@ -117,10 +117,10 @@ int16_t SX1273::checkDataRate(DataRate_t dr) {
|
|||
|
||||
int16_t SX1273::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -81,10 +81,10 @@ int16_t SX1276::setFrequency(float freq) {
|
|||
|
||||
int16_t SX1276::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -159,10 +159,10 @@ int16_t SX1277::checkDataRate(DataRate_t dr) {
|
|||
|
||||
int16_t SX1277::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -535,11 +535,13 @@ int16_t SX1278::autoLDRO() {
|
|||
}
|
||||
|
||||
int16_t SX1278::implicitHeader(size_t len) {
|
||||
return(setHeaderType(RADIOLIB_SX1278_HEADER_IMPL_MODE, len));
|
||||
this->implicitHdr = true;
|
||||
return(setHeaderType(RADIOLIB_SX1278_HEADER_IMPL_MODE, 0, len));
|
||||
}
|
||||
|
||||
int16_t SX1278::explicitHeader() {
|
||||
return(setHeaderType(RADIOLIB_SX1278_HEADER_EXPL_MODE));
|
||||
this->implicitHdr = false;
|
||||
return(setHeaderType(RADIOLIB_SX1278_HEADER_EXPL_MODE, 0));
|
||||
}
|
||||
|
||||
int16_t SX1278::setBandwidthRaw(uint8_t newBandwidth) {
|
||||
|
|
@ -559,11 +561,13 @@ int16_t SX1278::setSpreadingFactorRaw(uint8_t newSpreadingFactor) {
|
|||
// write registers
|
||||
Module* mod = this->getMod();
|
||||
if(newSpreadingFactor == RADIOLIB_SX127X_SF_6) {
|
||||
this->implicitHdr = true;
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, RADIOLIB_SX1278_HEADER_IMPL_MODE, 0, 0);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_2, RADIOLIB_SX127X_SF_6 | RADIOLIB_SX127X_TX_MODE_SINGLE, 7, 3);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECT_OPTIMIZE, RADIOLIB_SX127X_DETECT_OPTIMIZE_SF_6, 2, 0);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECTION_THRESHOLD, RADIOLIB_SX127X_DETECTION_THRESHOLD_SF_6);
|
||||
} else {
|
||||
this->implicitHdr = false;
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, RADIOLIB_SX1278_HEADER_EXPL_MODE, 0, 0);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_2, newSpreadingFactor | RADIOLIB_SX127X_TX_MODE_SINGLE, 7, 3);
|
||||
state |= mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DETECT_OPTIMIZE, RADIOLIB_SX127X_DETECT_OPTIMIZE_SF_7_12, 2, 0);
|
||||
|
|
@ -582,27 +586,6 @@ int16_t SX1278::setCodingRateRaw(uint8_t newCodingRate) {
|
|||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX1278::setHeaderType(uint8_t headerType, size_t len) {
|
||||
// check active modem
|
||||
if(getActiveModem() != RADIOLIB_SX127X_LORA) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// set requested packet mode
|
||||
Module* mod = this->getMod();
|
||||
int16_t state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, headerType, 0, 0);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set length to register
|
||||
state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_PAYLOAD_LENGTH, len);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// update cached value
|
||||
SX127x::packetLength = len;
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX1278::configFSK() {
|
||||
// configure common registers
|
||||
int16_t state = SX127x::configFSK();
|
||||
|
|
@ -707,10 +690,10 @@ void SX1278::errataFix(bool rx) {
|
|||
|
||||
int16_t SX1278::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -328,7 +328,6 @@ class SX1278: public SX127x {
|
|||
int16_t setBandwidthRaw(uint8_t newBandwidth);
|
||||
int16_t setSpreadingFactorRaw(uint8_t newSpreadingFactor);
|
||||
int16_t setCodingRateRaw(uint8_t newCodingRate);
|
||||
int16_t setHeaderType(uint8_t headerType, size_t len = 0xFF);
|
||||
|
||||
int16_t configFSK();
|
||||
void errataFix(bool rx) override;
|
||||
|
|
|
|||
|
|
@ -81,10 +81,10 @@ int16_t SX1279::setFrequency(float freq) {
|
|||
|
||||
int16_t SX1279::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
|
|||
|
|
@ -417,8 +417,9 @@ int16_t SX127x::startReceive(uint32_t timeout, RadioLibIrqFlags_t irqFlags, Radi
|
|||
state = this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_DIO_MAPPING_1, RADIOLIB_SX127X_DIO1_LORA_FHSS_CHANGE_CHANNEL, 5, 4);
|
||||
}
|
||||
|
||||
// set expected packet length for SF6
|
||||
if(this->spreadingFactor == 6) {
|
||||
// in implicit header mode, use the provided length if it is nonzero
|
||||
// otherwise we trust the user has previously set the payload length manually
|
||||
if((this->implicitHdr) && (len != 0)) {
|
||||
state |= this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_PAYLOAD_LENGTH, len);
|
||||
this->packetLength = len;
|
||||
}
|
||||
|
|
@ -504,6 +505,10 @@ void SX127x::clearFifoEmptyAction() {
|
|||
clearDio1Action();
|
||||
}
|
||||
|
||||
void SX127x::setFifoThreshold(uint8_t threshold) {
|
||||
this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FIFO_THRESH, threshold, 5, 0);
|
||||
}
|
||||
|
||||
void SX127x::setFifoFullAction(void (*func)(void)) {
|
||||
// set the interrupt
|
||||
this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FIFO_THRESH, RADIOLIB_SX127X_FIFO_THRESH, 5, 0);
|
||||
|
|
@ -1197,9 +1202,10 @@ int16_t SX127x::setFrequencyRaw(float newFreq) {
|
|||
uint32_t FRF = (newFreq * (uint32_t(1) << RADIOLIB_SX127X_DIV_EXPONENT)) / RADIOLIB_SX127X_CRYSTAL_FREQ;
|
||||
|
||||
// write registers
|
||||
// lsb needs to be written no matter what in order for the module to update the frequency
|
||||
state |= this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FRF_MSB, (FRF & 0xFF0000) >> 16);
|
||||
state |= this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FRF_MID, (FRF & 0x00FF00) >> 8);
|
||||
state |= this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FRF_LSB, FRF & 0x0000FF);
|
||||
state |= this->mod->SPIsetRegValue(RADIOLIB_SX127X_REG_FRF_LSB, FRF & 0x0000FF, 7U, 0U, 2U, 0xFF, true);
|
||||
return(state);
|
||||
}
|
||||
|
||||
|
|
@ -1207,12 +1213,12 @@ size_t SX127x::getPacketLength(bool update) {
|
|||
int16_t modem = getActiveModem();
|
||||
|
||||
if(modem == RADIOLIB_SX127X_LORA) {
|
||||
if(this->spreadingFactor != 6) {
|
||||
// get packet length for SF7 - SF12
|
||||
if(!this->implicitHdr) {
|
||||
// get packet length for explicit header mode
|
||||
return(this->mod->SPIreadRegister(RADIOLIB_SX127X_REG_RX_NB_BYTES));
|
||||
|
||||
} else {
|
||||
// return the cached value for SF6
|
||||
// return the cached value for implicit header mode
|
||||
return(this->packetLength);
|
||||
}
|
||||
|
||||
|
|
@ -1320,7 +1326,7 @@ int16_t SX127x::setIrqFlags(uint32_t irq) {
|
|||
uint8_t usedPinFlags = 0;
|
||||
bool conflict = false;
|
||||
int16_t modem = getActiveModem();
|
||||
int16_t state;
|
||||
int16_t state = RADIOLIB_ERR_NONE;
|
||||
for(uint8_t i = 0; i <= 31; i++) {
|
||||
// check if the bit is set
|
||||
uint32_t irqBit = irq & (1UL << i);
|
||||
|
|
@ -1760,10 +1766,10 @@ int16_t SX127x::getModem(ModemType_t* modem) {
|
|||
int16_t packetType = getActiveModem();
|
||||
switch(packetType) {
|
||||
case(RADIOLIB_SX127X_LORA):
|
||||
*modem = ModemType_t::LoRa;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_SX127X_FSK_OOK):
|
||||
*modem = ModemType_t::FSK;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
|
|
@ -1856,6 +1862,27 @@ float SX127x::getRSSI(bool packet, bool skipReceive, int16_t offset) {
|
|||
}
|
||||
}
|
||||
|
||||
int16_t SX127x::setHeaderType(uint8_t headerType, uint8_t bitIndex, size_t len) {
|
||||
// check active modem
|
||||
if(getActiveModem() != RADIOLIB_SX127X_LORA) {
|
||||
return(RADIOLIB_ERR_WRONG_MODEM);
|
||||
}
|
||||
|
||||
// set requested packet mode
|
||||
Module* mod = this->getMod();
|
||||
int16_t state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_MODEM_CONFIG_1, headerType, bitIndex, bitIndex);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// set length to register
|
||||
state = mod->SPIsetRegValue(RADIOLIB_SX127X_REG_PAYLOAD_LENGTH, len);
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// update cached value
|
||||
SX127x::packetLength = len;
|
||||
|
||||
return(state);
|
||||
}
|
||||
|
||||
int16_t SX127x::setLowBatteryThreshold(int8_t level, uint32_t pin) {
|
||||
// check disable
|
||||
if(level < 0) {
|
||||
|
|
|
|||
|
|
@ -761,6 +761,14 @@ class SX127x: public PhysicalLayer {
|
|||
*/
|
||||
void clearFifoEmptyAction();
|
||||
|
||||
/*!
|
||||
\brief Set FIFO threshold level.
|
||||
Be aware that threshold is also set in setFifoFullAction method.
|
||||
setFifoThreshold method must be called AFTER calling setFifoFullAction!
|
||||
\param threshold Threshold level in bytes.
|
||||
*/
|
||||
void setFifoThreshold(uint8_t threshold);
|
||||
|
||||
/*!
|
||||
\brief Set interrupt service routine function to call when FIFO is full.
|
||||
\param func Pointer to interrupt service routine.
|
||||
|
|
@ -1241,12 +1249,14 @@ class SX127x: public PhysicalLayer {
|
|||
uint8_t codingRate = 0;
|
||||
bool crcEnabled = false;
|
||||
bool ookEnabled = false;
|
||||
bool implicitHdr = false;
|
||||
|
||||
int16_t configFSK();
|
||||
int16_t getActiveModem();
|
||||
int16_t setFrequencyRaw(float newFreq);
|
||||
int16_t setBitRateCommon(float br, uint8_t fracRegAddr);
|
||||
float getRSSI(bool packet, bool skipReceive, int16_t offset);
|
||||
int16_t setHeaderType(uint8_t headerType, uint8_t bitIndex, size_t len = 0xFF);
|
||||
|
||||
#if !RADIOLIB_GODMODE
|
||||
private:
|
||||
|
|
|
|||
|
|
@ -327,8 +327,8 @@ int16_t SX128x::transmit(const uint8_t* data, size_t len, uint8_t addr) {
|
|||
int16_t state = standby();
|
||||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// calculate timeout in ms (500% of expected time-on-air)
|
||||
RadioLibTime_t timeout = (getTimeOnAir(len) * 5) / 1000;
|
||||
// calculate timeout in ms (5ms + 500 % of expected time-on-air)
|
||||
RadioLibTime_t timeout = 5 + (getTimeOnAir(len) * 5) / 1000;
|
||||
RADIOLIB_DEBUG_BASIC_PRINTLN("Timeout in %lu ms", timeout);
|
||||
|
||||
// start transmission
|
||||
|
|
@ -480,8 +480,9 @@ int16_t SX128x::standby(uint8_t mode, bool wakeup) {
|
|||
this->mod->setRfSwitchState(Module::MODE_IDLE);
|
||||
|
||||
if(wakeup) {
|
||||
// pull NSS low to wake up
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
// send a NOP command - this pulls the NSS low to exit the sleep mode,
|
||||
// while preventing interference with possible other SPI transactions
|
||||
(void)this->mod->SPIwriteStream((uint16_t)RADIOLIB_SX128X_CMD_NOP, NULL, 0, false, false);
|
||||
}
|
||||
|
||||
uint8_t data[] = { mode };
|
||||
|
|
@ -589,7 +590,11 @@ int16_t SX128x::startReceive() {
|
|||
}
|
||||
|
||||
int16_t SX128x::startReceive(uint16_t timeout, RadioLibIrqFlags_t irqFlags, RadioLibIrqFlags_t irqMask, size_t len) {
|
||||
(void)len;
|
||||
// in implicit header mode, use the provided length if it is nonzero
|
||||
// otherwise we trust the user has previously set the payload length manually
|
||||
if((this->headerType == RADIOLIB_SX128X_LORA_HEADER_IMPLICIT) && (len != 0)) {
|
||||
this->payloadLen = len;
|
||||
}
|
||||
|
||||
// check active modem
|
||||
if(getPacketType() == RADIOLIB_SX128X_PACKET_TYPE_RANGING) {
|
||||
|
|
@ -858,10 +863,10 @@ int16_t SX128x::checkOutputPower(int8_t pwr, int8_t* clipped) {
|
|||
|
||||
int16_t SX128x::setModem(ModemType_t modem) {
|
||||
switch(modem) {
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
return(this->begin());
|
||||
} break;
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
return(this->beginGFSK());
|
||||
} break;
|
||||
default:
|
||||
|
|
@ -875,10 +880,10 @@ int16_t SX128x::getModem(ModemType_t* modem) {
|
|||
uint8_t packetType = getPacketType();
|
||||
switch(packetType) {
|
||||
case(RADIOLIB_SX128X_PACKET_TYPE_LORA):
|
||||
*modem = ModemType_t::LoRa;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
case(RADIOLIB_SX128X_PACKET_TYPE_GFSK):
|
||||
*modem = ModemType_t::FSK;
|
||||
*modem = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -615,43 +615,7 @@ void nRF24::SPIwriteTxPayload(uint8_t* data, uint8_t numBytes) {
|
|||
}
|
||||
|
||||
void nRF24::SPItransfer(uint8_t cmd, bool write, uint8_t* dataOut, uint8_t* dataIn, uint8_t numBytes) {
|
||||
// prepare the buffers
|
||||
size_t buffLen = 1 + numBytes;
|
||||
#if RADIOLIB_STATIC_ONLY
|
||||
uint8_t buffOut[RADIOLIB_STATIC_ARRAY_SIZE];
|
||||
uint8_t buffIn[RADIOLIB_STATIC_ARRAY_SIZE];
|
||||
#else
|
||||
uint8_t* buffOut = new uint8_t[buffLen];
|
||||
uint8_t* buffIn = new uint8_t[buffLen];
|
||||
#endif
|
||||
uint8_t* buffOutPtr = buffOut;
|
||||
|
||||
// copy the command
|
||||
*(buffOutPtr++) = cmd;
|
||||
|
||||
// copy the data
|
||||
if(write) {
|
||||
memcpy(buffOutPtr, dataOut, numBytes);
|
||||
} else {
|
||||
memset(buffOutPtr, 0x00, numBytes);
|
||||
}
|
||||
|
||||
// do the transfer
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelLow);
|
||||
this->mod->hal->spiBeginTransaction();
|
||||
this->mod->hal->spiTransfer(buffOut, buffLen, buffIn);
|
||||
this->mod->hal->spiEndTransaction();
|
||||
this->mod->hal->digitalWrite(this->mod->getCs(), this->mod->hal->GpioLevelHigh);
|
||||
|
||||
// copy the data
|
||||
if(!write) {
|
||||
memcpy(dataIn, &buffIn[1], numBytes);
|
||||
}
|
||||
|
||||
#if !RADIOLIB_STATIC_ONLY
|
||||
delete[] buffOut;
|
||||
delete[] buffIn;
|
||||
#endif
|
||||
(void)this->mod->SPItransferStream(&cmd, 1, write, dataOut, dataIn, numBytes, false);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -12,13 +12,11 @@ LoRaWANNode::LoRaWANNode(PhysicalLayer* phy, const LoRaWANBand_t* band, uint8_t
|
|||
this->channels[RADIOLIB_LORAWAN_DIR_RX2] = this->band->rx2;
|
||||
this->txPowerMax = this->band->powerMax;
|
||||
this->subBand = subBand;
|
||||
this->dwellTimeEnabledUp = this->dwellTimeUp != 0;
|
||||
this->dwellTimeEnabledDn = this->dwellTimeDn != 0;
|
||||
memset(this->channelPlan, 0, sizeof(this->channelPlan));
|
||||
}
|
||||
|
||||
#if defined(RADIOLIB_BUILD_ARDUINO)
|
||||
int16_t LoRaWANNode::sendReceive(String& strUp, uint8_t fPort, String& strDown, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
int16_t LoRaWANNode::sendReceive(const String& strUp, uint8_t fPort, String& strDown, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
int16_t state = RADIOLIB_ERR_UNKNOWN;
|
||||
|
||||
const char* dataUp = strUp.c_str();
|
||||
|
|
@ -28,7 +26,7 @@ int16_t LoRaWANNode::sendReceive(String& strUp, uint8_t fPort, String& strDown,
|
|||
size_t lenDown = 0;
|
||||
uint8_t dataDown[251];
|
||||
|
||||
state = this->sendReceive((uint8_t*)dataUp, strlen(dataUp), fPort, dataDown, &lenDown, isConfirmed, eventUp, eventDown);
|
||||
state = this->sendReceive((const uint8_t*)dataUp, strlen(dataUp), fPort, dataDown, &lenDown, isConfirmed, eventUp, eventDown);
|
||||
|
||||
if(state == RADIOLIB_ERR_NONE) {
|
||||
// add null terminator
|
||||
|
|
@ -55,7 +53,7 @@ int16_t LoRaWANNode::sendReceive(const char* strUp, uint8_t fPort, uint8_t* data
|
|||
return(this->sendReceive((uint8_t*)strUp, strlen(strUp), fPort, dataDown, lenDown, isConfirmed, eventUp, eventDown));
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::sendReceive(uint8_t* dataUp, size_t lenUp, uint8_t fPort, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
int16_t LoRaWANNode::sendReceive(const uint8_t* dataUp, size_t lenUp, uint8_t fPort, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
// build a temporary buffer
|
||||
// LoRaWAN downlinks can have 250 bytes at most with 1 extra byte for NULL
|
||||
size_t lenDown = 0;
|
||||
|
|
@ -64,7 +62,7 @@ int16_t LoRaWANNode::sendReceive(uint8_t* dataUp, size_t lenUp, uint8_t fPort, b
|
|||
return(this->sendReceive(dataUp, lenUp, fPort, dataDown, &lenDown, isConfirmed, eventUp, eventDown));
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::sendReceive(uint8_t* dataUp, size_t lenUp, uint8_t fPort, uint8_t* dataDown, size_t* lenDown, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
int16_t LoRaWANNode::sendReceive(const uint8_t* dataUp, size_t lenUp, uint8_t fPort, uint8_t* dataDown, size_t* lenDown, bool isConfirmed, LoRaWANEvent_t* eventUp, LoRaWANEvent_t* eventDown) {
|
||||
if(!dataUp || !dataDown || !lenDown) {
|
||||
return(RADIOLIB_ERR_NULL_POINTER);
|
||||
}
|
||||
|
|
@ -241,7 +239,7 @@ uint8_t* LoRaWANNode::getBufferNonces() {
|
|||
return(this->bufferNonces);
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::setBufferNonces(uint8_t* persistentBuffer) {
|
||||
int16_t LoRaWANNode::setBufferNonces(const uint8_t* persistentBuffer) {
|
||||
if(this->isActivated()) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("Did not update buffer: session already active");
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
|
|
@ -292,7 +290,8 @@ void LoRaWANNode::clearSession() {
|
|||
this->confFCntDown = RADIOLIB_LORAWAN_FCNT_NONE;
|
||||
this->adrFCnt = 0;
|
||||
|
||||
// reset number of retransmissions from ADR
|
||||
// reset ADR state
|
||||
this->txPowerSteps = 0;
|
||||
this->nbTrans = 1;
|
||||
|
||||
// clear CSMA settings
|
||||
|
|
@ -307,7 +306,7 @@ void LoRaWANNode::createSession(uint16_t lwMode, uint8_t initialDr) {
|
|||
|
||||
// setup JoinRequest uplink/downlink frequencies and datarates
|
||||
if(this->band->bandType == RADIOLIB_LORAWAN_BAND_DYNAMIC) {
|
||||
this->selectChannelPlanDyn(true);
|
||||
this->selectChannelPlanDyn();
|
||||
} else {
|
||||
this->selectChannelPlanFix();
|
||||
}
|
||||
|
|
@ -346,15 +345,9 @@ void LoRaWANNode::createSession(uint16_t lwMode, uint8_t initialDr) {
|
|||
}
|
||||
|
||||
// if there is no (channel that allowed the) user-specified datarate, use a default datarate
|
||||
// we use the floor of the average datarate of the first enabled channel
|
||||
if(initialDr == RADIOLIB_LORAWAN_DATA_RATE_UNUSED) {
|
||||
for(int i = 0; i < RADIOLIB_LORAWAN_NUM_AVAILABLE_CHANNELS; i++) {
|
||||
if(this->channelPlan[RADIOLIB_LORAWAN_UPLINK][i].enabled) {
|
||||
uint8_t drMin = this->channelPlan[RADIOLIB_LORAWAN_UPLINK][i].drMin;
|
||||
uint8_t drMax = this->channelPlan[RADIOLIB_LORAWAN_UPLINK][i].drMax;
|
||||
drUp = (drMin + drMax) / 2;
|
||||
}
|
||||
}
|
||||
// use the specified datarate from the first channel (this is always defined)
|
||||
drUp = this->channelPlan[RADIOLIB_LORAWAN_UPLINK][0].dr;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -464,7 +457,7 @@ uint8_t* LoRaWANNode::getBufferSession() {
|
|||
return(this->bufferSession);
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::setBufferSession(uint8_t* persistentBuffer) {
|
||||
int16_t LoRaWANNode::setBufferSession(const uint8_t* persistentBuffer) {
|
||||
if(this->isActivated()) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("Did not update buffer: session already active");
|
||||
return(RADIOLIB_ERR_NONE);
|
||||
|
|
@ -588,7 +581,7 @@ int16_t LoRaWANNode::setBufferSession(uint8_t* persistentBuffer) {
|
|||
return(state);
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::beginOTAA(uint64_t joinEUI, uint64_t devEUI, uint8_t* nwkKey, uint8_t* appKey) {
|
||||
int16_t LoRaWANNode::beginOTAA(uint64_t joinEUI, uint64_t devEUI, const uint8_t* nwkKey, const uint8_t* appKey) {
|
||||
if(!appKey) {
|
||||
return(RADIOLIB_ERR_NULL_POINTER);
|
||||
}
|
||||
|
|
@ -617,7 +610,7 @@ int16_t LoRaWANNode::beginOTAA(uint64_t joinEUI, uint64_t devEUI, uint8_t* nwkKe
|
|||
return(RADIOLIB_ERR_NONE);
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::beginABP(uint32_t addr, uint8_t* fNwkSIntKey, uint8_t* sNwkSIntKey, uint8_t* nwkSEncKey, uint8_t* appSKey) {
|
||||
int16_t LoRaWANNode::beginABP(uint32_t addr, const uint8_t* fNwkSIntKey, const uint8_t* sNwkSIntKey, const uint8_t* nwkSEncKey, const uint8_t* appSKey) {
|
||||
if(!nwkSEncKey || !appSKey) {
|
||||
return(RADIOLIB_ERR_NULL_POINTER);
|
||||
}
|
||||
|
|
@ -723,7 +716,7 @@ int16_t LoRaWANNode::processJoinAccept(LoRaWANJoinEvent_t *joinEvent) {
|
|||
}
|
||||
} else {
|
||||
// for v1.0.4, the JoinNonce is simply a non-repeating value (we only check the last value)
|
||||
if(joinNonceNew == this->joinNonce) {
|
||||
if((this->joinNonce > 0) && (joinNonceNew == this->joinNonce)) {
|
||||
return(RADIOLIB_ERR_JOIN_NONCE_INVALID);
|
||||
}
|
||||
}
|
||||
|
|
@ -767,7 +760,7 @@ int16_t LoRaWANNode::processJoinAccept(LoRaWANJoinEvent_t *joinEvent) {
|
|||
|
||||
// in case of dynamic band, reset the channels to clear JoinRequest-specific channels
|
||||
if(this->band->bandType == RADIOLIB_LORAWAN_BAND_DYNAMIC) {
|
||||
this->selectChannelPlanDyn(false);
|
||||
this->selectChannelPlanDyn();
|
||||
}
|
||||
|
||||
uint8_t cOcts[5];
|
||||
|
|
@ -846,8 +839,10 @@ int16_t LoRaWANNode::processJoinAccept(LoRaWANJoinEvent_t *joinEvent) {
|
|||
this->bufferNonces[RADIOLIB_LORAWAN_NONCES_ACTIVE] = (uint8_t)true;
|
||||
|
||||
// generate the signature of the Nonces buffer, and store it in the last two bytes of the Nonces buffer
|
||||
// also store this signature in the Session buffer to make sure these buffers match
|
||||
uint16_t signature = LoRaWANNode::checkSum16(this->bufferNonces, RADIOLIB_LORAWAN_NONCES_BUF_SIZE - 2);
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferNonces[RADIOLIB_LORAWAN_NONCES_SIGNATURE], signature);
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE], signature);
|
||||
|
||||
// store DevAddr and all keys
|
||||
LoRaWANNode::hton<uint32_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_DEV_ADDR], this->devAddr);
|
||||
|
|
@ -855,9 +850,6 @@ int16_t LoRaWANNode::processJoinAccept(LoRaWANJoinEvent_t *joinEvent) {
|
|||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_NWK_SENC_KEY], this->nwkSEncKey, RADIOLIB_AES128_KEY_SIZE);
|
||||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_FNWK_SINT_KEY], this->fNwkSIntKey, RADIOLIB_AES128_KEY_SIZE);
|
||||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_SNWK_SINT_KEY], this->sNwkSIntKey, RADIOLIB_AES128_KEY_SIZE);
|
||||
|
||||
// set the signature of the Nonces buffer in the Session buffer
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE], signature);
|
||||
|
||||
// store network parameters
|
||||
LoRaWANNode::hton<uint32_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_HOMENET_ID], this->homeNetId);
|
||||
|
|
@ -913,7 +905,7 @@ int16_t LoRaWANNode::activateOTAA(uint8_t joinDr, LoRaWANJoinEvent_t *joinEvent)
|
|||
RADIOLIB_ASSERT(state);
|
||||
|
||||
// calculate JoinRequest time-on-air in milliseconds
|
||||
if(this->dwellTimeEnabledUp) {
|
||||
if(this->dwellTimeUp) {
|
||||
RadioLibTime_t toa = this->phyLayer->getTimeOnAir(RADIOLIB_LORAWAN_JOIN_REQUEST_LEN) / 1000;
|
||||
if(toa > this->dwellTimeUp) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("Dwell time exceeded: ToA = %lu, max = %d", (unsigned long)toa, this->dwellTimeUp);
|
||||
|
|
@ -982,8 +974,10 @@ int16_t LoRaWANNode::activateABP(uint8_t initialDr) {
|
|||
this->bufferNonces[RADIOLIB_LORAWAN_NONCES_ACTIVE] = (uint8_t)true;
|
||||
|
||||
// generate the signature of the Nonces buffer, and store it in the last two bytes of the Nonces buffer
|
||||
// also store this signature in the Session buffer to make sure these buffers match
|
||||
uint16_t signature = LoRaWANNode::checkSum16(this->bufferNonces, RADIOLIB_LORAWAN_NONCES_BUF_SIZE - 2);
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferNonces[RADIOLIB_LORAWAN_NONCES_SIGNATURE], signature);
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE], signature);
|
||||
|
||||
// store DevAddr and all keys
|
||||
LoRaWANNode::hton<uint32_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_DEV_ADDR], this->devAddr);
|
||||
|
|
@ -992,9 +986,6 @@ int16_t LoRaWANNode::activateABP(uint8_t initialDr) {
|
|||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_FNWK_SINT_KEY], this->fNwkSIntKey, RADIOLIB_AES128_BLOCK_SIZE);
|
||||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_SNWK_SINT_KEY], this->sNwkSIntKey, RADIOLIB_AES128_BLOCK_SIZE);
|
||||
|
||||
// set the signature of the Nonces buffer in the Session buffer
|
||||
LoRaWANNode::hton<uint16_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE], signature);
|
||||
|
||||
// store network parameters
|
||||
LoRaWANNode::hton<uint32_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_HOMENET_ID], this->homeNetId);
|
||||
LoRaWANNode::hton<uint8_t>(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_VERSION], this->rev);
|
||||
|
|
@ -1139,15 +1130,26 @@ void LoRaWANNode::adrBackoff() {
|
|||
}
|
||||
}
|
||||
|
||||
// try to decrease the datarate
|
||||
// if datarate can be decreased, try it
|
||||
if(this->channels[RADIOLIB_LORAWAN_UPLINK].dr > 0) {
|
||||
if(this->setDatarate(this->channels[RADIOLIB_LORAWAN_UPLINK].dr - 1) == RADIOLIB_ERR_NONE) {
|
||||
return;
|
||||
uint8_t oldDr = this->channels[RADIOLIB_LORAWAN_UPLINK].dr;
|
||||
|
||||
if(this->setDatarate(oldDr - 1) == RADIOLIB_ERR_NONE) {
|
||||
// if there is no dwell time limit, a lower datarate is OK
|
||||
if(!this->dwellTimeUp) {
|
||||
return;
|
||||
}
|
||||
// if there is a dwell time limit, check if this datarate allows an empty uplink
|
||||
if(this->phyLayer->getTimeOnAir(13) / 1000 < this->dwellTimeUp) {
|
||||
return;
|
||||
}
|
||||
// if the Time on Air of an empty uplink exceeded the dwell time, revert
|
||||
this->setDatarate(oldDr);
|
||||
}
|
||||
}
|
||||
|
||||
if(this->band->bandType == RADIOLIB_LORAWAN_BAND_DYNAMIC) {
|
||||
this->selectChannelPlanDyn(false); // revert to default frequencies
|
||||
this->selectChannelPlanDyn(); // revert to default frequencies
|
||||
} else {
|
||||
this->selectChannelPlanFix(); // go back to default selected subband
|
||||
}
|
||||
|
|
@ -1159,7 +1161,7 @@ void LoRaWANNode::adrBackoff() {
|
|||
return;
|
||||
}
|
||||
|
||||
void LoRaWANNode::composeUplink(uint8_t* in, uint8_t lenIn, uint8_t* out, uint8_t fPort, bool isConfirmed) {
|
||||
void LoRaWANNode::composeUplink(const uint8_t* in, uint8_t lenIn, uint8_t* out, uint8_t fPort, bool isConfirmed) {
|
||||
// set the packet fields
|
||||
if(isConfirmed) {
|
||||
out[RADIOLIB_LORAWAN_FHDR_LEN_START_OFFS] = RADIOLIB_LORAWAN_MHDR_MTYPE_CONF_DATA_UP;
|
||||
|
|
@ -1175,10 +1177,18 @@ void LoRaWANNode::composeUplink(uint8_t* in, uint8_t lenIn, uint8_t* out, uint8_
|
|||
out[RADIOLIB_LORAWAN_FHDR_FCTRL_POS] |= RADIOLIB_LORAWAN_FCTRL_ADR_ENABLED;
|
||||
|
||||
// AdrAckReq is set if no downlink has been received for >=Limit uplinks
|
||||
// but it is unset once backoff has been completed (which is internally denoted by adrFCnt == FCNT_NONE)
|
||||
uint32_t adrLimit = 0x01 << this->adrLimitExp;
|
||||
if(this->adrFCnt != RADIOLIB_LORAWAN_FCNT_NONE && (this->fCntUp - this->adrFCnt) >= adrLimit) {
|
||||
out[RADIOLIB_LORAWAN_FHDR_FCTRL_POS] |= RADIOLIB_LORAWAN_FCTRL_ADR_ACK_REQ;
|
||||
if(this->rev == 1) {
|
||||
// AdrAckReq is unset once backoff has been completed
|
||||
// (which is internally denoted by adrFCnt == FCNT_NONE)
|
||||
if(this->adrFCnt != RADIOLIB_LORAWAN_FCNT_NONE && (this->fCntUp - this->adrFCnt) >= adrLimit) {
|
||||
out[RADIOLIB_LORAWAN_FHDR_FCTRL_POS] |= RADIOLIB_LORAWAN_FCTRL_ADR_ACK_REQ;
|
||||
}
|
||||
} else { // rev == 0
|
||||
// AdrAckReq is always set, also when backoff has been completed
|
||||
if(this->adrFCnt == RADIOLIB_LORAWAN_FCNT_NONE || (this->fCntUp - this->adrFCnt) >= adrLimit) {
|
||||
out[RADIOLIB_LORAWAN_FHDR_FCTRL_POS] |= RADIOLIB_LORAWAN_FCTRL_ADR_ACK_REQ;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1561,7 +1571,7 @@ int16_t LoRaWANNode::parseDownlink(uint8_t* data, size_t* len, LoRaWANEvent_t* e
|
|||
#if !RADIOLIB_STATIC_ONLY
|
||||
delete[] downlinkMsg;
|
||||
#endif
|
||||
return(RADIOLIB_ERR_INVALID_PORT);
|
||||
return(RADIOLIB_ERR_DOWNLINK_MALFORMED);
|
||||
}
|
||||
|
||||
// get the frame counter
|
||||
|
|
@ -1641,8 +1651,8 @@ int16_t LoRaWANNode::parseDownlink(uint8_t* data, size_t* len, LoRaWANEvent_t* e
|
|||
isConfirmedDown = true;
|
||||
}
|
||||
|
||||
// a downlink was received, so reset the ADR counter to the last uplink's fCnt
|
||||
this->adrFCnt = this->getFCntUp();
|
||||
// a downlink was received, so restart the ADR counter with the next uplink
|
||||
this->adrFCnt = this->getFCntUp() + 1;
|
||||
|
||||
// if this downlink is on FPort 0, the FOptsLen is the length of the payload
|
||||
// in any other case, the payload (length) is user accessible
|
||||
|
|
@ -1710,15 +1720,24 @@ int16_t LoRaWANNode::parseDownlink(uint8_t* data, size_t* len, LoRaWANEvent_t* e
|
|||
|
||||
while(procLen < fOptsLen) {
|
||||
cid = *mPtr; // MAC id is the first byte
|
||||
|
||||
// fetch length of MAC downlink payload
|
||||
state = this->getMacLen(cid, &fLen, RADIOLIB_LORAWAN_DOWNLINK, true);
|
||||
RADIOLIB_ASSERT(state);
|
||||
if(state != RADIOLIB_ERR_NONE) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("WARNING: Unknown MAC CID %02x", cid);
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("WARNING: Skipping remaining MAC commands");
|
||||
break;
|
||||
}
|
||||
|
||||
// already fetch length of MAC answer payload (if any)
|
||||
uint8_t fLenRe = 0;
|
||||
state = this->getMacLen(cid, &fLenRe, RADIOLIB_LORAWAN_UPLINK, true);
|
||||
RADIOLIB_ASSERT(state);
|
||||
(void)this->getMacLen(cid, &fLenRe, RADIOLIB_LORAWAN_UPLINK, true);
|
||||
// don't care about return value: the previous getMacLen() would have failed anyway
|
||||
|
||||
if(procLen + fLen > fOptsLen) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("Incomplete MAC command %02x (%d bytes, expected %d)", cid, fOptsLen, fLen);
|
||||
return(RADIOLIB_ERR_INVALID_CID);
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("WARNING: Incomplete MAC command %02x (%d bytes, expected %d)", cid, fOptsLen - procLen, fLen);
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("WARNING: Skipping remaining MAC commands");
|
||||
break;
|
||||
}
|
||||
|
||||
bool reply = false;
|
||||
|
|
@ -1929,7 +1948,6 @@ bool LoRaWANNode::execMacCommand(uint8_t cid, uint8_t* optIn, uint8_t lenIn, uin
|
|||
// only acknowledge if the radio is able to operate at or below the requested power level
|
||||
if(state == RADIOLIB_ERR_NONE || (state == RADIOLIB_ERR_INVALID_OUTPUT_POWER && powerActual < power)) {
|
||||
pwrAck = 1;
|
||||
this->txPowerSteps = macTxSteps;
|
||||
} else {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("ADR failed to configure Tx power %d, code %d!", power, state);
|
||||
}
|
||||
|
|
@ -1941,10 +1959,17 @@ bool LoRaWANNode::execMacCommand(uint8_t cid, uint8_t* optIn, uint8_t lenIn, uin
|
|||
|
||||
// if ACK not completely successful, revert and stop
|
||||
if(optOut[0] != 0x07) {
|
||||
this->applyChannelMask(chMaskGrp0123, chMaskGrp45);
|
||||
this->setAvailableChannels(chMaskActive);
|
||||
// according to paragraph 4.3.1.1, if ADR is disabled,
|
||||
// the ADR channel mask must be accepted even if drAck/pwrAck fails.
|
||||
// therefore, only revert the channel mask if ADR is enabled.
|
||||
if(this->adrEnabled) {
|
||||
this->applyChannelMask(chMaskGrp0123, chMaskGrp45);
|
||||
this->setAvailableChannels(chMaskActive);
|
||||
}
|
||||
// revert datarate
|
||||
this->channels[RADIOLIB_LORAWAN_UPLINK].dr = currentDr;
|
||||
// Tx power was not modified
|
||||
// Tx power was not actually modified
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
|
|
@ -2211,10 +2236,7 @@ bool LoRaWANNode::execMacCommand(uint8_t cid, uint8_t* optIn, uint8_t lenIn, uin
|
|||
this->txPowerMax = eirpEncoding[maxEirpRaw];
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("TxParamSetupReq: dlDwell = %d, ulDwell = %d, maxEirp = %d dBm", dlDwell, ulDwell, eirpEncoding[maxEirpRaw]);
|
||||
|
||||
this->dwellTimeEnabledUp = ulDwell ? true : false;
|
||||
this->dwellTimeUp = ulDwell ? RADIOLIB_LORAWAN_DWELL_TIME : 0;
|
||||
|
||||
this->dwellTimeEnabledDn = dlDwell ? true : false;
|
||||
this->dwellTimeDn = dlDwell ? RADIOLIB_LORAWAN_DWELL_TIME : 0;
|
||||
|
||||
memcpy(&this->bufferSession[RADIOLIB_LORAWAN_SESSION_TX_PARAM_SETUP], optIn, lenIn);
|
||||
|
|
@ -2699,11 +2721,13 @@ void LoRaWANNode::setDutyCycle(bool enable, RadioLibTime_t msPerHour) {
|
|||
}
|
||||
|
||||
void LoRaWANNode::setDwellTime(bool enable, RadioLibTime_t msPerUplink) {
|
||||
this->dwellTimeEnabledUp = enable;
|
||||
if(msPerUplink == 0) {
|
||||
this->dwellTimeUp = this->band->dwellTimeUp;
|
||||
} else {
|
||||
if(!enable) {
|
||||
this->dwellTimeUp = 0;
|
||||
|
||||
} else if(msPerUplink > 0) {
|
||||
this->dwellTimeUp = msPerUplink;
|
||||
} else { //msPerUplink == 0
|
||||
this->dwellTimeUp = this->band->dwellTimeUp;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -2776,11 +2800,11 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
// set modem-dependent functions
|
||||
switch(this->band->dataRates[chnl->dr] & RADIOLIB_LORAWAN_DATA_RATE_MODEM) {
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_LORA):
|
||||
if(modem != ModemType_t::LoRa) {
|
||||
state = this->phyLayer->setModem(ModemType_t::LoRa);
|
||||
if(modem != ModemType_t::RADIOLIB_MODEM_LORA) {
|
||||
state = this->phyLayer->setModem(ModemType_t::RADIOLIB_MODEM_LORA);
|
||||
RADIOLIB_ASSERT(state);
|
||||
}
|
||||
modem = ModemType_t::LoRa;
|
||||
modem = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
// downlink messages are sent with inverted IQ
|
||||
if(dir == RADIOLIB_LORAWAN_DOWNLINK) {
|
||||
state = this->phyLayer->invertIQ(true);
|
||||
|
|
@ -2791,11 +2815,11 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
break;
|
||||
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_FSK):
|
||||
if(modem != ModemType_t::FSK) {
|
||||
state = this->phyLayer->setModem(ModemType_t::FSK);
|
||||
if(modem != ModemType_t::RADIOLIB_MODEM_FSK) {
|
||||
state = this->phyLayer->setModem(ModemType_t::RADIOLIB_MODEM_FSK);
|
||||
RADIOLIB_ASSERT(state);
|
||||
}
|
||||
modem = ModemType_t::FSK;
|
||||
modem = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
state = this->phyLayer->setDataShaping(RADIOLIB_SHAPING_1_0);
|
||||
RADIOLIB_ASSERT(state);
|
||||
state = this->phyLayer->setEncoding(RADIOLIB_ENCODING_WHITENING);
|
||||
|
|
@ -2803,11 +2827,11 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
break;
|
||||
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_LR_FHSS):
|
||||
if(modem != ModemType_t::LRFHSS) {
|
||||
state = this->phyLayer->setModem(ModemType_t::LRFHSS);
|
||||
if(modem != ModemType_t::RADIOLIB_MODEM_LRFHSS) {
|
||||
state = this->phyLayer->setModem(ModemType_t::RADIOLIB_MODEM_LRFHSS);
|
||||
RADIOLIB_ASSERT(state);
|
||||
}
|
||||
modem = ModemType_t::LRFHSS;
|
||||
modem = ModemType_t::RADIOLIB_MODEM_LRFHSS;
|
||||
break;
|
||||
|
||||
default:
|
||||
|
|
@ -2836,7 +2860,7 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
uint8_t syncWordLen = 0;
|
||||
size_t preLen = 0;
|
||||
switch(modem) {
|
||||
case(ModemType_t::FSK): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_FSK): {
|
||||
preLen = 8*RADIOLIB_LORAWAN_GFSK_PREAMBLE_LEN;
|
||||
syncWord[0] = (uint8_t)(RADIOLIB_LORAWAN_GFSK_SYNC_WORD >> 16);
|
||||
syncWord[1] = (uint8_t)(RADIOLIB_LORAWAN_GFSK_SYNC_WORD >> 8);
|
||||
|
|
@ -2846,7 +2870,7 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
dr.fsk.bitRate, dr.fsk.freqDev);
|
||||
} break;
|
||||
|
||||
case(ModemType_t::LoRa): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LORA): {
|
||||
preLen = RADIOLIB_LORAWAN_LORA_PREAMBLE_LEN;
|
||||
syncWord[0] = RADIOLIB_LORAWAN_LORA_SYNC_WORD;
|
||||
syncWordLen = 1;
|
||||
|
|
@ -2854,7 +2878,7 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
dr.lora.spreadingFactor, dr.lora.bandwidth, dr.lora.codingRate, dir ? 'D' : 'U');
|
||||
} break;
|
||||
|
||||
case(ModemType_t::LRFHSS): {
|
||||
case(ModemType_t::RADIOLIB_MODEM_LRFHSS): {
|
||||
syncWord[0] = (uint8_t)(RADIOLIB_LORAWAN_LR_FHSS_SYNC_WORD >> 24);
|
||||
syncWord[1] = (uint8_t)(RADIOLIB_LORAWAN_LR_FHSS_SYNC_WORD >> 16);
|
||||
syncWord[2] = (uint8_t)(RADIOLIB_LORAWAN_LR_FHSS_SYNC_WORD >> 8);
|
||||
|
|
@ -2875,7 +2899,7 @@ int16_t LoRaWANNode::setPhyProperties(const LoRaWANChannel_t* chnl, uint8_t dir,
|
|||
if(pre) {
|
||||
preLen = pre;
|
||||
}
|
||||
if(modem != ModemType_t::LRFHSS) {
|
||||
if(modem != ModemType_t::RADIOLIB_MODEM_LRFHSS) {
|
||||
state = this->phyLayer->setPreambleLength(preLen);
|
||||
}
|
||||
return(state);
|
||||
|
|
@ -2970,7 +2994,7 @@ void LoRaWANNode::getChannelPlanMask(uint64_t* chMaskGrp0123, uint32_t* chMaskGr
|
|||
}
|
||||
}
|
||||
|
||||
void LoRaWANNode::selectChannelPlanDyn(bool joinRequest) {
|
||||
void LoRaWANNode::selectChannelPlanDyn() {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("Setting up dynamic channels");
|
||||
|
||||
size_t num = 0;
|
||||
|
|
@ -2980,15 +3004,6 @@ void LoRaWANNode::selectChannelPlanDyn(bool joinRequest) {
|
|||
this->channelPlan[RADIOLIB_LORAWAN_DOWNLINK][num] = this->band->txFreqs[num];
|
||||
}
|
||||
|
||||
// if we're about to send a JoinRequest, copy the JoinRequest channels to the next slots
|
||||
if(joinRequest) {
|
||||
size_t numJR = 0;
|
||||
for(; numJR < 3 && this->band->txJoinReq[num].enabled; numJR++, num++) {
|
||||
this->channelPlan[RADIOLIB_LORAWAN_UPLINK][num] = this->band->txFreqs[num];
|
||||
this->channelPlan[RADIOLIB_LORAWAN_DOWNLINK][num] = this->band->txFreqs[num];
|
||||
}
|
||||
}
|
||||
|
||||
// clear all remaining channels
|
||||
for(; num < RADIOLIB_LORAWAN_NUM_AVAILABLE_CHANNELS; num++) {
|
||||
this->channelPlan[RADIOLIB_LORAWAN_UPLINK][num] = RADIOLIB_LORAWAN_CHANNEL_NONE;
|
||||
|
|
@ -3115,7 +3130,7 @@ int16_t LoRaWANNode::selectChannels() {
|
|||
|
||||
// if downlink dwelltime is enabled, datarate < 2 cannot be used, so clip to 2
|
||||
// only in use on AS923_x bands
|
||||
if(this->dwellTimeEnabledDn && rx1Dr < 2) {
|
||||
if(this->dwellTimeDn && rx1Dr < 2) {
|
||||
rx1Dr = 2;
|
||||
}
|
||||
this->channels[RADIOLIB_LORAWAN_DOWNLINK].dr = rx1Dr;
|
||||
|
|
@ -3267,7 +3282,7 @@ uint8_t LoRaWANNode::getMaxPayloadLen() {
|
|||
maxLen += 13; // mandatory FHDR is 12/13 bytes
|
||||
|
||||
// if not limited by dwell-time, just return maximum
|
||||
if(!this->dwellTimeEnabledUp) {
|
||||
if(!this->dwellTimeUp) {
|
||||
// subtract FHDR (13 bytes) as well as any FOpts
|
||||
return(maxLen - 13 - this->fOptsUpLen);
|
||||
}
|
||||
|
|
@ -3305,7 +3320,7 @@ int16_t LoRaWANNode::findDataRate(uint8_t dr, DataRate_t* dataRate) {
|
|||
|
||||
switch(dataRateBand & RADIOLIB_LORAWAN_DATA_RATE_MODEM) {
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_LORA):
|
||||
modemNew = ModemType_t::LoRa;
|
||||
modemNew = ModemType_t::RADIOLIB_MODEM_LORA;
|
||||
dataRate->lora.spreadingFactor = ((dataRateBand & RADIOLIB_LORAWAN_DATA_RATE_SF) >> 3) + 7;
|
||||
switch(dataRateBand & RADIOLIB_LORAWAN_DATA_RATE_BW) {
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_BW_125_KHZ):
|
||||
|
|
@ -3323,12 +3338,12 @@ int16_t LoRaWANNode::findDataRate(uint8_t dr, DataRate_t* dataRate) {
|
|||
dataRate->lora.codingRate = 5;
|
||||
break;
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_FSK):
|
||||
modemNew = ModemType_t::FSK;
|
||||
modemNew = ModemType_t::RADIOLIB_MODEM_FSK;
|
||||
dataRate->fsk.bitRate = 50;
|
||||
dataRate->fsk.freqDev = 25;
|
||||
break;
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_LR_FHSS):
|
||||
modemNew = ModemType_t::LRFHSS;
|
||||
modemNew = ModemType_t::RADIOLIB_MODEM_LRFHSS;
|
||||
switch(dataRateBand & RADIOLIB_LORAWAN_DATA_RATE_BW) {
|
||||
case(RADIOLIB_LORAWAN_DATA_RATE_BW_137_KHZ):
|
||||
dataRate->lrFhss.bw = 0x02; // specific encoding
|
||||
|
|
@ -3416,7 +3431,7 @@ void LoRaWANNode::processAES(const uint8_t* in, size_t len, uint8_t* key, uint8_
|
|||
}
|
||||
}
|
||||
|
||||
int16_t LoRaWANNode::checkBufferCommon(uint8_t *buffer, uint16_t size) {
|
||||
int16_t LoRaWANNode::checkBufferCommon(const uint8_t *buffer, uint16_t size) {
|
||||
// check if there are actually values in the buffer
|
||||
size_t i = 0;
|
||||
for(; i < size; i++) {
|
||||
|
|
|
|||
|
|
@ -232,7 +232,7 @@ struct LoRaWANMacCommand_t {
|
|||
#define RADIOLIB_LORAWAN_MAC_COMMAND_NONE { .cid = 0, .lenDn = 0, .lenUp = 0, .persist = false, .user = false }
|
||||
|
||||
constexpr LoRaWANMacCommand_t MacTable[RADIOLIB_LORAWAN_NUM_MAC_COMMANDS] = {
|
||||
{ RADIOLIB_LORAWAN_MAC_RESET, 1, 1, false, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_RESET, 1, 1, true, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_LINK_CHECK, 2, 0, false, true },
|
||||
{ RADIOLIB_LORAWAN_MAC_LINK_ADR, 4, 1, false, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_DUTY_CYCLE, 1, 0, false, false },
|
||||
|
|
@ -242,7 +242,7 @@ constexpr LoRaWANMacCommand_t MacTable[RADIOLIB_LORAWAN_NUM_MAC_COMMANDS] = {
|
|||
{ RADIOLIB_LORAWAN_MAC_RX_TIMING_SETUP, 1, 0, true, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_TX_PARAM_SETUP, 1, 0, true, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_DL_CHANNEL, 4, 1, true, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_REKEY, 1, 1, false, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_REKEY, 1, 1, true, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_ADR_PARAM_SETUP, 1, 0, false, false },
|
||||
{ RADIOLIB_LORAWAN_MAC_DEVICE_TIME, 5, 0, false, true },
|
||||
{ RADIOLIB_LORAWAN_MAC_FORCE_REJOIN, 2, 0, false, false },
|
||||
|
|
@ -273,8 +273,8 @@ enum LoRaWANSchemeSession_t {
|
|||
RADIOLIB_LORAWAN_SESSION_FNWK_SINT_KEY = RADIOLIB_LORAWAN_SESSION_APP_SKEY + RADIOLIB_AES128_KEY_SIZE, // 16 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_SNWK_SINT_KEY = RADIOLIB_LORAWAN_SESSION_FNWK_SINT_KEY + RADIOLIB_AES128_KEY_SIZE, // 16 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_DEV_ADDR = RADIOLIB_LORAWAN_SESSION_SNWK_SINT_KEY + RADIOLIB_AES128_KEY_SIZE, // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE = RADIOLIB_LORAWAN_SESSION_DEV_ADDR + sizeof(uint32_t), // 2 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_FCNT_UP = RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE + 2, // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE = RADIOLIB_LORAWAN_SESSION_DEV_ADDR + sizeof(uint32_t), // 2 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_FCNT_UP = RADIOLIB_LORAWAN_SESSION_NONCES_SIGNATURE + sizeof(uint16_t), // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_N_FCNT_DOWN = RADIOLIB_LORAWAN_SESSION_FCNT_UP + sizeof(uint32_t), // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_A_FCNT_DOWN = RADIOLIB_LORAWAN_SESSION_N_FCNT_DOWN + sizeof(uint32_t), // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_ADR_FCNT = RADIOLIB_LORAWAN_SESSION_A_FCNT_DOWN + sizeof(uint32_t), // 4 bytes
|
||||
|
|
@ -291,11 +291,7 @@ enum LoRaWANSchemeSession_t {
|
|||
RADIOLIB_LORAWAN_SESSION_TX_PARAM_SETUP = RADIOLIB_LORAWAN_SESSION_RX_TIMING_SETUP + 1, // 1 byte
|
||||
RADIOLIB_LORAWAN_SESSION_ADR_PARAM_SETUP = RADIOLIB_LORAWAN_SESSION_TX_PARAM_SETUP + 1, // 1 byte
|
||||
RADIOLIB_LORAWAN_SESSION_REJOIN_PARAM_SETUP = RADIOLIB_LORAWAN_SESSION_ADR_PARAM_SETUP + 1, // 1 byte
|
||||
RADIOLIB_LORAWAN_SESSION_BEACON_FREQ = RADIOLIB_LORAWAN_SESSION_REJOIN_PARAM_SETUP + 1, // 3 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_PING_SLOT_CHANNEL = RADIOLIB_LORAWAN_SESSION_BEACON_FREQ + 3, // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_PERIODICITY = RADIOLIB_LORAWAN_SESSION_PING_SLOT_CHANNEL + 4, // 1 byte
|
||||
RADIOLIB_LORAWAN_SESSION_LAST_TIME = RADIOLIB_LORAWAN_SESSION_PERIODICITY + 1, // 4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_UL_CHANNELS = RADIOLIB_LORAWAN_SESSION_LAST_TIME + 4, // 16*5 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_UL_CHANNELS = RADIOLIB_LORAWAN_SESSION_REJOIN_PARAM_SETUP + 1, // 16*5 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_DL_CHANNELS = RADIOLIB_LORAWAN_SESSION_UL_CHANNELS + RADIOLIB_LORAWAN_NUM_AVAILABLE_CHANNELS*5, // 16*4 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_AVAILABLE_CHANNELS = RADIOLIB_LORAWAN_SESSION_DL_CHANNELS + RADIOLIB_LORAWAN_NUM_AVAILABLE_CHANNELS*4, // 2 bytes
|
||||
RADIOLIB_LORAWAN_SESSION_MAC_QUEUE = RADIOLIB_LORAWAN_SESSION_AVAILABLE_CHANNELS + sizeof(uint16_t), // 15 bytes
|
||||
|
|
@ -405,9 +401,6 @@ struct LoRaWANBand_t {
|
|||
/*! \brief A set of default uplink (TX) channels for dynamic bands */
|
||||
LoRaWANChannel_t txFreqs[3];
|
||||
|
||||
/*! \brief A set of possible extra channels for the Join-Request message for dynamic bands */
|
||||
LoRaWANChannel_t txJoinReq[3];
|
||||
|
||||
/*! \brief The number of TX channel spans for fixed bands */
|
||||
uint8_t numTxSpans;
|
||||
|
||||
|
|
@ -548,7 +541,7 @@ class LoRaWANNode {
|
|||
\param persistentBuffer Buffer that should match the internal format (previously extracted using getBufferNonces)
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t setBufferNonces(uint8_t* persistentBuffer);
|
||||
int16_t setBufferNonces(const uint8_t* persistentBuffer);
|
||||
|
||||
/*!
|
||||
\brief Clear an active session, so that the device will have to rejoin the network.
|
||||
|
|
@ -566,7 +559,7 @@ class LoRaWANNode {
|
|||
\param persistentBuffer Buffer that should match the internal format (previously extracted using getBufferSession)
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t setBufferSession(uint8_t* persistentBuffer);
|
||||
int16_t setBufferSession(const uint8_t* persistentBuffer);
|
||||
|
||||
/*!
|
||||
\brief Set the device credentials and activation configuration
|
||||
|
|
@ -576,7 +569,7 @@ class LoRaWANNode {
|
|||
\param appKey Pointer to the application AES-128 key.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t beginOTAA(uint64_t joinEUI, uint64_t devEUI, uint8_t* nwkKey, uint8_t* appKey);
|
||||
int16_t beginOTAA(uint64_t joinEUI, uint64_t devEUI, const uint8_t* nwkKey, const uint8_t* appKey);
|
||||
|
||||
/*!
|
||||
\brief Set the device credentials and activation configuration
|
||||
|
|
@ -588,7 +581,7 @@ class LoRaWANNode {
|
|||
\param appSKey Pointer to the application session AES-128 key.
|
||||
\returns \ref status_codes
|
||||
*/
|
||||
int16_t beginABP(uint32_t addr, uint8_t* fNwkSIntKey, uint8_t* sNwkSIntKey, uint8_t* nwkSEncKey, uint8_t* appSKey);
|
||||
int16_t beginABP(uint32_t addr, const uint8_t* fNwkSIntKey, const uint8_t* sNwkSIntKey, const uint8_t* nwkSEncKey, const uint8_t* appSKey);
|
||||
|
||||
/*!
|
||||
\brief Join network by restoring OTAA session or performing over-the-air activation. By this procedure,
|
||||
|
|
@ -622,7 +615,7 @@ class LoRaWANNode {
|
|||
(fPort, frame counter, etc.). If set to NULL, no extra information will be passed to the user.
|
||||
\returns Window number > 0 if downlink was received, 0 is no downlink was received, otherwise \ref status_codes
|
||||
*/
|
||||
virtual int16_t sendReceive(String& strUp, uint8_t fPort, String& strDown, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
virtual int16_t sendReceive(const String& strUp, uint8_t fPort, String& strDown, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
#endif
|
||||
|
||||
/*!
|
||||
|
|
@ -665,7 +658,7 @@ class LoRaWANNode {
|
|||
(fPort, frame counter, etc.). If set to NULL, no extra information will be passed to the user.
|
||||
\returns Window number > 0 if downlink was received, 0 is no downlink was received, otherwise \ref status_codes
|
||||
*/
|
||||
virtual int16_t sendReceive(uint8_t* dataUp, size_t lenUp, uint8_t fPort = 1, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
virtual int16_t sendReceive(const uint8_t* dataUp, size_t lenUp, uint8_t fPort = 1, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
|
||||
/*!
|
||||
\brief Send a message to the server and wait for a downlink during Rx1 and/or Rx2 window.
|
||||
|
|
@ -681,7 +674,7 @@ class LoRaWANNode {
|
|||
(fPort, frame counter, etc.). If set to NULL, no extra information will be passed to the user.
|
||||
\returns Window number > 0 if downlink was received, 0 is no downlink was received, otherwise \ref status_codes
|
||||
*/
|
||||
virtual int16_t sendReceive(uint8_t* dataUp, size_t lenUp, uint8_t fPort, uint8_t* dataDown, size_t* lenDown, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
virtual int16_t sendReceive(const uint8_t* dataUp, size_t lenUp, uint8_t fPort, uint8_t* dataDown, size_t* lenDown, bool isConfirmed = false, LoRaWANEvent_t* eventUp = NULL, LoRaWANEvent_t* eventDown = NULL);
|
||||
|
||||
/*!
|
||||
\brief Add a MAC command to the uplink queue.
|
||||
|
|
@ -750,10 +743,10 @@ class LoRaWANNode {
|
|||
void setDutyCycle(bool enable = true, RadioLibTime_t msPerHour = 0);
|
||||
|
||||
/*!
|
||||
\brief Toggle adherence to dwellTime limits to on or off.
|
||||
\brief Set or disable uplink dwell time limitation; enabled by default if mandatory.
|
||||
\param enable Whether to adhere to dwellTime limits or not (default true).
|
||||
\param msPerUplink The maximum allowed Time-on-Air per uplink in milliseconds
|
||||
(default 0 = maximum allowed for configured band).
|
||||
(default 0 = band default value); make sure you follow regulations/law!
|
||||
*/
|
||||
void setDwellTime(bool enable, RadioLibTime_t msPerUplink = 0);
|
||||
|
||||
|
|
@ -920,9 +913,7 @@ class LoRaWANNode {
|
|||
uint32_t dutyCycle = 0;
|
||||
|
||||
// dwell time is set upon initialization and activated in regions that impose this
|
||||
bool dwellTimeEnabledUp = false;
|
||||
uint16_t dwellTimeUp = 0;
|
||||
bool dwellTimeEnabledDn = false;
|
||||
uint16_t dwellTimeDn = 0;
|
||||
|
||||
RadioLibTime_t tUplink = 0; // scheduled uplink transmission time (internal clock)
|
||||
|
|
@ -1002,7 +993,7 @@ class LoRaWANNode {
|
|||
void adrBackoff();
|
||||
|
||||
// create an encrypted uplink buffer, composing metadata, user data and MAC data
|
||||
void composeUplink(uint8_t* in, uint8_t lenIn, uint8_t* out, uint8_t fPort, bool isConfirmed);
|
||||
void composeUplink(const uint8_t* in, uint8_t lenIn, uint8_t* out, uint8_t fPort, bool isConfirmed);
|
||||
|
||||
// generate and set the MIC of an uplink buffer (depends on selected channels)
|
||||
void micUplink(uint8_t* inOut, uint8_t lenInOut);
|
||||
|
|
@ -1071,7 +1062,7 @@ class LoRaWANNode {
|
|||
// setup uplink/downlink channel data rates and frequencies
|
||||
// for dynamic channels, there is a small set of predefined channels
|
||||
// in case of JoinRequest, add some optional extra frequencies
|
||||
void selectChannelPlanDyn(bool joinRequest = false);
|
||||
void selectChannelPlanDyn();
|
||||
|
||||
// setup uplink/downlink channel data rates and frequencies
|
||||
// for fixed bands, we only allow one sub-band at a time to be selected
|
||||
|
|
@ -1112,11 +1103,11 @@ class LoRaWANNode {
|
|||
static uint16_t checkSum16(const uint8_t *key, uint16_t keyLen);
|
||||
|
||||
// check the integrity of a buffer using a 16-bit checksum located in the last two bytes of the buffer
|
||||
static int16_t checkBufferCommon(uint8_t *buffer, uint16_t size);
|
||||
static int16_t checkBufferCommon(const uint8_t *buffer, uint16_t size);
|
||||
|
||||
// network-to-host conversion method - takes data from network packet and converts it to the host endians
|
||||
template<typename T>
|
||||
static T ntoh(uint8_t* buff, size_t size = 0);
|
||||
static T ntoh(const uint8_t* buff, size_t size = 0);
|
||||
|
||||
// host-to-network conversion method - takes data from host variable and and converts it to network packet endians
|
||||
template<typename T>
|
||||
|
|
@ -1124,8 +1115,8 @@ class LoRaWANNode {
|
|||
};
|
||||
|
||||
template<typename T>
|
||||
T LoRaWANNode::ntoh(uint8_t* buff, size_t size) {
|
||||
uint8_t* buffPtr = buff;
|
||||
T LoRaWANNode::ntoh(const uint8_t* buff, size_t size) {
|
||||
const uint8_t* buffPtr = buff;
|
||||
size_t targetSize = sizeof(T);
|
||||
if(size != 0) {
|
||||
targetSize = size;
|
||||
|
|
|
|||
|
|
@ -30,14 +30,9 @@ const LoRaWANBand_t EU868 = {
|
|||
.dwellTimeDn = 0,
|
||||
.txParamSupported = false,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 8681000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 8683000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 8685000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
{ .enabled = true, .idx = 0, .freq = 8681000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 8683000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 8685000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
.txSpans = {
|
||||
|
|
@ -107,11 +102,6 @@ const LoRaWANBand_t US915 = {
|
|||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 2,
|
||||
.txSpans = {
|
||||
{
|
||||
|
|
@ -197,14 +187,9 @@ const LoRaWANBand_t EU433 = {
|
|||
.dwellTimeDn = 0,
|
||||
.txParamSupported = false,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 4331750, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 4333750, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 4335750, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
{ .enabled = true, .idx = 0, .freq = 4331750, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 4333750, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 4335750, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
.txSpans = {
|
||||
|
|
@ -274,11 +259,6 @@ const LoRaWANBand_t AU915 = {
|
|||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 2,
|
||||
.txSpans = {
|
||||
{
|
||||
|
|
@ -368,11 +348,6 @@ const LoRaWANBand_t CN500 = {
|
|||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 1,
|
||||
.txSpans = {
|
||||
{
|
||||
|
|
@ -451,13 +426,8 @@ const LoRaWANBand_t AS923 = {
|
|||
.dwellTimeDn = RADIOLIB_LORAWAN_DWELL_TIME,
|
||||
.txParamSupported = true,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 9232000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9234000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
{ .enabled = true, .idx = 0, .freq = 9232000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9234000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
|
|
@ -524,13 +494,8 @@ const LoRaWANBand_t AS923_2 = {
|
|||
.dwellTimeDn = RADIOLIB_LORAWAN_DWELL_TIME,
|
||||
.txParamSupported = true,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 9214000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9216000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
{ .enabled = true, .idx = 0, .freq = 9214000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9216000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
|
|
@ -597,13 +562,8 @@ const LoRaWANBand_t AS923_3 = {
|
|||
.dwellTimeDn = RADIOLIB_LORAWAN_DWELL_TIME,
|
||||
.txParamSupported = true,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 9166000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9168000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
{ .enabled = true, .idx = 0, .freq = 9166000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9168000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
|
|
@ -670,13 +630,8 @@ const LoRaWANBand_t AS923_4 = {
|
|||
.dwellTimeDn = RADIOLIB_LORAWAN_DWELL_TIME,
|
||||
.txParamSupported = true,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 9173000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9175000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
{ .enabled = true, .idx = 0, .freq = 9173000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9175000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
|
|
@ -743,14 +698,9 @@ const LoRaWANBand_t KR920 = {
|
|||
.dwellTimeDn = 0,
|
||||
.txParamSupported = false,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 9221000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9223000, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 9225000, .drMin = 0, .drMax = 5, .dr = 5, .available = true }
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
{ .enabled = true, .idx = 0, .freq = 9221000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 9223000, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 9225000, .drMin = 0, .drMax = 5, .dr = 3, .available = true }
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
.txSpans = {
|
||||
|
|
@ -816,14 +766,9 @@ const LoRaWANBand_t IN865 = {
|
|||
.dwellTimeDn = 0,
|
||||
.txParamSupported = false,
|
||||
.txFreqs = {
|
||||
{ .enabled = true, .idx = 0, .freq = 8650625, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 8654025, .drMin = 0, .drMax = 5, .dr = 5, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 8659850, .drMin = 0, .drMax = 5, .dr = 5, .available = true }
|
||||
},
|
||||
.txJoinReq = {
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE,
|
||||
RADIOLIB_LORAWAN_CHANNEL_NONE
|
||||
{ .enabled = true, .idx = 0, .freq = 8650625, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 1, .freq = 8654025, .drMin = 0, .drMax = 5, .dr = 3, .available = true },
|
||||
{ .enabled = true, .idx = 2, .freq = 8659850, .drMin = 0, .drMax = 5, .dr = 3, .available = true }
|
||||
},
|
||||
.numTxSpans = 0,
|
||||
.txSpans = {
|
||||
|
|
|
|||
|
|
@ -93,7 +93,7 @@ int16_t PagerClient::transmit(uint8_t* data, size_t len, uint32_t addr, uint8_t
|
|||
}
|
||||
|
||||
// Automatically set function bits based on given encoding
|
||||
if (function == RADIOLIB_PAGER_FUNC_AUTO) {
|
||||
if(function == RADIOLIB_PAGER_FUNC_AUTO) {
|
||||
if(encoding == RADIOLIB_PAGER_BCD) {
|
||||
function = RADIOLIB_PAGER_FUNC_BITS_NUMERIC;
|
||||
|
||||
|
|
@ -101,14 +101,14 @@ int16_t PagerClient::transmit(uint8_t* data, size_t len, uint32_t addr, uint8_t
|
|||
function = RADIOLIB_PAGER_FUNC_BITS_ALPHA;
|
||||
|
||||
} else {
|
||||
return(RADIOLIB_ERR_INVALID_ENCODING);
|
||||
return(RADIOLIB_ERR_INVALID_ENCODING);
|
||||
|
||||
}
|
||||
if(len == 0) {
|
||||
function = RADIOLIB_PAGER_FUNC_BITS_TONE;
|
||||
}
|
||||
}
|
||||
if (function > RADIOLIB_PAGER_FUNC_BITS_ALPHA) {
|
||||
if(function > RADIOLIB_PAGER_FUNC_BITS_ALPHA) {
|
||||
return(RADIOLIB_ERR_INVALID_FUNCTION);
|
||||
}
|
||||
|
||||
|
|
@ -168,7 +168,7 @@ int16_t PagerClient::transmit(uint8_t* data, size_t len, uint32_t addr, uint8_t
|
|||
uint8_t blockPos = RADIOLIB_PAGER_PREAMBLE_LENGTH + 1 + framePos + 1 + i;
|
||||
|
||||
// check if we need to skip a frame sync marker
|
||||
if(((blockPos - (RADIOLIB_PAGER_PREAMBLE_LENGTH + 1)) % RADIOLIB_PAGER_BATCH_LEN) == 0) {
|
||||
if(((blockPos - RADIOLIB_PAGER_PREAMBLE_LENGTH) % (RADIOLIB_PAGER_BATCH_LEN + 1)) == 0) {
|
||||
blockPos++;
|
||||
i++;
|
||||
}
|
||||
|
|
@ -323,7 +323,7 @@ int16_t PagerClient::readData(String& str, size_t len, uint32_t* addr) {
|
|||
state = readData(data, &length, addr);
|
||||
|
||||
if(state == RADIOLIB_ERR_NONE) {
|
||||
// check tone-only tramsissions
|
||||
// check tone-only transmissions
|
||||
if(length == 0) {
|
||||
length = 6;
|
||||
strncpy((char*)data, "<tone>", length + 1);
|
||||
|
|
@ -497,6 +497,7 @@ bool PagerClient::addressMatched(uint32_t addr) {
|
|||
void PagerClient::write(uint32_t* data, size_t len) {
|
||||
// write code words from buffer
|
||||
for(size_t i = 0; i < len; i++) {
|
||||
RADIOLIB_DEBUG_PROTOCOL_PRINTLN("POCSAG W\t%lu\t%08lX", (long unsigned int)i, (long unsigned int)data[i]);
|
||||
PagerClient::write(data[i]);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -135,9 +135,9 @@ union ChannelScanConfig_t {
|
|||
\brief Type of modem, used by setModem.
|
||||
*/
|
||||
enum ModemType_t {
|
||||
FSK = 0,
|
||||
LoRa,
|
||||
LRFHSS,
|
||||
RADIOLIB_MODEM_FSK = 0,
|
||||
RADIOLIB_MODEM_LORA,
|
||||
RADIOLIB_MODEM_LRFHSS,
|
||||
};
|
||||
|
||||
/*!
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ uint32_t rlb_reflect(uint32_t in, uint8_t bits) {
|
|||
return(res);
|
||||
}
|
||||
|
||||
void rlb_hexdump(const char* level, uint8_t* data, size_t len, uint32_t offset, uint8_t width, bool be) {
|
||||
void rlb_hexdump(const char* level, const uint8_t* data, size_t len, uint32_t offset, uint8_t width, bool be) {
|
||||
#if RADIOLIB_DEBUG
|
||||
size_t rem_len = len;
|
||||
for(size_t i = 0; i < len; i+=16) {
|
||||
|
|
|
|||
|
|
@ -33,7 +33,7 @@ uint32_t rlb_reflect(uint32_t in, uint8_t bits);
|
|||
\param width Word width (1 for uint8_t, 2 for uint16_t, 4 for uint32_t).
|
||||
\param be Print multi-byte data as big endian. Defaults to false.
|
||||
*/
|
||||
void rlb_hexdump(const char* level, uint8_t* data, size_t len, uint32_t offset = 0, uint8_t width = 1, bool be = false);
|
||||
void rlb_hexdump(const char* level, const uint8_t* data, size_t len, uint32_t offset = 0, uint8_t width = 1, bool be = false);
|
||||
|
||||
#if RADIOLIB_DEBUG && defined(RADIOLIB_BUILD_ARDUINO)
|
||||
size_t rlb_printf(const char* format, ...);
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue