mirror of
https://github.com/meshcore-dev/MeshCore.git
synced 2026-03-30 19:15:49 +00:00
Merge branch 'dev' into t114_monochrome
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -5,3 +5,4 @@
|
||||
.vscode/launch.json
|
||||
.vscode/ipch
|
||||
out/
|
||||
.direnv/
|
||||
|
||||
@@ -4,6 +4,12 @@
|
||||
|
||||
#define AUTO_OFF_MILLIS 15000 // 15 seconds
|
||||
|
||||
#ifdef PIN_STATUS_LED
|
||||
#define LED_ON_MILLIS 20
|
||||
#define LED_ON_MSG_MILLIS 200
|
||||
#define LED_CYCLE_MILLIS 4000
|
||||
#endif
|
||||
|
||||
#ifndef USER_BTN_PRESSED
|
||||
#define USER_BTN_PRESSED LOW
|
||||
#endif
|
||||
@@ -43,10 +49,6 @@ void UITask::begin(DisplayDriver* display, const char* node_name, const char* bu
|
||||
*dash = 0;
|
||||
}
|
||||
|
||||
#ifdef PIN_USER_BTN
|
||||
pinMode(PIN_USER_BTN, INPUT);
|
||||
#endif
|
||||
|
||||
// v1.2.3 (1 Jan 2025)
|
||||
sprintf(_version_info, "%s (%s)", version, build_date);
|
||||
}
|
||||
@@ -135,22 +137,21 @@ void UITask::userLedHandler() {
|
||||
#ifdef PIN_STATUS_LED
|
||||
static int state = 0;
|
||||
static int next_change = 0;
|
||||
static int last_increment = 0;
|
||||
|
||||
int cur_time = millis();
|
||||
if (cur_time > next_change) {
|
||||
if (state == 0) {
|
||||
state = 1; // led on, short = unread msg
|
||||
state = 1;
|
||||
if (_msgcount > 0) {
|
||||
next_change = cur_time + 500;
|
||||
last_increment = LED_ON_MSG_MILLIS;
|
||||
} else {
|
||||
next_change = cur_time + 2000;
|
||||
last_increment = LED_ON_MILLIS;
|
||||
}
|
||||
next_change = cur_time + last_increment;
|
||||
} else {
|
||||
state = 0;
|
||||
if (_board->getBattMilliVolts() > 3800) {
|
||||
next_change = cur_time + 2000;
|
||||
} else {
|
||||
next_change = cur_time + 4000; // 4s blank if bat level low
|
||||
}
|
||||
next_change = cur_time + LED_CYCLE_MILLIS - last_increment;
|
||||
}
|
||||
digitalWrite(PIN_STATUS_LED, state);
|
||||
}
|
||||
|
||||
@@ -105,6 +105,13 @@ struct ClientInfo {
|
||||
|
||||
#define MAX_CLIENTS 4
|
||||
|
||||
struct NeighbourInfo {
|
||||
mesh::Identity id;
|
||||
uint32_t advert_timestamp;
|
||||
uint32_t heard_timestamp;
|
||||
int8_t snr; // multiplied by 4, user should divide to get float value
|
||||
};
|
||||
|
||||
// NOTE: need to space the ACK and the reply text apart (in CLI)
|
||||
#define CLI_REPLY_DELAY_MILLIS 1500
|
||||
|
||||
@@ -116,6 +123,9 @@ class MyMesh : public mesh::Mesh, public CommonCLICallbacks {
|
||||
CommonCLI _cli;
|
||||
uint8_t reply_data[MAX_PACKET_PAYLOAD];
|
||||
ClientInfo known_clients[MAX_CLIENTS];
|
||||
#if MAX_NEIGHBOURS
|
||||
NeighbourInfo neighbours[MAX_NEIGHBOURS];
|
||||
#endif
|
||||
|
||||
ClientInfo* putClient(const mesh::Identity& id) {
|
||||
uint32_t min_time = 0xFFFFFFFF;
|
||||
@@ -135,6 +145,33 @@ class MyMesh : public mesh::Mesh, public CommonCLICallbacks {
|
||||
return oldest;
|
||||
}
|
||||
|
||||
void putNeighbour(const mesh::Identity& id, uint32_t timestamp, float snr) {
|
||||
#if MAX_NEIGHBOURS // check if neighbours enabled
|
||||
// find existing neighbour, else use least recently updated
|
||||
uint32_t oldest_timestamp = 0xFFFFFFFF;
|
||||
NeighbourInfo* neighbour = &neighbours[0];
|
||||
for (int i = 0; i < MAX_NEIGHBOURS; i++) {
|
||||
// if neighbour already known, we should update it
|
||||
if (id.matches(neighbours[i].id)) {
|
||||
neighbour = &neighbours[i];
|
||||
break;
|
||||
}
|
||||
|
||||
// otherwise we should update the least recently updated neighbour
|
||||
if (neighbours[i].heard_timestamp < oldest_timestamp) {
|
||||
neighbour = &neighbours[i];
|
||||
oldest_timestamp = neighbour->heard_timestamp;
|
||||
}
|
||||
}
|
||||
|
||||
// update neighbour info
|
||||
neighbour->id = id;
|
||||
neighbour->advert_timestamp = timestamp;
|
||||
neighbour->heard_timestamp = getRTCClock()->getCurrentTime();
|
||||
neighbour->snr = (int8_t) (snr * 4);
|
||||
#endif
|
||||
}
|
||||
|
||||
int handleRequest(ClientInfo* sender, uint8_t* payload, size_t payload_len) {
|
||||
uint32_t now = getRTCClock()->getCurrentTimeUnique();
|
||||
memcpy(reply_data, &now, 4); // response packets always prefixed with timestamp
|
||||
@@ -361,6 +398,18 @@ protected:
|
||||
}
|
||||
}
|
||||
|
||||
void onAdvertRecv(mesh::Packet* packet, const mesh::Identity& id, uint32_t timestamp, const uint8_t* app_data, size_t app_data_len) {
|
||||
mesh::Mesh::onAdvertRecv(packet, id, timestamp, app_data, app_data_len); // chain to super impl
|
||||
|
||||
// if this a zero hop advert, add it to neighbours
|
||||
if (packet->path_len == 0) {
|
||||
AdvertDataParser parser(app_data, app_data_len);
|
||||
if (parser.isValid() && parser.getType() == ADV_TYPE_REPEATER) { // just keep neigbouring Repeaters
|
||||
putNeighbour(id, timestamp, packet->getSNR());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void onPeerDataRecv(mesh::Packet* packet, uint8_t type, int sender_idx, const uint8_t* secret, uint8_t* data, size_t len) override {
|
||||
int i = matching_peer_indexes[sender_idx];
|
||||
if (i < 0 || i >= MAX_CLIENTS) { // get from our known_clients table (sender SHOULD already be known in this context)
|
||||
@@ -427,12 +476,35 @@ protected:
|
||||
}
|
||||
|
||||
uint8_t temp[166];
|
||||
const char *command = (const char *) &data[5];
|
||||
char *reply = (char *) &temp[5];
|
||||
if (is_retry) {
|
||||
temp[0] = 0;
|
||||
*reply = 0;
|
||||
#if MAX_NEIGHBOURS
|
||||
} else if (memcmp(command, "neighbors", 9) == 0) {
|
||||
char *dp = reply;
|
||||
|
||||
for (int i = 0; i < MAX_NEIGHBOURS && dp - reply < 136; i++) {
|
||||
NeighbourInfo* neighbour = &neighbours[i];
|
||||
if (neighbour->heard_timestamp == 0) continue; // skip empty slots
|
||||
|
||||
// add new line if not first item
|
||||
if (i > 0) *dp++ = '\n';
|
||||
|
||||
char hex[10];
|
||||
// get 4 bytes of neighbour id as hex
|
||||
mesh::Utils::toHex(hex, neighbour->id.pub_key, 4);
|
||||
|
||||
// add next neighbour
|
||||
sprintf(dp, "%s:%d:%d", hex, neighbour->advert_timestamp, neighbour->snr);
|
||||
while (*dp) dp++; // find end of string
|
||||
}
|
||||
*dp = 0; // null terminator
|
||||
#endif
|
||||
} else {
|
||||
_cli.handleCommand(sender_timestamp, (const char *) &data[5], (char *) &temp[5]);
|
||||
_cli.handleCommand(sender_timestamp, command, reply);
|
||||
}
|
||||
int text_len = strlen((char *) &temp[5]);
|
||||
int text_len = strlen(reply);
|
||||
if (text_len > 0) {
|
||||
uint32_t timestamp = getRTCClock()->getCurrentTimeUnique();
|
||||
if (timestamp == sender_timestamp) {
|
||||
@@ -482,6 +554,10 @@ public:
|
||||
next_local_advert = next_flood_advert = 0;
|
||||
_logging = false;
|
||||
|
||||
#if MAX_NEIGHBOURS
|
||||
memset(neighbours, 0, sizeof(neighbours));
|
||||
#endif
|
||||
|
||||
// defaults
|
||||
memset(&_prefs, 0, sizeof(_prefs));
|
||||
_prefs.airtime_factor = 1.0; // one half
|
||||
|
||||
@@ -52,6 +52,7 @@ bool Packet::readFrom(const uint8_t src[], uint8_t len) {
|
||||
memcpy(path, &src[i], path_len); i += path_len;
|
||||
if (i >= len) return false; // bad encoding
|
||||
payload_len = len - i;
|
||||
if (payload_len > sizeof(payload)) return false; // bad encoding
|
||||
memcpy(payload, &src[i], payload_len); //i += payload_len;
|
||||
return true; // success
|
||||
}
|
||||
|
||||
@@ -33,6 +33,7 @@ build_flags =
|
||||
-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 =
|
||||
|
||||
@@ -79,17 +79,20 @@ build_flags =
|
||||
-D MAX_CONTACTS=100
|
||||
-D MAX_GROUP_CHANNELS=8
|
||||
-D BLE_PIN_CODE=123456
|
||||
-D DISPLAY_CLASS=SSD1306Display
|
||||
; -D BLE_DEBUG_LOGGING=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_S3_WIO.build_src_filter}
|
||||
+<helpers/ui/SSD1306Display.cpp>
|
||||
+<helpers/esp32/*.cpp>
|
||||
+<../examples/companion_radio/main.cpp>
|
||||
+<../examples/companion_radio>
|
||||
lib_deps =
|
||||
${Xiao_S3_WIO.lib_deps}
|
||||
densaugeo/base64 @ ~1.4.0
|
||||
adafruit/Adafruit SSD1306 @ ^2.5.13
|
||||
|
||||
[env:Xiao_S3_WIO_companion_radio_serial]
|
||||
extends = Xiao_S3_WIO
|
||||
@@ -108,24 +111,4 @@ lib_deps =
|
||||
${Xiao_S3_WIO.lib_deps}
|
||||
densaugeo/base64 @ ~1.4.0
|
||||
|
||||
[env:Xiao_S3_WIO_expansion_companion_radio_ble]
|
||||
extends = Xiao_S3_WIO
|
||||
build_flags =
|
||||
${Xiao_S3_WIO.build_flags}
|
||||
-D MAX_CONTACTS=100
|
||||
-D MAX_GROUP_CHANNELS=8
|
||||
-D BLE_PIN_CODE=123456
|
||||
-D DISPLAY_CLASS=SSD1306Display
|
||||
; -D BLE_DEBUG_LOGGING=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_S3_WIO.build_src_filter}
|
||||
+<helpers/ui/SSD1306Display.cpp>
|
||||
+<helpers/esp32/*.cpp>
|
||||
+<../examples/companion_radio>
|
||||
lib_deps =
|
||||
${Xiao_S3_WIO.lib_deps}
|
||||
densaugeo/base64 @ ~1.4.0
|
||||
adafruit/Adafruit SSD1306 @ ^2.5.13
|
||||
|
||||
|
||||
Reference in New Issue
Block a user