From bb5509d43e59f9a207c526b2eb676cb2b5fedb44 Mon Sep 17 00:00:00 2001 From: Matthew Sainsbury Date: Mon, 26 May 2025 18:22:31 -0700 Subject: [PATCH 1/6] initial try at documenting payload formats --- docs/payloads.md | 176 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 176 insertions(+) create mode 100644 docs/payloads.md diff --git a/docs/payloads.md b/docs/payloads.md new file mode 100644 index 0000000..2c40210 --- /dev/null +++ b/docs/payloads.md @@ -0,0 +1,176 @@ +# Meshcore payloads +Inside of each [meshcore packet](./packet_structure.md) is a payload, identified by the payload type in the packet header. The types of payloads are: + +* Request (destination/source hashes + MAC). +* Response to REQ or ANON_REQ. +* Plain text message. +* Acknowledgment. +* Node advertisement. +* Group text message (unverified). +* Group datagram (unverified). +* Anonymous request. +* Returned path. +* Custom packet (raw bytes, custom encryption). + +This document defines the structure of each of these payload types + +# Node advertisement +This kind of payload notifies receivers that a node exists, and gives information about the node + +| Field | Size (bytes) | Description | +|---------------|-----------------|----------------------------------------------------------| +| public key | 32 | Ed25519 public key | +| timestamp | 4 | unix timestamp of advertisement | +| signature | 64 | Ed25519 signature of public key, timestamp, and app data | +| appdata | rest of payload | optional, see below | + +Appdata + +| Field | Size (bytes) | Description | +|---------------|-----------------|-------------------------------------------------------| +| flags | 1 | specifies which of the fields are present, see below | +| latitude | 4 | decimal latitude multiplied by 1000000, integer | +| longitude | 4 | decimal longitude multiplied by 1000000, integer | +| feature 1 | 2 | reserved for future use | +| feature 2 | 2 | reserved for future use | +| name | rest of appdata | name of the node | + +Appdata Flags + +| Value | Name | Description | +|--------|-----------|---------------------------------------| +| `0x10` | location | appdata contains lat/long information | +| `0x20` | feature 1 | Reserved for future use. | +| `0x40` | feature 2 | Reserved for future use. | +| `0x80` | name | appdata contains a node name | + +# Acknowledgement +| Field | Size (bytes) | Description | +|----------|--------------|------------------------------------------------------------| +| checksum | 4 | CRC checksum of message timestamp, text, and sender pubkey | + + +# Returned path, request, response, and plain text message +| Field | Size (bytes) | Description | +|------------------|-----------------|------------------------------------------------------| +| destination hash | 1 | first byte of destination node public key | +| source hash | 1 | first byte of source node public key | +| cipher MAC | 2 | MAC for encrypted data in next field | +| ciphertext | rest of payload | encrypted message, see subsections below for details | + +## Returned path + +| Field | Size (bytes) | Description | +|-------------|--------------|----------------------------------------------------------------------------------------------| +| path length | 1 | length of next field | +| path | see above | a list of node hashes (one byte each) describing the route from us to the packet author | +| extra type | 1 | extra, bundled payload type, eg., acknowledgement or response. See packet structure spec | +| extra | rest of data | extra, bundled payload content, follows same format as main content defined by this document | + +## Request + +| Field | Size (bytes) | Description | +|--------------|-----------------|----------------------------| +| timestamp | 4 | send time (unix timestamp) | +| request type | 1 | see below | +| request data | rest of payload | depends on request type | + +Request type + +| Value | Name | Description | +|--------|--------------------|---------------------------------------| +| `0x01` | get status | get status of repeater or room server | +| `0x02` | keepalive | TODO | +| `0x03` | get telemetry data | TODO | + +### Get status + +Gets information about the node, possibly including the following: + +* Battery level (millivolts) +* Current transmit queue length +* Current free queue length +* Last RSSI value +* Number of received packets +* Number of sent packets +* Total airtime (seconds) +* Total uptime (seconds) +* Number of packets sent as flood +* Number of packets sent directly +* Number of packets received as flood +* Number of packets received directly +* Error flags +* Last SNR value +* Number of direct route duplicates +* Number of flood route duplicates +* Number posted (?) +* Number of post pushes (?) + +### Keepalive + +No-op request. + +### Get telemetry data + +Request data about sensors on the node, including battery level. + +## Response + +| Field | Size (bytes) | Description | +|---------|-----------------|-------------| +| tag | 4 | TODO | +| content | rest of payload | TODO | + +## Plain text message + +| Field | Size (bytes) | Description | +|--------------|-----------------|--------------------------------------------------------------| +| timestamp | 4 | send time (unix timestamp) | +| flags + TODO | 1 | first six bits are flags (see below), last two bits are TODO | +| message | rest of payload | the message content, see next table | + +Flags + +| Value | Description | Message content | +|--------|---------------------------|------------------------------------------------------------| +| `0x00` | plain text message | the plain text of the message | +| `0x01` | CLI command | the command text of the message | +| `0x02` | signed plain text message | two bytes of sender prefix, followed by plain text message | + +# Anonymous request + +| Field | Size (bytes) | Description | +|------------------|-----------------|-------------------------------------------| +| destination hash | 1 | first byte of destination node public key | +| public key | 32 | sender's Ed25519 public key | +| cipher MAC | 2 | MAC for encrypted data in next field | +| ciphertext | rest of payload | encrypted message, see below for details | + +Plaintext message + +| Field | Size (bytes) | Description | +|----------------|-----------------|-------------------------------------------------------------------------------| +| timestamp | 4 | send time (unix timestamp) | +| sync timestamp | 4 | for room server, otherwise absent: sender's "sync messages SINCE x" timestamp | +| password | rest of message | password for repeater/room | + +# Group text message / datagram + +| Field | Size (bytes) | Description | +|--------------|-----------------|------------------------------------------| +| channel hash | 1 | TODO | +| cipher MAC | 2 | MAC for encrypted data in next field | +| ciphertext | rest of payload | encrypted message, see below for details | + +Plaintext for text message + +| Field | Size (bytes) | Description | +|-----------|-----------------|----------------------------------| +| timestamp | 4 | send time (unix timestamp) | +| content | rest of message | plain group text message content | + +TODO: describe what datagram looks like + +# Custom packet + +Custom packets have no defined format. \ No newline at end of file From 8b780ddd7b0ad6f2308be19042e04e5b6df7aae7 Mon Sep 17 00:00:00 2001 From: uncle lit <43320854+LitBomb@users.noreply.github.com> Date: Sat, 31 May 2025 21:59:14 -0700 Subject: [PATCH 2/6] faq.md: update OTA firmware instructions added ESP32 OTA firmware update instructions added nRF OTA firmware update instructions to use the new nRF DFU app on android and iOS --- docs/faq.md | 88 +++++++++++++++-------------------------------------- 1 file changed, 25 insertions(+), 63 deletions(-) diff --git a/docs/faq.md b/docs/faq.md index 030c553..c61c8d2 100644 --- a/docs/faq.md +++ b/docs/faq.md @@ -65,7 +65,8 @@ author: https://github.com/LitBomb - [6.4. Q: I can't connect via Bluetooth, what is the Bluetooth pairing code?](#64-q-i-cant-connect-via-bluetooth-what-is-the-bluetooth-pairing-code) - [6.5. Q: My Heltec V3 keeps disconnecting from my smartphone. It can't hold a solid Bluetooth connection.](#65-q-my-heltec-v3-keeps-disconnecting-from-my-smartphone--it-cant-hold-a-solid-bluetooth-connection) - [7. Other Questions:](#7-other-questions) - - [7.1. Q: How to Update repeater and room server firmware over the air?](#71-q-how-to--update-repeater-and-room-server-firmware-over-the-air) + - [7.2 Q: How to update ESP32-based devices over the air?](#72-q-how-to-update-esp32-based-devices-over-the-air) + - [7.1 Q: How to update nRF (RAK, T114, Seed XIAO) repeater and room server firmware over the air using the new simpler DFU app?](#71-q-how-to-update-nrf-rak-t114-seed-xiao-repeater-and-room-server-firmware-over-the-air-using-the-new-simpler-dfu-app) ## 1. Introduction @@ -534,74 +535,35 @@ You can get the epoch time on and use it to se --- ## 7. Other Questions: -### 7.1. Q: How to Update repeater and room server firmware over the air? -**A:** Only nRF-based RAK4631 and Heltec T114 OTA firmware update are verified using nRF smartphone app. Lilygo T-Echo doesn't work currently. -You can update repeater and room server firmware with a Bluetooth connection between your smartphone and your LoRa radio using the nRF app. +### 7.2 Q: How to update ESP32-based devices over the air? -1. Download the ZIP file for the specific node from the web flasher to your smartphone -2. On the phone client, log on to the repeater as administrator (default password is `password`) to issue the `start ota`command to the repeater or room server to get the device into OTA DFU mode - -![image](https://github.com/user-attachments/assets/889bb81b-7214-4a1c-955a-396b5a05d8ad) - -1. `start ota` can be initiated from USB serial console on the web flasher page or a T-Deck -4. On the smartphone, download and run the nRF app and scan for Bluetooth devices -5. Connect to the repeater/room server node you want to update - 1. nRF app is available on both Android and iOS - -**Android continues after the iOS section:** - -**iOS continues here:** -5. Once connected successfully, a `DFU` icon ![Pasted image 20250309173039](https://github.com/user-attachments/assets/af7a9f78-8739-4946-b734-02bade9c8e71) - appears in the top right corner of the app - ![Pasted image 20250309171919](https://github.com/user-attachments/assets/08007ec8-4924-49c1-989f-ca2611e78793) - -6. Scroll down to change the `PRN(s)` number: - -![Pasted image 20250309190158](https://github.com/user-attachments/assets/11f69cdd-12f3-4696-a6fc-14a78c85fe32) - -- For the T114, change the number of packets `(PRN(s)` to 8 -- For RAK, it can be 10, but it also works on 8. - -7. Click the `DFU` icon ![Pasted image 20250309173039](https://github.com/user-attachments/assets/af7a9f78-8739-4946-b734-02bade9c8e71), select the type of file to upload (choose ZIP), then select the ZIP file that was downloaded earlier from the web flasher -8. The upload process will start now. If everything goes well, the node resets and is flashed successfully. -![Pasted image 20250309190342](https://github.com/user-attachments/assets/a60e25d0-33b8-46cf-af90-20a7d8ac2adb) +**A:** For ESP32-based devices (e.g. Heltec V3): +1. On flasher.meshcore.co.uk, download the **non-merged** version of the firmware for your ESP32 device (e.g. `Heltec_v3_repeater-v1.6.2-4449fd3.bin`, no `"merged"` in the file name) +2. From the MeshCore app, login remotely to the repeater you want to update with admin priviledge +4. Go to the Command Line tab, type `start ota` and hit enter. +5. you should see `OK` to confirm the repeater device is now in OTA mode +6. The command `start ota` on an ESP32-based device starts a wifi hotspot named `MeshCore OTA` +7. From your phone or computer connect to the 'MeshCore OTA' hotspot +8. From a browser, go to http://192.168.4.1/update and upload the non-merged bin from the flasher +### 7.1 Q: How to update nRF (RAK, T114, Seed XIAO) repeater and room server firmware over the air using the new simpler DFU app? -**Android steps continues below:** -1. on the top left corner of the nRF Connect app on Android, tap the 3-bar hamburger menu, then `Settings`, then `nRF5 DFU Options` +**A:** The steps below work on both Android and iOS as nRF has made both apps' user interface the same on both platforms: -![Android nRF Hamberger](https://github.com/user-attachments/assets/ea6dfeef-9367-4830-bd70-1441d517c706) - -![Android nRF Settings](https://github.com/user-attachments/assets/c63726bf-cecd-4987-be68-afb6358c7190) - -![Android nRF DFU Options](https://github.com/user-attachments/assets/b20e872f-5122-41d9-90df-0215cff5fbc9) - -2. Change `Number of packets` to `10` for RAK, `8` for Heltec T114 - -![Android nRF Number of Packets](https://github.com/user-attachments/assets/c092adaf-4cb3-460b-b7ef-8d7f450d602b) - -3. Go back to the main screen -4. Your LoRa device should already ben in DFU mode from previous steps -5. tap `SCANNER` and then `SCAN` to find the device you want to update, tap `CONNECT` - -![Android nRF Scanner Scan Connect](https://github.com/user-attachments/assets/37218717-f167-48b6-a6ca-93d132ef77ca) - -6. On the top left corner of the nRF Connect app, tap the `DFU` icon next to the three dots - -![Android nRF DFU](https://github.com/user-attachments/assets/1ec3b818-bf0c-461f-8fdf-37c41a63cafa) - -7. Choose `Distribution packet (ZIP)` and then `OK` - -![Android nRF Distribution Packet (ZIP)](https://github.com/user-attachments/assets/e65f5616-9793-44f5-95c0-a3eb15aa7152) - -8. Choose the firmware file in ZIP formate that you downloaded earlier from the MeshCore web flasher, update will start as soon as you tap the file - -![Android nRF FW Updating](https://github.com/user-attachments/assets/0814d123-85ce-4c87-90a7-e1a25dc71900) - -9. When the update process is done, the device will disconnect from nRF app and the LoRa device is updated +1. Download nRF's DFU app from iOS App Store or Android's Play Store, you can find the app by searching for `nrf dfu`, the app's full name is `nRF Device Firmware Update` +2. On flasher.meshcore.co.uk, download the **ZIP** version of the firmware for your nRF device (e.g. RAK or Heltec T114 or Seeed Studio's Xiao) +3. From the MeshCore app, login remotely to the repeater you want to update with admin priviledge +4. Go to the Command Line tab, type `start ota` and hit enter. +5. you should see `OK` to confirm the repeater device is now in OTA mode +6. Run the DFU app,tab `Settings` on the top right corner +7. Enable `Packets receipt notifications` and change `Number of Packets` to 10 for RAK, 8 for T114. 8 also works for RAK. +8. Select the firmware zip file you downloaded +9. Select the device you want to update. If the device you want to updat is not on the list, try enabling`OTA` on the device again +10. Tab the `Upload` to begin OTA update +11. If it fails, try turning off and on Bluetooth on your phone. If that doesn't work, try rebooting your phone. +12. Wait for the update to complete. It can take a few minutes. --- - From 4eccc9e5a59ec77cd5affeb0d600a66ccbbbde4d Mon Sep 17 00:00:00 2001 From: ripplebiz Date: Mon, 2 Jun 2025 11:18:37 +1000 Subject: [PATCH 3/6] Update README.md --- README.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/README.md b/README.md index b4943de..708db2c 100644 --- a/README.md +++ b/README.md @@ -95,6 +95,11 @@ MeshCore is open-source software released under the MIT License. You are free to Please submit PR's using 'dev' as the base branch! For minor changes just submit your PR and I'll try to review it, but for anything more 'impactful' please open an Issue first and start a discussion. Is better to sound out what it is you want to achieve first, and try to come to a consensus on what the best approach is, especially when it impacts the structure or architecture of this codebase. +Here are some general principals you should try to adhere to: +* Keep it simple. Please, don't think like a high-level lang programmer. Think embedded, and keep code concise, without any unecessary layers. +* No dynamic memory allocation, except during setup/begin functions. +* Use the same brace and indenting style that's in the core source modules. (A .clang-format is prob going to be added soon, but please do NOT retroactively re-format existing code. This just creates unnecessary diffs that make finding problems harder) + ## 📞 Get Support - Report bugs and request features on the [GitHub Issues](https://github.com/ripplebiz/MeshCore/issues) page. From 22058c0ee5c0421270ce848516cfe21101e65084 Mon Sep 17 00:00:00 2001 From: liamcottle Date: Thu, 5 Jun 2025 20:35:40 +1200 Subject: [PATCH 4/6] add logo files --- logo/meshcore.afdesign | Bin 0 -> 20497 bytes logo/meshcore.png | Bin 0 -> 12486 bytes logo/meshcore.svg | 12 ++++++++++++ logo/meshcore_tm.svg | 14 ++++++++++++++ 4 files changed, 26 insertions(+) create mode 100644 logo/meshcore.afdesign create mode 100644 logo/meshcore.png create mode 100644 logo/meshcore.svg create mode 100644 logo/meshcore_tm.svg diff --git a/logo/meshcore.afdesign b/logo/meshcore.afdesign new file mode 100644 index 0000000000000000000000000000000000000000..17cc02a98815dc6dc1d220cb4628038b4a3a314b GIT binary patch literal 20497 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

u;rIY?=}Kfk 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 B%d!9f literal 0 HcmV?d00001 diff --git a/logo/meshcore.svg b/logo/meshcore.svg new file mode 100644 index 0000000..eb1b7bc --- /dev/null +++ b/logo/meshcore.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/logo/meshcore_tm.svg b/logo/meshcore_tm.svg new file mode 100644 index 0000000..b7e252d --- /dev/null +++ b/logo/meshcore_tm.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + From 6e5c865c21c2d3c7fdeae76f1a6ecf7cfd97dc92 Mon Sep 17 00:00:00 2001 From: Rastislav Vysoky Date: Fri, 6 Jun 2025 00:23:57 +0200 Subject: [PATCH 5/6] Disable LFS_ASSERT to stop freezing the boards on LFS errors --- platformio.ini | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/platformio.ini b/platformio.ini index 80f850e..0c16ead 100644 --- a/platformio.ini +++ b/platformio.ini @@ -54,6 +54,7 @@ extends = arduino_base platform = nordicnrf52 build_flags = ${arduino_base.build_flags} -D NRF52_PLATFORM + -D LFS_NO_ASSERT=1 [nrf52840_base] extends = nrf52_base @@ -83,4 +84,4 @@ build_flags = ${arduino_base.build_flags} build_src_filter = ${arduino_base.build_src_filter} + lib_deps = ${arduino_base.lib_deps} - file://arch/stm32/Adafruit_LittleFS_stm32 \ No newline at end of file + file://arch/stm32/Adafruit_LittleFS_stm32 From 4b9eac81c6d72fc18302a0999fe36f89639d9cfb Mon Sep 17 00:00:00 2001 From: liamcottle Date: Fri, 6 Jun 2025 21:55:03 +1200 Subject: [PATCH 6/6] fix 150mA power draw on ThinkNode M1 --- src/helpers/ui/buzzer.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/helpers/ui/buzzer.cpp b/src/helpers/ui/buzzer.cpp index ccc18cd..c8e5cfc 100644 --- a/src/helpers/ui/buzzer.cpp +++ b/src/helpers/ui/buzzer.cpp @@ -11,6 +11,7 @@ void genericBuzzer::begin() { quiet(false); pinMode(PIN_BUZZER, OUTPUT); + digitalWrite(PIN_BUZZER, LOW); // need to pull low by default to avoid extreme power draw startup(); }