From 9c9a2ba2db593b203eb66a428fd21f9b26a7d24e Mon Sep 17 00:00:00 2001 From: Daniel Novak Date: Mon, 23 Feb 2026 21:40:17 +0100 Subject: [PATCH 01/12] Fix stack buffer overflow in MACThenDecrypt via block-alignment check Add validation that ciphertext length is a multiple of CIPHER_BLOCK_SIZE before calling decrypt(). The decrypt() function processes data in 16-byte AES blocks, rounding up non-aligned input, which can write up to 8 bytes past the caller's stack buffer. This can be triggered by crafted packets that pass the 2-byte HMAC check (1-in-65536 chance per attempt), enabling a persistent denial-of-service attack against repeaters and other nodes. --- src/Utils.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/Utils.cpp b/src/Utils.cpp index 186c8720a..573c4398f 100644 --- a/src/Utils.cpp +++ b/src/Utils.cpp @@ -82,7 +82,9 @@ int Utils::MACThenDecrypt(const uint8_t* shared_secret, uint8_t* dest, const uin sha.finalizeHMAC(shared_secret, PUB_KEY_SIZE, hmac, CIPHER_MAC_SIZE); } if (memcmp(hmac, src, CIPHER_MAC_SIZE) == 0) { - return decrypt(shared_secret, dest, src + CIPHER_MAC_SIZE, src_len - CIPHER_MAC_SIZE); + int enc_len = src_len - CIPHER_MAC_SIZE; + if (enc_len % CIPHER_BLOCK_SIZE != 0) return 0; // reject non-block-aligned ciphertext + return decrypt(shared_secret, dest, src + CIPHER_MAC_SIZE, enc_len); } return 0; // invalid HMAC } From b74ba545308f077120cf329f2023f171e2e2f9fa Mon Sep 17 00:00:00 2001 From: Daniel Novak Date: Thu, 26 Feb 2026 09:08:06 +0100 Subject: [PATCH 02/12] Move block-alignment check before HMAC computation Address review feedback: - Move the alignment check before the HMAC-SHA256 computation to skip expensive crypto on obviously malformed packets - Update MACThenDecrypt header comment to document block-alignment as a reason for returning zero --- src/Utils.cpp | 7 ++++--- src/Utils.h | 2 +- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/Utils.cpp b/src/Utils.cpp index 573c4398f..a70d4a70c 100644 --- a/src/Utils.cpp +++ b/src/Utils.cpp @@ -74,16 +74,17 @@ int Utils::encryptThenMAC(const uint8_t* shared_secret, uint8_t* dest, const uin int Utils::MACThenDecrypt(const uint8_t* shared_secret, uint8_t* dest, const uint8_t* src, int src_len) { if (src_len <= CIPHER_MAC_SIZE) return 0; // invalid src bytes + int enc_len = src_len - CIPHER_MAC_SIZE; + if (enc_len % CIPHER_BLOCK_SIZE != 0) return 0; // reject non-block-aligned ciphertext + uint8_t hmac[CIPHER_MAC_SIZE]; { SHA256 sha; sha.resetHMAC(shared_secret, PUB_KEY_SIZE); - sha.update(src + CIPHER_MAC_SIZE, src_len - CIPHER_MAC_SIZE); + sha.update(src + CIPHER_MAC_SIZE, enc_len); sha.finalizeHMAC(shared_secret, PUB_KEY_SIZE, hmac, CIPHER_MAC_SIZE); } if (memcmp(hmac, src, CIPHER_MAC_SIZE) == 0) { - int enc_len = src_len - CIPHER_MAC_SIZE; - if (enc_len % CIPHER_BLOCK_SIZE != 0) return 0; // reject non-block-aligned ciphertext return decrypt(shared_secret, dest, src + CIPHER_MAC_SIZE, enc_len); } return 0; // invalid HMAC diff --git a/src/Utils.h b/src/Utils.h index 5736b8747..9997fe3cb 100644 --- a/src/Utils.h +++ b/src/Utils.h @@ -50,7 +50,7 @@ public: /** * \brief checks the MAC (in leading bytes of 'src'), then if valid, decrypts remaining bytes in src. - * \returns zero if MAC is invalid, otherwise the length of decrypted bytes in 'dest' + * \returns zero if MAC is invalid or ciphertext is not block-aligned, otherwise the length of decrypted bytes in 'dest' */ static int MACThenDecrypt(const uint8_t* shared_secret, uint8_t* dest, const uint8_t* src, int src_len); From fc71d34509edf593dfd12622d8c0c8ac2394107d Mon Sep 17 00:00:00 2001 From: Emily Kerst Date: Sun, 3 May 2026 22:40:01 +0200 Subject: [PATCH 03/12] Added USB Companion variant for LilyGo T-Echo Lite Co-authored-by: Natalie Kagelmacher Mentored-by: Natalie Kagelmacher Tested-by: Emily Kerst --- variants/lilygo_techo_lite/platformio.ini | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/variants/lilygo_techo_lite/platformio.ini b/variants/lilygo_techo_lite/platformio.ini index 4b5edf691..db629b363 100644 --- a/variants/lilygo_techo_lite/platformio.ini +++ b/variants/lilygo_techo_lite/platformio.ini @@ -190,3 +190,24 @@ lib_deps = extends = LilyGo_T-Echo-Lite build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} +<../examples/kiss_modem/> +[env:LilyGo_T-Echo-Lite_companion_radio_usb] +extends = LilyGo_T-Echo-Lite +board_build.ldscript = boards/nrf52840_s140_v6_extrafs.ld +board_upload.maximum_size = 712704 +build_flags = + ${LilyGo_T-Echo-Lite.build_flags} + -I src/helpers/ui + -I examples/companion_radio/ui-new + -D MAX_CONTACTS=350 + -D MAX_GROUP_CHANNELS=40 + -D OFFLINE_QUEUE_SIZE=256 + -D UI_RECENT_LIST_SIZE=9 + -D UI_SENSORS_PAGE=1 + -D AUTO_SHUTDOWN_MILLIVOLTS=3300 +; -D QSPIFLASH=1 +build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} + +<../examples/companion_radio/*.cpp> + +<../examples/companion_radio/ui-new/*.cpp> +lib_deps = + ${LilyGo_T-Echo-Lite.lib_deps} + densaugeo/base64 @ ~1.4.0 From 356af9fdc8ff60a2cd60432b6aae2162f6ed07a0 Mon Sep 17 00:00:00 2001 From: Emily Kerst Date: Fri, 15 May 2026 20:20:27 +0200 Subject: [PATCH 04/12] chore: reformat T-Echo Lite platformio.ini to keep normal and non-shell variants together --- variants/lilygo_techo_lite/platformio.ini | 52 +++++++++++------------ 1 file changed, 26 insertions(+), 26 deletions(-) diff --git a/variants/lilygo_techo_lite/platformio.ini b/variants/lilygo_techo_lite/platformio.ini index db629b363..ed46adcd6 100644 --- a/variants/lilygo_techo_lite/platformio.ini +++ b/variants/lilygo_techo_lite/platformio.ini @@ -98,6 +98,32 @@ lib_deps = ${LilyGo_T-Echo-Lite.lib_deps} densaugeo/base64 @ ~1.4.0 +[env:LilyGo_T-Echo-Lite_kiss_modem] +extends = LilyGo_T-Echo-Lite +build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} + +<../examples/kiss_modem/> +[env:LilyGo_T-Echo-Lite_companion_radio_usb] +extends = LilyGo_T-Echo-Lite +board_build.ldscript = boards/nrf52840_s140_v6_extrafs.ld +board_upload.maximum_size = 712704 +build_flags = + ${LilyGo_T-Echo-Lite.build_flags} + -I src/helpers/ui + -I examples/companion_radio/ui-new + -D MAX_CONTACTS=350 + -D MAX_GROUP_CHANNELS=40 + -D OFFLINE_QUEUE_SIZE=256 + -D UI_RECENT_LIST_SIZE=9 + -D UI_SENSORS_PAGE=1 + -D AUTO_SHUTDOWN_MILLIVOLTS=3300 +; -D QSPIFLASH=1 +build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} + +<../examples/companion_radio/*.cpp> + +<../examples/companion_radio/ui-new/*.cpp> +lib_deps = + ${LilyGo_T-Echo-Lite.lib_deps} + densaugeo/base64 @ ~1.4.0 + [env:LilyGo_T-Echo-Lite_non_shell_companion_radio_ble] extends = LilyGo_T-Echo-Lite upload_protocol = nrfutil @@ -185,29 +211,3 @@ build_src_filter = ${nrf52_base.build_src_filter} lib_deps = ${LilyGo_T-Echo-Lite.lib_deps} densaugeo/base64 @ ~1.4.0 - -[env:LilyGo_T-Echo-Lite_kiss_modem] -extends = LilyGo_T-Echo-Lite -build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} - +<../examples/kiss_modem/> -[env:LilyGo_T-Echo-Lite_companion_radio_usb] -extends = LilyGo_T-Echo-Lite -board_build.ldscript = boards/nrf52840_s140_v6_extrafs.ld -board_upload.maximum_size = 712704 -build_flags = - ${LilyGo_T-Echo-Lite.build_flags} - -I src/helpers/ui - -I examples/companion_radio/ui-new - -D MAX_CONTACTS=350 - -D MAX_GROUP_CHANNELS=40 - -D OFFLINE_QUEUE_SIZE=256 - -D UI_RECENT_LIST_SIZE=9 - -D UI_SENSORS_PAGE=1 - -D AUTO_SHUTDOWN_MILLIVOLTS=3300 -; -D QSPIFLASH=1 -build_src_filter = ${LilyGo_T-Echo-Lite.build_src_filter} - +<../examples/companion_radio/*.cpp> - +<../examples/companion_radio/ui-new/*.cpp> -lib_deps = - ${LilyGo_T-Echo-Lite.lib_deps} - densaugeo/base64 @ ~1.4.0 From 35142a8896733f6815b6a43bea2367d570059e7c Mon Sep 17 00:00:00 2001 From: Wessel Nieboer Date: Mon, 2 Mar 2026 10:11:51 +0100 Subject: [PATCH 05/12] Fix 1970 date after crash/watchdog/brownout reset on ESP32 Currently, time is only set to ~2024 when it powers on cleanly. When time is lost, this results in time dropping to 1970. Save time as backup to RTC slow memory. Should fix time staying accurate during brownouts etc. --- src/helpers/ESP32Board.h | 31 ++++++++++++++++++++++++++----- 1 file changed, 26 insertions(+), 5 deletions(-) diff --git a/src/helpers/ESP32Board.h b/src/helpers/ESP32Board.h index 75428bc69..3d1b97f45 100644 --- a/src/helpers/ESP32Board.h +++ b/src/helpers/ESP32Board.h @@ -200,19 +200,30 @@ public: } }; +static RTC_NOINIT_ATTR uint32_t _rtc_backup_time; +static RTC_NOINIT_ATTR uint32_t _rtc_backup_magic; +#define RTC_BACKUP_MAGIC 0xAA55CC33 +#define RTC_TIME_MIN 1772323200 // 1 Mar 2026 + class ESP32RTCClock : public mesh::RTCClock { public: ESP32RTCClock() { } void begin() { esp_reset_reason_t reason = esp_reset_reason(); - if (reason == ESP_RST_POWERON) { - // start with some date/time in the recent past - struct timeval tv; - tv.tv_sec = 1715770351; // 15 May 2024, 8:50pm + if (reason == ESP_RST_DEEPSLEEP) { + return; // ESP-IDF preserves system time across deep sleep + } + // All other resets (power-on, crash, WDT, brownout) lose system time. + // Restore from RTC backup if valid, otherwise use hardcoded seed. + struct timeval tv; + if (_rtc_backup_magic == RTC_BACKUP_MAGIC && _rtc_backup_time > RTC_TIME_MIN) { + tv.tv_sec = _rtc_backup_time; + } else { + tv.tv_sec = 1772323200; // 1 Mar 2026 + } tv.tv_usec = 0; settimeofday(&tv, NULL); } - } uint32_t getCurrentTime() override { time_t _now; time(&_now); @@ -223,6 +234,16 @@ public: tv.tv_sec = time; tv.tv_usec = 0; settimeofday(&tv, NULL); + _rtc_backup_time = time; + _rtc_backup_magic = RTC_BACKUP_MAGIC; + } + void tick() override { + time_t now; + time(&now); + if (now > RTC_TIME_MIN && (uint32_t)now != _rtc_backup_time) { + _rtc_backup_time = (uint32_t)now; + _rtc_backup_magic = RTC_BACKUP_MAGIC; + } } }; From cb6f2f22555826d1392262b1a2c24661b988c3c8 Mon Sep 17 00:00:00 2001 From: Wessel Date: Fri, 5 Jun 2026 19:00:33 +0200 Subject: [PATCH 06/12] Update src/helpers/ESP32Board.h Co-authored-by: Dan McGee --- src/helpers/ESP32Board.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/helpers/ESP32Board.h b/src/helpers/ESP32Board.h index 3d1b97f45..3f95e6923 100644 --- a/src/helpers/ESP32Board.h +++ b/src/helpers/ESP32Board.h @@ -219,7 +219,7 @@ public: if (_rtc_backup_magic == RTC_BACKUP_MAGIC && _rtc_backup_time > RTC_TIME_MIN) { tv.tv_sec = _rtc_backup_time; } else { - tv.tv_sec = 1772323200; // 1 Mar 2026 + tv.tv_sec = RTC_TIME_MIN; } tv.tv_usec = 0; settimeofday(&tv, NULL); From f9e70426ae5eed7782edd9c6b56af86180e0c63c Mon Sep 17 00:00:00 2001 From: Scott Powell Date: Thu, 24 Sep 2026 13:35:27 +1000 Subject: [PATCH 07/12] increased MAX_SEARCH_RESULTS to 24. (was 8) Closes #3243 --- examples/simple_sensor/SensorMesh.h | 2 +- src/helpers/BaseChatMesh.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/examples/simple_sensor/SensorMesh.h b/examples/simple_sensor/SensorMesh.h index 6b7a32fef..8b421081b 100644 --- a/examples/simple_sensor/SensorMesh.h +++ b/examples/simple_sensor/SensorMesh.h @@ -43,7 +43,7 @@ #define FIRMWARE_ROLE "sensor" -#define MAX_SEARCH_RESULTS 8 +#define MAX_SEARCH_RESULTS 24 #define MAX_CONCURRENT_ALERTS 4 class SensorMesh : public mesh::Mesh, public CommonCLICallbacks { diff --git a/src/helpers/BaseChatMesh.h b/src/helpers/BaseChatMesh.h index 0a8fdef4f..835384b74 100644 --- a/src/helpers/BaseChatMesh.h +++ b/src/helpers/BaseChatMesh.h @@ -9,7 +9,7 @@ #include "ContactInfo.h" -#define MAX_SEARCH_RESULTS 8 +#define MAX_SEARCH_RESULTS 24 #define MSG_SEND_FAILED 0 #define MSG_SEND_SENT_FLOOD 1 From d07803bd9bff45a2ba9b6343de81ad1a56edef78 Mon Sep 17 00:00:00 2001 From: Marcel Verdult Date: Sat, 26 Sep 2026 14:07:28 +0200 Subject: [PATCH 08/12] Fix RAK11310 build: add no-op attachDynamicPrefs() --- variants/rak11310/RAK11310Board.h | 3 +++ 1 file changed, 3 insertions(+) diff --git a/variants/rak11310/RAK11310Board.h b/variants/rak11310/RAK11310Board.h index ea0f15e26..5b75ac361 100644 --- a/variants/rak11310/RAK11310Board.h +++ b/variants/rak11310/RAK11310Board.h @@ -2,6 +2,7 @@ #include #include +#include // from https://github.com/RAKWireless/RAK11300-AT-Command-Firmware/blob/9c48409a43620a828d653501d536473200aa33af/RAK11300-AT-Arduino/batt.cpp#L17-L19 #define VBAT_MV_PER_LSB (0.806F) // 3.0V ADC range and 12 - bit ADC resolution = 3300mV / 4096 @@ -46,4 +47,6 @@ public: void reboot() override { rp2040.reboot(); } bool startOTAUpdate(const char *id, char reply[]) override; + + void attachDynamicPrefs(KeyValueStore* prefs) { } // no-op }; From 3fa8dbf4d10e780bec9ec0e5de3b1807e828830e Mon Sep 17 00:00:00 2001 From: taco Date: Tue, 29 Sep 2026 20:10:51 +1000 Subject: [PATCH 09/12] feat: add waitFor() and drain() to LocationProvider to support sending commands to GPS --- src/helpers/sensors/LocationProvider.h | 2 ++ .../sensors/MicroNMEALocationProvider.h | 21 +++++++++++++++++++ 2 files changed, 23 insertions(+) diff --git a/src/helpers/sensors/LocationProvider.h b/src/helpers/sensors/LocationProvider.h index 81d08652e..e11b738b5 100644 --- a/src/helpers/sensors/LocationProvider.h +++ b/src/helpers/sensors/LocationProvider.h @@ -17,6 +17,8 @@ public: virtual bool isValid() = 0; virtual long getTimestamp() = 0; virtual void sendSentence(const char * sentence); + virtual bool waitFor(const char* prefix, uint32_t timeout_ms) { return false; } + virtual void drain() { } virtual void reset() = 0; virtual void begin() = 0; virtual void stop() = 0; diff --git a/src/helpers/sensors/MicroNMEALocationProvider.h b/src/helpers/sensors/MicroNMEALocationProvider.h index b66cb1145..e559ad018 100644 --- a/src/helpers/sensors/MicroNMEALocationProvider.h +++ b/src/helpers/sensors/MicroNMEALocationProvider.h @@ -129,10 +129,31 @@ public : return dt.unixtime(); } + void drain() { while (_gps_serial->available()) _gps_serial->read(); } + + const char* getSentence() const { return nmea.getSentence(); } + void sendSentence(const char *sentence) override { nmea.sendSentence(*_gps_serial, sentence); } + bool waitFor(const char* prefix, uint32_t timeout_ms) { + size_t plen = strlen(prefix); + uint32_t timeout = millis() + timeout_ms; + while ((int32_t)(millis() - timeout) < 0) { + if (_gps_serial->available()) { + char c = _gps_serial->read(); + #ifdef GPS_NMEA_DEBUG + Serial.print(c); + #endif + if (nmea.process(c) && strncmp(nmea.getSentence(), prefix, plen) == 0) return true; + } else { + yield(); + } + } + return false; + } + void loop() override { while (_gps_serial->available()) { From 037e27833b5edc63cd905bb706c07025819114ec Mon Sep 17 00:00:00 2001 From: taco Date: Tue, 29 Sep 2026 20:12:08 +1000 Subject: [PATCH 10/12] feat: add AirohaSleep.h helper for faster fix on AG3335 based GPS --- src/helpers/sensors/AirohaSleep.h | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 src/helpers/sensors/AirohaSleep.h diff --git a/src/helpers/sensors/AirohaSleep.h b/src/helpers/sensors/AirohaSleep.h new file mode 100644 index 000000000..6637d0fbf --- /dev/null +++ b/src/helpers/sensors/AirohaSleep.h @@ -0,0 +1,19 @@ +#pragma once +#include + +// Board must keep the GPS RTC backup pin powered and can cut GPS power once we return. +// Returns true if the command was acked within 3 attempts, otherwise returns false. +static inline bool airohaEnterSleep(LocationProvider* nmea) { + for (uint8_t attempt = 0; attempt < 3; attempt++) { + nmea->drain(); + nmea->sendSentence("$PAIR650,0"); + if (nmea->waitFor("$PAIR001,650,0", 50)) { // wait for the command received signal + #ifdef GPS_NMEA_DEBUG + Serial.printf("Airoha RTC Backup sleep command accepted by GPS after %u attempts\r\n", attempt + 1); + #endif + nmea->waitFor("$PAIR650,0", 50); // give the GPS 50ms grace to signal it is ready for sleep + return true; + } + } + return false; +} \ No newline at end of file From 11755c81996fc8cd76708d2a420aaee920a58b02 Mon Sep 17 00:00:00 2001 From: taco Date: Tue, 29 Sep 2026 20:14:19 +1000 Subject: [PATCH 11/12] MeshTracker X1 GPS: use RTC backup for faster fix --- variants/meshtracker_x1/target.cpp | 38 ++++++++---------------------- 1 file changed, 10 insertions(+), 28 deletions(-) diff --git a/variants/meshtracker_x1/target.cpp b/variants/meshtracker_x1/target.cpp index d6d548b51..5b90d6609 100644 --- a/variants/meshtracker_x1/target.cpp +++ b/variants/meshtracker_x1/target.cpp @@ -1,6 +1,7 @@ #include #include "target.h" #include +#include MeshTrackerX1Board board; @@ -27,46 +28,27 @@ mesh::LocalIdentity radio_new_identity() { void MeshTrackerX1SensorManager::start_gps() { gps_active = true; - // this init sequence comes from seeed examples and deals with all gps pins - pinMode(GPS_EN, OUTPUT); digitalWrite(GPS_EN, HIGH); delay(10); - pinMode(GPS_VRTC_EN, OUTPUT); - digitalWrite(GPS_VRTC_EN, HIGH); - delay(10); - - pinMode(GPS_RESET, OUTPUT); - digitalWrite(GPS_RESET, HIGH); - delay(10); - digitalWrite(GPS_RESET, LOW); - - pinMode(GPS_SLEEP_INT, OUTPUT); - digitalWrite(GPS_SLEEP_INT, HIGH); - pinMode(GPS_RTC_INT, OUTPUT); - digitalWrite(GPS_RTC_INT, LOW); -} - -void MeshTrackerX1SensorManager::sleep_gps() { - gps_active = false; - digitalWrite(GPS_VRTC_EN, HIGH); // keep RTC alive for faster fix on wake - digitalWrite(GPS_EN, LOW); - digitalWrite(GPS_RESET, LOW); - digitalWrite(GPS_SLEEP_INT, HIGH); + digitalWrite(GPS_RTC_INT, HIGH); + delay(5); digitalWrite(GPS_RTC_INT, LOW); } void MeshTrackerX1SensorManager::stop_gps() { gps_active = false; - digitalWrite(GPS_VRTC_EN, LOW); + digitalWrite(GPS_VRTC_EN, HIGH); // keep GPS RTC alive for faster fix on wake + digitalWrite(GPS_RTC_INT, LOW); // make sure this is LOW so we can pulse it to wake + airohaEnterSleep(_nmea); digitalWrite(GPS_EN, LOW); - digitalWrite(GPS_RESET, LOW); - digitalWrite(GPS_SLEEP_INT, HIGH); - digitalWrite(GPS_RTC_INT, LOW); } bool MeshTrackerX1SensorManager::begin() { // init GPS Serial1.begin(GPS_BAUD_RATE); + digitalWrite(GPS_RESET, HIGH); + delay(10); + digitalWrite(GPS_RESET, LOW); // init SPA06-003 barometer baro_ok = spa06.begin(SPA06_003_DEFAULT_ADDR, &Wire) || spa06.begin(0x76, &Wire); @@ -122,7 +104,7 @@ const char* MeshTrackerX1SensorManager::getSettingValue(int i) const { bool MeshTrackerX1SensorManager::setSettingValue(const char* name, const char* value) { if (strcmp(name, "gps") == 0) { if (strcmp(value, "0") == 0) { - sleep_gps(); // sleep for faster fix ! + stop_gps(); } else { start_gps(); } From 74413f0e4df005d3d776027439a8e1f15fd509a4 Mon Sep 17 00:00:00 2001 From: taco Date: Tue, 29 Sep 2026 20:16:32 +1000 Subject: [PATCH 12/12] T1000e GPS: use RTC backup for faster fix --- variants/t1000-e/target.cpp | 48 ++++++++---------------------------- variants/t1000-e/variant.cpp | 8 +++--- 2 files changed, 14 insertions(+), 42 deletions(-) diff --git a/variants/t1000-e/target.cpp b/variants/t1000-e/target.cpp index 425328270..70a64359f 100644 --- a/variants/t1000-e/target.cpp +++ b/variants/t1000-e/target.cpp @@ -2,6 +2,7 @@ #include "t1000e_sensors.h" #include "target.h" #include +#include T1000eBoard board; @@ -81,56 +82,28 @@ mesh::LocalIdentity radio_new_identity() { void T1000SensorManager::start_gps() { gps_active = true; - //_nmea->begin(); - // this init sequence should be better - // comes from seeed examples and deals with all gps pins - pinMode(GPS_EN, OUTPUT); digitalWrite(GPS_EN, HIGH); delay(10); - pinMode(GPS_VRTC_EN, OUTPUT); - digitalWrite(GPS_VRTC_EN, HIGH); - delay(10); - - pinMode(GPS_RESET, OUTPUT); - digitalWrite(GPS_RESET, HIGH); - delay(10); - digitalWrite(GPS_RESET, LOW); - - pinMode(GPS_SLEEP_INT, OUTPUT); - digitalWrite(GPS_SLEEP_INT, HIGH); - pinMode(GPS_RTC_INT, OUTPUT); + digitalWrite(GPS_RTC_INT, HIGH); + delay(5); digitalWrite(GPS_RTC_INT, LOW); - pinMode(GPS_RESETB, INPUT_PULLUP); -} - -void T1000SensorManager::sleep_gps() { - gps_active = false; - digitalWrite(GPS_VRTC_EN, HIGH); - digitalWrite(GPS_EN, LOW); - digitalWrite(GPS_RESET, HIGH); - digitalWrite(GPS_SLEEP_INT, HIGH); - digitalWrite(GPS_RTC_INT, LOW); - pinMode(GPS_RESETB, OUTPUT); - digitalWrite(GPS_RESETB, LOW); - //_nmea->stop(); } void T1000SensorManager::stop_gps() { gps_active = false; - digitalWrite(GPS_VRTC_EN, LOW); + digitalWrite(GPS_VRTC_EN, HIGH); // keep GPS RTC alive for faster fix on wake + digitalWrite(GPS_RTC_INT, LOW); // make sure this is LOW so we can pulse it to wake + airohaEnterSleep(_nmea); // send command to put the GPS into RTC backup sleep digitalWrite(GPS_EN, LOW); - digitalWrite(GPS_RESET, HIGH); - digitalWrite(GPS_SLEEP_INT, HIGH); - digitalWrite(GPS_RTC_INT, LOW); - pinMode(GPS_RESETB, OUTPUT); - digitalWrite(GPS_RESETB, LOW); - //_nmea->stop(); } bool T1000SensorManager::begin() { // init GPS Serial1.begin(115200); + digitalWrite(GPS_RESET, HIGH); + delay(10); + digitalWrite(GPS_RESET, LOW); return true; } @@ -156,7 +129,6 @@ void T1000SensorManager::loop() { node_lat = ((double)_nmea->getLatitude())/1000000.; node_lon = ((double)_nmea->getLongitude())/1000000.; node_altitude = ((double)_nmea->getAltitude()) / 1000.0; - //Serial.printf("lat %f lon %f\r\n", _lat, _lon); } next_gps_update = millis() + 1000; } @@ -176,7 +148,7 @@ const char* T1000SensorManager::getSettingValue(int i) const { bool T1000SensorManager::setSettingValue(const char* name, const char* value) { if (strcmp(name, "gps") == 0) { if (strcmp(value, "0") == 0) { - sleep_gps(); // sleep for faster fix ! + stop_gps(); } else { start_gps(); } diff --git a/variants/t1000-e/variant.cpp b/variants/t1000-e/variant.cpp index ed21fd68c..fc30a6197 100644 --- a/variants/t1000-e/variant.cpp +++ b/variants/t1000-e/variant.cpp @@ -71,7 +71,7 @@ void initVariant() pinMode(LUX_SENSOR, INPUT); pinMode(EXT_CHRG_DETECT, INPUT); pinMode(EXT_PWR_DETECT, INPUT); - pinMode(GPS_RESETB, INPUT); + pinMode(GPS_RESETB, INPUT_PULLUP); pinMode(PIN_BUTTON1, INPUT); pinMode(PIN_3V3_EN, OUTPUT); @@ -89,10 +89,10 @@ void initVariant() digitalWrite(PIN_3V3_ACC_EN, LOW); digitalWrite(BUZZER_EN, LOW); digitalWrite(SENSOR_EN, LOW); - digitalWrite(GPS_EN, LOW); + digitalWrite(GPS_EN, HIGH); digitalWrite(GPS_RESET, LOW); - digitalWrite(GPS_VRTC_EN, LOW); - digitalWrite(GPS_SLEEP_INT, HIGH); + digitalWrite(GPS_VRTC_EN, HIGH); + digitalWrite(GPS_SLEEP_INT, LOW); digitalWrite(GPS_RTC_INT, LOW); digitalWrite(LED_PIN, LOW); }