From 211cf00a74d52a2bfdcff8fdabe4c22c675e7754 Mon Sep 17 00:00:00 2001 From: Florent Date: Sun, 1 Jun 2025 17:13:07 +0200 Subject: [PATCH 01/13] initial support for xiao_c6 --- variants/xiao_c6/platformio.ini | 68 +++++++++++++++++++++++++++ variants/xiao_c6/target.cpp | 82 +++++++++++++++++++++++++++++++++ variants/xiao_c6/target.h | 20 ++++++++ 3 files changed, 170 insertions(+) create mode 100644 variants/xiao_c6/platformio.ini create mode 100644 variants/xiao_c6/target.cpp create mode 100644 variants/xiao_c6/target.h diff --git a/variants/xiao_c6/platformio.ini b/variants/xiao_c6/platformio.ini new file mode 100644 index 00000000..6dab57d9 --- /dev/null +++ b/variants/xiao_c6/platformio.ini @@ -0,0 +1,68 @@ +[Xiao_C6] +extends = esp32c6_base +board = esp32-c6-devkitm-1 +board_build.partitions = min_spiffs.csv ; get around 4mb flash limit +build_flags = + ${esp32c6_base.build_flags} + -I variants/xiao_c6 + -D ARDUINO_USB_CDC_ON_BOOT=1 + -D ARDUINO_USB_MODE=1 + -D P_LORA_TX_LED=15 + -D P_LORA_SCLK=19 + -D P_LORA_MISO=20 + -D P_LORA_MOSI=18 + -D P_LORA_NSS=22 + -D P_LORA_DIO_1=1 + -D P_LORA_BUSY=21 + -D P_LORA_RESET=2 + -D PIN_BOARD_SDA=16 + -D PIN_BOARD_SCL=17 + -D SX126X_RXEN=23 +; -D SX126X_TXEN=14 + -D SX126X_DIO2_AS_RF_SWITCH=true + -D SX126X_DIO3_TCXO_VOLTAGE=1.8 + -D SX126X_CURRENT_LIMIT=140 + -D SX126X_RX_BOOSTED_GAIN=1 + -D RADIO_CLASS=CustomSX1262 + -D WRAPPER_CLASS=CustomSX1262Wrapper + -D LORA_TX_POWER=22 + -D DISABLE_WIFI_OTA=1 +build_src_filter = ${esp32c6_base.build_src_filter} + +<../variants/xiao_c6> + +[env:Xiao_C6_Repeater] +extends = Xiao_C6 +build_src_filter = ${Xiao_C6.build_src_filter} + +<../examples/simple_repeater/main.cpp> +build_flags = + ${Xiao_C6.build_flags} + -D ADVERT_NAME='"Xiao C6 Repeater"' + -D ADVERT_LAT=0.0 + -D ADVERT_LON=0.0 + -D ADMIN_PASSWORD='"password"' + -D MAX_NEIGHBOURS=8 +; -D MESH_PACKET_LOGGING=1 +; -D MESH_DEBUG=1 +lib_deps = + ${Xiao_C6.lib_deps} +; ${esp32_ota.lib_deps} + +[env:Xiao_C6_companion_radio_ble] +extends = Xiao_C6 +build_flags = ${Xiao_C6.build_flags} + -D MAX_CONTACTS=100 + -D MAX_GROUP_CHANNELS=8 + -D BLE_PIN_CODE=123456 + -D BLE_DEBUG_LOGGING=1 + -D OFFLINE_QUEUE_SIZE=256 +; -D ENABLE_PRIVATE_KEY_IMPORT=1 +; -D ENABLE_PRIVATE_KEY_EXPORT=1 +; -D MESH_PACKET_LOGGING=1 +; -D MESH_DEBUG=1 +build_src_filter = ${Xiao_C6.build_src_filter} + + + - + +<../examples/companion_radio> +lib_deps = + ${Xiao_C6.lib_deps} + densaugeo/base64 @ ~1.4.0 diff --git a/variants/xiao_c6/target.cpp b/variants/xiao_c6/target.cpp new file mode 100644 index 00000000..1e60dc32 --- /dev/null +++ b/variants/xiao_c6/target.cpp @@ -0,0 +1,82 @@ +#include +#include "target.h" + +ESP32Board board; + +#if defined(P_LORA_SCLK) + static SPIClass spi(0); + RADIO_CLASS radio = new Module(P_LORA_NSS, P_LORA_DIO_1, P_LORA_RESET, P_LORA_BUSY, spi); +#else + RADIO_CLASS radio = new Module(P_LORA_NSS, P_LORA_DIO_1, P_LORA_RESET, P_LORA_BUSY); +#endif + +WRAPPER_CLASS radio_driver(radio, board); + +ESP32RTCClock fallback_clock; +AutoDiscoverRTCClock rtc_clock(fallback_clock); +SensorManager sensors; + +#ifndef LORA_CR + #define LORA_CR 5 +#endif + +bool radio_init() { + fallback_clock.begin(); + rtc_clock.begin(Wire); + +#ifdef SX126X_DIO3_TCXO_VOLTAGE + float tcxo = SX126X_DIO3_TCXO_VOLTAGE; +#else + float tcxo = 1.6f; +#endif + +#if defined(P_LORA_SCLK) + spi.begin(P_LORA_SCLK, P_LORA_MISO, P_LORA_MOSI); +#endif + int status = radio.begin(LORA_FREQ, LORA_BW, LORA_SF, LORA_CR, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); + if (status != RADIOLIB_ERR_NONE) { + Serial.print("ERROR: radio init failed: "); + Serial.println(status); + return false; // fail + } + + radio.setCRC(1); + +#if defined(SX126X_RXEN) && defined(SX126X_TXEN) + radio.setRfSwitchPins(SX126X_RXEN, SX126X_TXEN); +#endif + +#ifdef SX126X_CURRENT_LIMIT + radio.setCurrentLimit(SX126X_CURRENT_LIMIT); +#endif + +#ifdef SX126X_DIO2_AS_RF_SWITCH + radio.setDio2AsRfSwitch(SX126X_DIO2_AS_RF_SWITCH); +#endif + +#ifdef SX126X_RX_BOOSTED_GAIN + radio.setRxBoostedGainMode(SX126X_RX_BOOSTED_GAIN); +#endif + + return true; // success +} + +uint32_t radio_get_rng_seed() { + return radio.random(0x7FFFFFFF); +} + +void radio_set_params(float freq, float bw, uint8_t sf, uint8_t cr) { + radio.setFrequency(freq); + radio.setSpreadingFactor(sf); + radio.setBandwidth(bw); + radio.setCodingRate(cr); +} + +void radio_set_tx_power(uint8_t dbm) { + radio.setOutputPower(dbm); +} + +mesh::LocalIdentity radio_new_identity() { + RadioNoiseListener rng(radio); + return mesh::LocalIdentity(&rng); // create new random identity +} diff --git a/variants/xiao_c6/target.h b/variants/xiao_c6/target.h new file mode 100644 index 00000000..eef923ab --- /dev/null +++ b/variants/xiao_c6/target.h @@ -0,0 +1,20 @@ +#pragma once + +#define RADIOLIB_STATIC_ONLY 1 +#include +#include +#include +#include +#include +#include + +extern ESP32Board board; +extern WRAPPER_CLASS radio_driver; +extern AutoDiscoverRTCClock rtc_clock; +extern SensorManager sensors; + +bool radio_init(); +uint32_t radio_get_rng_seed(); +void radio_set_params(float freq, float bw, uint8_t sf, uint8_t cr); +void radio_set_tx_power(uint8_t dbm); +mesh::LocalIdentity radio_new_identity(); From 725ee477ff29fd30295e276b2eb51d27dd6e29a1 Mon Sep 17 00:00:00 2001 From: Florent de Lamotte Date: Thu, 19 Jun 2025 15:49:30 +0200 Subject: [PATCH 02/13] xiao_c6: apply sx1262 init refactoring --- variants/xiao_c6/platformio.ini | 5 ++--- variants/xiao_c6/target.cpp | 35 +++------------------------------ 2 files changed, 5 insertions(+), 35 deletions(-) diff --git a/variants/xiao_c6/platformio.ini b/variants/xiao_c6/platformio.ini index 6dab57d9..bc1c789b 100644 --- a/variants/xiao_c6/platformio.ini +++ b/variants/xiao_c6/platformio.ini @@ -18,7 +18,6 @@ build_flags = -D PIN_BOARD_SDA=16 -D PIN_BOARD_SCL=17 -D SX126X_RXEN=23 -; -D SX126X_TXEN=14 -D SX126X_DIO2_AS_RF_SWITCH=true -D SX126X_DIO3_TCXO_VOLTAGE=1.8 -D SX126X_CURRENT_LIMIT=140 @@ -55,8 +54,8 @@ build_flags = ${Xiao_C6.build_flags} -D BLE_PIN_CODE=123456 -D BLE_DEBUG_LOGGING=1 -D OFFLINE_QUEUE_SIZE=256 -; -D ENABLE_PRIVATE_KEY_IMPORT=1 -; -D ENABLE_PRIVATE_KEY_EXPORT=1 + -D ENABLE_PRIVATE_KEY_IMPORT=1 + -D ENABLE_PRIVATE_KEY_EXPORT=1 ; -D MESH_PACKET_LOGGING=1 ; -D MESH_DEBUG=1 build_src_filter = ${Xiao_C6.build_src_filter} diff --git a/variants/xiao_c6/target.cpp b/variants/xiao_c6/target.cpp index 1e60dc32..7791b588 100644 --- a/variants/xiao_c6/target.cpp +++ b/variants/xiao_c6/target.cpp @@ -24,41 +24,12 @@ bool radio_init() { fallback_clock.begin(); rtc_clock.begin(Wire); -#ifdef SX126X_DIO3_TCXO_VOLTAGE - float tcxo = SX126X_DIO3_TCXO_VOLTAGE; -#else - float tcxo = 1.6f; -#endif - #if defined(P_LORA_SCLK) spi.begin(P_LORA_SCLK, P_LORA_MISO, P_LORA_MOSI); + return radio.std_init(&spi); +#else + return radio.std_init(); #endif - int status = radio.begin(LORA_FREQ, LORA_BW, LORA_SF, LORA_CR, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); - if (status != RADIOLIB_ERR_NONE) { - Serial.print("ERROR: radio init failed: "); - Serial.println(status); - return false; // fail - } - - radio.setCRC(1); - -#if defined(SX126X_RXEN) && defined(SX126X_TXEN) - radio.setRfSwitchPins(SX126X_RXEN, SX126X_TXEN); -#endif - -#ifdef SX126X_CURRENT_LIMIT - radio.setCurrentLimit(SX126X_CURRENT_LIMIT); -#endif - -#ifdef SX126X_DIO2_AS_RF_SWITCH - radio.setDio2AsRfSwitch(SX126X_DIO2_AS_RF_SWITCH); -#endif - -#ifdef SX126X_RX_BOOSTED_GAIN - radio.setRxBoostedGainMode(SX126X_RX_BOOSTED_GAIN); -#endif - - return true; // success } uint32_t radio_get_rng_seed() { From 4579aa25d7e37063ebd7a95e149a270b85c693ec Mon Sep 17 00:00:00 2001 From: Florent de Lamotte Date: Fri, 20 Jun 2025 09:51:35 +0200 Subject: [PATCH 03/13] xiao_c6: fallback for LORA_CR is set in std_init --- variants/xiao_c6/target.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/variants/xiao_c6/target.cpp b/variants/xiao_c6/target.cpp index 7791b588..caca57bc 100644 --- a/variants/xiao_c6/target.cpp +++ b/variants/xiao_c6/target.cpp @@ -16,10 +16,6 @@ ESP32RTCClock fallback_clock; AutoDiscoverRTCClock rtc_clock(fallback_clock); SensorManager sensors; -#ifndef LORA_CR - #define LORA_CR 5 -#endif - bool radio_init() { fallback_clock.begin(); rtc_clock.begin(Wire); From dbee0d8b8e2efaa28fae8eb5f31646661e3db229 Mon Sep 17 00:00:00 2001 From: Rob Loranger Date: Fri, 20 Jun 2025 08:25:19 -0700 Subject: [PATCH 04/13] update ADC multipler to fix voltage reading --- src/helpers/HeltecV3Board.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/helpers/HeltecV3Board.h b/src/helpers/HeltecV3Board.h index 988e66d9..57015a04 100644 --- a/src/helpers/HeltecV3Board.h +++ b/src/helpers/HeltecV3Board.h @@ -99,7 +99,7 @@ public: digitalWrite(PIN_ADC_CTRL, !adc_active_state); - return (5.2 * (3.3 / 1024.0) * raw) * 1000; + return (5.42 * (3.3 / 1024.0) * raw) * 1000; } const char* getManufacturerName() const override { From f30698eacb4f5585c585b650d836bc258291241e Mon Sep 17 00:00:00 2001 From: Rob Loranger Date: Fri, 20 Jun 2025 08:40:06 -0700 Subject: [PATCH 05/13] add time output to both clock sync and time cli --- src/helpers/CommonCLI.cpp | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/helpers/CommonCLI.cpp b/src/helpers/CommonCLI.cpp index 63e2740c..803424ea 100644 --- a/src/helpers/CommonCLI.cpp +++ b/src/helpers/CommonCLI.cpp @@ -144,7 +144,9 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch uint32_t curr = getRTCClock()->getCurrentTime(); if (sender_timestamp > curr) { getRTCClock()->setCurrentTime(sender_timestamp + 1); - strcpy(reply, "OK - clock set"); + uint32_t now = getRTCClock()->getCurrentTime(); + DateTime dt = DateTime(now); + sprintf(reply, "OK - clock set: %02d:%02d - %d/%d/%d UTC", dt.hour(), dt.minute(), dt.day(), dt.month(), dt.year()); } else { strcpy(reply, "ERR: clock cannot go backwards"); } @@ -161,7 +163,9 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch uint32_t curr = getRTCClock()->getCurrentTime(); if (secs > curr) { getRTCClock()->setCurrentTime(secs); - strcpy(reply, "(OK - clock set!)"); + uint32_t now = getRTCClock()->getCurrentTime(); + DateTime dt = DateTime(now); + sprintf(reply, "OK - clock set: %02d:%02d - %d/%d/%d UTC", dt.hour(), dt.minute(), dt.day(), dt.month(), dt.year()); } else { strcpy(reply, "(ERR: clock cannot go backwards)"); } From e5ecf29d0c1cad64acff58ad3a03d8e8f91ea2f1 Mon Sep 17 00:00:00 2001 From: Rob Loranger Date: Fri, 20 Jun 2025 09:22:49 -0700 Subject: [PATCH 06/13] return range with advert interval set error updates both local and flood advert preference setting errors to include the allowable range and time units --- src/helpers/CommonCLI.cpp | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/src/helpers/CommonCLI.cpp b/src/helpers/CommonCLI.cpp index 63e2740c..5b1e439c 100644 --- a/src/helpers/CommonCLI.cpp +++ b/src/helpers/CommonCLI.cpp @@ -245,10 +245,8 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch strcpy(reply, "OK"); } else if (memcmp(config, "flood.advert.interval ", 22) == 0) { int hours = _atoi(&config[22]); - if (hours > 0 && hours < 3) { - sprintf(reply, "Error: min is 3 hours"); - } else if (hours > 48) { - strcpy(reply, "Error: max is 48 hours"); + if ((hours > 0 && hours < 3) || (hours > 48)) { + strcpy(reply, "Error: interval range is 3-48 hours"); } else { _prefs->flood_advert_interval = (uint8_t)(hours); _callbacks->updateFloodAdvertTimer(); @@ -257,10 +255,8 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch } } else if (memcmp(config, "advert.interval ", 16) == 0) { int mins = _atoi(&config[16]); - if (mins > 0 && mins < MIN_LOCAL_ADVERT_INTERVAL) { - sprintf(reply, "Error: min is %d mins", MIN_LOCAL_ADVERT_INTERVAL); - } else if (mins > 240) { - strcpy(reply, "Error: max is 240 mins"); + if ((mins > 0 && mins < MIN_LOCAL_ADVERT_INTERVAL) || (mins > 240)) { + sprintf(reply, "Error: interval range is %d-240 minutes", MIN_LOCAL_ADVERT_INTERVAL); } else { _prefs->advert_interval = (uint8_t)(mins / 2); _callbacks->updateAdvertTimer(); From 52a579a366dd327d404e2987c5cb0b56966408b1 Mon Sep 17 00:00:00 2001 From: Rob Loranger Date: Fri, 20 Jun 2025 10:31:39 -0700 Subject: [PATCH 07/13] fix Heltec v2 getBattMilliVolts --- src/helpers/HeltecV2Board.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/helpers/HeltecV2Board.h b/src/helpers/HeltecV2Board.h index 32545b61..5bf78778 100644 --- a/src/helpers/HeltecV2Board.h +++ b/src/helpers/HeltecV2Board.h @@ -68,7 +68,7 @@ public: } raw = raw / 8; - return (1.883 * (2 / 1024.0) * raw) * 1000; + return (1.98 * (2 / 1024.0) * raw) * 1000; } const char* getManufacturerName() const override { From 9eff882e18e0ce9e8395ab7dab89823076b8bbdd Mon Sep 17 00:00:00 2001 From: taco Date: Sat, 21 Jun 2025 09:52:39 +1000 Subject: [PATCH 08/13] refactor: RAK4631 with CustomSX1262::std_init() --- variants/rak4631/target.cpp | 34 +--------------------------------- 1 file changed, 1 insertion(+), 33 deletions(-) diff --git a/variants/rak4631/target.cpp b/variants/rak4631/target.cpp index daadd044..ede755e2 100644 --- a/variants/rak4631/target.cpp +++ b/variants/rak4631/target.cpp @@ -23,10 +23,6 @@ RAK4631SensorManager sensors; DISPLAY_CLASS display; #endif -#ifndef LORA_CR - #define LORA_CR 5 -#endif - #ifdef MESH_DEBUG uint32_t deviceOnline = 0x00; void scanDevices(TwoWire *w) @@ -75,35 +71,7 @@ void scanDevices(TwoWire *w) bool radio_init() { rtc_clock.begin(Wire); - -#ifdef SX126X_DIO3_TCXO_VOLTAGE - float tcxo = SX126X_DIO3_TCXO_VOLTAGE; -#else - float tcxo = 1.6f; -#endif - - SPI.setPins(P_LORA_MISO, P_LORA_SCLK, P_LORA_MOSI); - SPI.begin(); - int status = radio.begin(LORA_FREQ, LORA_BW, LORA_SF, LORA_CR, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); - if (status != RADIOLIB_ERR_NONE) { - Serial.print("ERROR: radio init failed: "); - Serial.println(status); - return false; // fail - } - - radio.setCRC(1); - -#ifdef SX126X_CURRENT_LIMIT - radio.setCurrentLimit(SX126X_CURRENT_LIMIT); -#endif -#ifdef SX126X_DIO2_AS_RF_SWITCH - radio.setDio2AsRfSwitch(SX126X_DIO2_AS_RF_SWITCH); -#endif -#ifdef SX126X_RX_BOOSTED_GAIN - radio.setRxBoostedGainMode(SX126X_RX_BOOSTED_GAIN); -#endif - - return true; // success + return radio.std_init(&SPI); } uint32_t radio_get_rng_seed() { From 83842e4b25adb28c30c5109d056a59eea716bff8 Mon Sep 17 00:00:00 2001 From: taco Date: Sat, 21 Jun 2025 10:09:28 +1000 Subject: [PATCH 09/13] fix: EnvironmentSensorManager.cpp: don't update location if GPS is turned off. previously the location would always snap to the last heard GPS location after GPS had been on. --- src/helpers/sensors/EnvironmentSensorManager.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/helpers/sensors/EnvironmentSensorManager.cpp b/src/helpers/sensors/EnvironmentSensorManager.cpp index dda1fd55..ed20b8a4 100644 --- a/src/helpers/sensors/EnvironmentSensorManager.cpp +++ b/src/helpers/sensors/EnvironmentSensorManager.cpp @@ -220,7 +220,7 @@ void EnvironmentSensorManager::loop() { _location->loop(); if (millis() > next_gps_update) { - if (_location->isValid()) { + if (gps_active && _location->isValid()) { node_lat = ((double)_location->getLatitude())/1000000.; node_lon = ((double)_location->getLongitude())/1000000.; MESH_DEBUG_PRINTLN("lat %f lon %f", node_lat, node_lon); From 14ff7bfbcdae80398eae418895512a6be1fff293 Mon Sep 17 00:00:00 2001 From: taco Date: Sat, 21 Jun 2025 11:03:25 +1000 Subject: [PATCH 10/13] added std_init to CustomLLCC68.h --- src/helpers/CustomLLCC68.h | 70 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) diff --git a/src/helpers/CustomLLCC68.h b/src/helpers/CustomLLCC68.h index db037639..52b37a0e 100644 --- a/src/helpers/CustomLLCC68.h +++ b/src/helpers/CustomLLCC68.h @@ -9,6 +9,76 @@ class CustomLLCC68 : public LLCC68 { public: CustomLLCC68(Module *mod) : LLCC68(mod) { } + #ifdef RP2040_PLATFORM + bool std_init(SPIClassRP2040* spi = NULL) + #else + bool std_init(SPIClass* spi = NULL) + #endif + { + #ifdef SX126X_DIO3_TCXO_VOLTAGE + float tcxo = SX126X_DIO3_TCXO_VOLTAGE; + #else + float tcxo = 1.6f; + #endif + + #ifdef LORA_CR + uint8_t cr = LORA_CR; + #else + uint8_t cr = 5; + #endif + + #if defined(P_LORA_SCLK) + #ifdef NRF52_PLATFORM + if (spi) { spi->setPins(P_LORA_MISO, P_LORA_SCLK, P_LORA_MOSI); spi->begin(); } + #elif defined(RP2040_PLATFORM) + if (spi) { + spi->setMISO(P_LORA_MISO); + //spi->setCS(P_LORA_NSS); // Setting CS results in freeze + spi->setSCK(P_LORA_SCLK); + spi->setMOSI(P_LORA_MOSI); + spi->begin(); + } + #else + if (spi) spi->begin(P_LORA_SCLK, P_LORA_MISO, P_LORA_MOSI); + #endif + #endif + int status = begin(LORA_FREQ, LORA_BW, LORA_SF, cr, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); + // if radio init fails with -707/-706, try again with tcxo voltage set to 0.0f + if (status == RADIOLIB_ERR_SPI_CMD_FAILED || status == RADIOLIB_ERR_SPI_CMD_INVALID) { + #define SX126X_DIO3_TCXO_VOLTAGE (0.0f); + tcxo = SX126X_DIO3_TCXO_VOLTAGE; + status = begin(LORA_FREQ, LORA_BW, LORA_SF, cr, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); + } + if (status != RADIOLIB_ERR_NONE) { + Serial.print("ERROR: radio init failed: "); + Serial.println(status); + return false; // fail + } + + setCRC(1); + + #ifdef SX126X_CURRENT_LIMIT + setCurrentLimit(SX126X_CURRENT_LIMIT); + #endif + #ifdef SX126X_DIO2_AS_RF_SWITCH + setDio2AsRfSwitch(SX126X_DIO2_AS_RF_SWITCH); + #endif + #ifdef SX126X_RX_BOOSTED_GAIN + setRxBoostedGainMode(SX126X_RX_BOOSTED_GAIN); + #endif + #if defined(SX126X_RXEN) || defined(SX126X_TXEN) + #ifndef SX1262X_RXEN + #define SX1262X_RXEN RADIOLIB_NC + #endif + #ifndef SX1262X_TXEN + #define SX1262X_TXEN RADIOLIB_NC + #endif + setRfSwitchPins(SX126X_RXEN, SX126X_TXEN); + #endif + + return true; // success + } + bool isReceiving() { uint16_t irq = getIrqFlags(); bool detected = (irq & SX126X_IRQ_HEADER_VALID) || (irq & SX126X_IRQ_PREAMBLE_DETECTED); From 4d2b176ccc829ea606a72dcfbb73df14e9ac78fd Mon Sep 17 00:00:00 2001 From: taco Date: Sat, 21 Jun 2025 13:04:39 +1000 Subject: [PATCH 11/13] feature: GPS support on HeltecV3 GPS support via EnvironmentSensorManager. Connect GPS RX to pin 45, TX to pin 46. Note that while you can disable using the GPS there is no way to power down the GPS without using a mosfet and adjusting PIN_GPS_EN. --- variants/heltec_v3/platformio.ini | 7 ++++++- variants/heltec_v3/target.cpp | 9 ++++++++- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/variants/heltec_v3/platformio.ini b/variants/heltec_v3/platformio.ini index e8818fdd..8f9b1a27 100644 --- a/variants/heltec_v3/platformio.ini +++ b/variants/heltec_v3/platformio.ini @@ -21,6 +21,10 @@ build_flags = -D ENV_INCLUDE_BME280=1 -D ENV_INCLUDE_INA3221=1 -D ENV_INCLUDE_INA219=1 + -D ENV_INCLUDE_GPS=1 + -D PIN_GPS_RX=45 + -D PIN_GPS_TX=46 + -D PIN_GPS_EN=-1 build_src_filter = ${esp32_base.build_src_filter} +<../variants/heltec_v3> + @@ -30,7 +34,8 @@ lib_deps = adafruit/Adafruit INA3221 Library @ ^1.0.1 adafruit/Adafruit INA219 @ ^1.2.3 adafruit/Adafruit AHTX0 @ ^2.0.5 - adafruit/Adafruit BME280 Library @ ^2.3.0 + adafruit/Adafruit BME280 Library @ ^2.3.0 + stevemarple/MicroNMEA @ ^2.0.6 [env:Heltec_v3_repeater] extends = Heltec_lora32_v3 diff --git a/variants/heltec_v3/target.cpp b/variants/heltec_v3/target.cpp index de8e0f92..4ae06be3 100644 --- a/variants/heltec_v3/target.cpp +++ b/variants/heltec_v3/target.cpp @@ -14,7 +14,14 @@ WRAPPER_CLASS radio_driver(radio, board); ESP32RTCClock fallback_clock; AutoDiscoverRTCClock rtc_clock(fallback_clock); -EnvironmentSensorManager sensors; + +#if ENV_INCLUDE_GPS + #include + MicroNMEALocationProvider nmea = MicroNMEALocationProvider(Serial1); + EnvironmentSensorManager sensors = EnvironmentSensorManager(nmea); +#else + EnvironmentSensorManager sensors; +#endif #ifdef DISPLAY_CLASS DISPLAY_CLASS display; From 205624824a5d09905aae88bc89e1f2bb7b2f303a Mon Sep 17 00:00:00 2001 From: Scott Powell Date: Sat, 21 Jun 2025 15:27:58 +1000 Subject: [PATCH 12/13] * added std_init() to CustomSX1268 --- src/helpers/CustomSX1268.h | 70 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) diff --git a/src/helpers/CustomSX1268.h b/src/helpers/CustomSX1268.h index a8180fc4..eb2d4f12 100644 --- a/src/helpers/CustomSX1268.h +++ b/src/helpers/CustomSX1268.h @@ -9,6 +9,76 @@ class CustomSX1268 : public SX1268 { public: CustomSX1268(Module *mod) : SX1268(mod) { } + #ifdef RP2040_PLATFORM + bool std_init(SPIClassRP2040* spi = NULL) + #else + bool std_init(SPIClass* spi = NULL) + #endif + { + #ifdef SX126X_DIO3_TCXO_VOLTAGE + float tcxo = SX126X_DIO3_TCXO_VOLTAGE; + #else + float tcxo = 1.6f; + #endif + + #ifdef LORA_CR + uint8_t cr = LORA_CR; + #else + uint8_t cr = 5; + #endif + + #if defined(P_LORA_SCLK) + #ifdef NRF52_PLATFORM + if (spi) { spi->setPins(P_LORA_MISO, P_LORA_SCLK, P_LORA_MOSI); spi->begin(); } + #elif defined(RP2040_PLATFORM) + if (spi) { + spi->setMISO(P_LORA_MISO); + //spi->setCS(P_LORA_NSS); // Setting CS results in freeze + spi->setSCK(P_LORA_SCLK); + spi->setMOSI(P_LORA_MOSI); + spi->begin(); + } + #else + if (spi) spi->begin(P_LORA_SCLK, P_LORA_MISO, P_LORA_MOSI); + #endif + #endif + int status = begin(LORA_FREQ, LORA_BW, LORA_SF, cr, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); + // if radio init fails with -707/-706, try again with tcxo voltage set to 0.0f + if (status == RADIOLIB_ERR_SPI_CMD_FAILED || status == RADIOLIB_ERR_SPI_CMD_INVALID) { + #define SX126X_DIO3_TCXO_VOLTAGE (0.0f); + tcxo = SX126X_DIO3_TCXO_VOLTAGE; + status = begin(LORA_FREQ, LORA_BW, LORA_SF, cr, RADIOLIB_SX126X_SYNC_WORD_PRIVATE, LORA_TX_POWER, 8, tcxo); + } + if (status != RADIOLIB_ERR_NONE) { + Serial.print("ERROR: radio init failed: "); + Serial.println(status); + return false; // fail + } + + setCRC(1); + + #ifdef SX126X_CURRENT_LIMIT + setCurrentLimit(SX126X_CURRENT_LIMIT); + #endif + #ifdef SX126X_DIO2_AS_RF_SWITCH + setDio2AsRfSwitch(SX126X_DIO2_AS_RF_SWITCH); + #endif + #ifdef SX126X_RX_BOOSTED_GAIN + setRxBoostedGainMode(SX126X_RX_BOOSTED_GAIN); + #endif + #if defined(SX126X_RXEN) || defined(SX126X_TXEN) + #ifndef SX1262X_RXEN + #define SX1262X_RXEN RADIOLIB_NC + #endif + #ifndef SX1262X_TXEN + #define SX1262X_TXEN RADIOLIB_NC + #endif + setRfSwitchPins(SX126X_RXEN, SX126X_TXEN); + #endif + + return true; // success + } + bool isReceiving() { uint16_t irq = getIrqFlags(); bool detected = (irq & SX126X_IRQ_HEADER_VALID) || (irq & SX126X_IRQ_PREAMBLE_DETECTED); From 1295c4633b8049b94a6389a7fe173ef069b6ba0c Mon Sep 17 00:00:00 2001 From: Scott Powell Date: Sat, 21 Jun 2025 20:48:28 +1000 Subject: [PATCH 13/13] * companion: minor refactor of who should invoke UITask::loop() --- examples/companion_radio/MyMesh.cpp | 1 - examples/companion_radio/main.cpp | 3 +++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/examples/companion_radio/MyMesh.cpp b/examples/companion_radio/MyMesh.cpp index 034f0206..d996d752 100644 --- a/examples/companion_radio/MyMesh.cpp +++ b/examples/companion_radio/MyMesh.cpp @@ -1474,7 +1474,6 @@ void MyMesh::loop() { #ifdef DISPLAY_CLASS ui_task.setHasConnection(_serial->isConnected()); - ui_task.loop(); #endif } diff --git a/examples/companion_radio/main.cpp b/examples/companion_radio/main.cpp index 098baf99..34c30498 100644 --- a/examples/companion_radio/main.cpp +++ b/examples/companion_radio/main.cpp @@ -193,4 +193,7 @@ void setup() { void loop() { the_mesh.loop(); sensors.loop(); +#ifdef DISPLAY_CLASS + ui_task.loop(); +#endif }