diff --git a/docs/stats_binary_frames.md b/docs/stats_binary_frames.md new file mode 100644 index 00000000..1b409912 --- /dev/null +++ b/docs/stats_binary_frames.md @@ -0,0 +1,312 @@ +# Stats Binary Frame Structures + +Binary frame structures for companion radio stats commands. All multi-byte integers use little-endian byte order. + +## Command Codes + +| Command | Code | Description | +|---------|------|-------------| +| `CMD_GET_STATS` | 56 | Get statistics (2-byte command: code + sub-type) | + +### Stats Sub-Types + +The `CMD_GET_STATS` command uses a 2-byte frame structure: +- **Byte 0:** `CMD_GET_STATS` (56) +- **Byte 1:** Stats sub-type: + - `STATS_TYPE_CORE` (0) - Get core device statistics + - `STATS_TYPE_RADIO` (1) - Get radio statistics + - `STATS_TYPE_PACKETS` (2) - Get packet statistics + +## Response Codes + +| Response | Code | Description | +|----------|------|-------------| +| `RESP_CODE_STATS` | 24 | Statistics response (2-byte response: code + sub-type) | + +### Stats Response Sub-Types + +The `RESP_CODE_STATS` response uses a 2-byte header structure: +- **Byte 0:** `RESP_CODE_STATS` (24) +- **Byte 1:** Stats sub-type (matches command sub-type): + - `STATS_TYPE_CORE` (0) - Core device statistics response + - `STATS_TYPE_RADIO` (1) - Radio statistics response + - `STATS_TYPE_PACKETS` (2) - Packet statistics response + +--- + +## RESP_CODE_STATS + STATS_TYPE_CORE (24, 0) + +**Total Frame Size:** 11 bytes + +| Offset | Size | Type | Field Name | Description | Range/Notes | +|--------|------|------|------------|-------------|-------------| +| 0 | 1 | uint8_t | response_code | Always `0x18` (24) | - | +| 1 | 1 | uint8_t | stats_type | Always `0x00` (STATS_TYPE_CORE) | - | +| 2 | 2 | uint16_t | battery_mv | Battery voltage in millivolts | 0 - 65,535 | +| 4 | 4 | uint32_t | uptime_secs | Device uptime in seconds | 0 - 4,294,967,295 | +| 8 | 2 | uint16_t | errors | Error flags bitmask | - | +| 10 | 1 | uint8_t | queue_len | Outbound packet queue length | 0 - 255 | + +### Example Structure (C/C++) + +```c +struct StatsCore { + uint8_t response_code; // 0x18 + uint8_t stats_type; // 0x00 (STATS_TYPE_CORE) + uint16_t battery_mv; + uint32_t uptime_secs; + uint16_t errors; + uint8_t queue_len; +} __attribute__((packed)); +``` + +--- + +## RESP_CODE_STATS + STATS_TYPE_RADIO (24, 1) + +**Total Frame Size:** 14 bytes + +| Offset | Size | Type | Field Name | Description | Range/Notes | +|--------|------|------|------------|-------------|-------------| +| 0 | 1 | uint8_t | response_code | Always `0x18` (24) | - | +| 1 | 1 | uint8_t | stats_type | Always `0x01` (STATS_TYPE_RADIO) | - | +| 2 | 2 | int16_t | noise_floor | Radio noise floor in dBm | -140 to +10 | +| 4 | 1 | int8_t | last_rssi | Last received signal strength in dBm | -128 to +127 | +| 5 | 1 | int8_t | last_snr | SNR scaled by 4 | Divide by 4.0 for dB | +| 6 | 4 | uint32_t | tx_air_secs | Cumulative transmit airtime in seconds | 0 - 4,294,967,295 | +| 10 | 4 | uint32_t | rx_air_secs | Cumulative receive airtime in seconds | 0 - 4,294,967,295 | + +### Example Structure (C/C++) + +```c +struct StatsRadio { + uint8_t response_code; // 0x18 + uint8_t stats_type; // 0x01 (STATS_TYPE_RADIO) + int16_t noise_floor; + int8_t last_rssi; + int8_t last_snr; // Divide by 4.0 to get actual SNR in dB + uint32_t tx_air_secs; + uint32_t rx_air_secs; +} __attribute__((packed)); +``` + +--- + +## RESP_CODE_STATS + STATS_TYPE_PACKETS (24, 2) + +**Total Frame Size:** 26 bytes + +| Offset | Size | Type | Field Name | Description | Range/Notes | +|--------|------|------|------------|-------------|-------------| +| 0 | 1 | uint8_t | response_code | Always `0x18` (24) | - | +| 1 | 1 | uint8_t | stats_type | Always `0x02` (STATS_TYPE_PACKETS) | - | +| 2 | 4 | uint32_t | recv | Total packets received | 0 - 4,294,967,295 | +| 6 | 4 | uint32_t | sent | Total packets sent | 0 - 4,294,967,295 | +| 10 | 4 | uint32_t | flood_tx | Packets sent via flood routing | 0 - 4,294,967,295 | +| 14 | 4 | uint32_t | direct_tx | Packets sent via direct routing | 0 - 4,294,967,295 | +| 18 | 4 | uint32_t | flood_rx | Packets received via flood routing | 0 - 4,294,967,295 | +| 22 | 4 | uint32_t | direct_rx | Packets received via direct routing | 0 - 4,294,967,295 | + +### Notes + +- Counters are cumulative from boot and may wrap. +- `recv = flood_rx + direct_rx` +- `sent = flood_tx + direct_tx` + +### Example Structure (C/C++) + +```c +struct StatsPackets { + uint8_t response_code; // 0x18 + uint8_t stats_type; // 0x02 (STATS_TYPE_PACKETS) + uint32_t recv; + uint32_t sent; + uint32_t flood_tx; + uint32_t direct_tx; + uint32_t flood_rx; + uint32_t direct_rx; +} __attribute__((packed)); +``` + +--- + +## Command Usage Example (Python) + +```python +# Send CMD_GET_STATS command +def send_get_stats_core(serial_interface): + """Send command to get core stats""" + cmd = bytes([56, 0]) # CMD_GET_STATS (56) + STATS_TYPE_CORE (0) + serial_interface.write(cmd) + +def send_get_stats_radio(serial_interface): + """Send command to get radio stats""" + cmd = bytes([56, 1]) # CMD_GET_STATS (56) + STATS_TYPE_RADIO (1) + serial_interface.write(cmd) + +def send_get_stats_packets(serial_interface): + """Send command to get packet stats""" + cmd = bytes([56, 2]) # CMD_GET_STATS (56) + STATS_TYPE_PACKETS (2) + serial_interface.write(cmd) +``` + +--- + +## Response Parsing Example (Python) + +```python +import struct + +def parse_stats_core(frame): + """Parse RESP_CODE_STATS + STATS_TYPE_CORE frame (11 bytes)""" + response_code, stats_type, battery_mv, uptime_secs, errors, queue_len = \ + struct.unpack('= 2) { + uint8_t stats_type = cmd_frame[1]; + if (stats_type == STATS_TYPE_CORE) { + int i = 0; + out_frame[i++] = RESP_CODE_STATS; + out_frame[i++] = STATS_TYPE_CORE; + uint16_t battery_mv = board.getBattMilliVolts(); + uint32_t uptime_secs = _ms->getMillis() / 1000; + uint8_t queue_len = (uint8_t)_mgr->getOutboundCount(0xFFFFFFFF); + memcpy(&out_frame[i], &battery_mv, 2); i += 2; + memcpy(&out_frame[i], &uptime_secs, 4); i += 4; + memcpy(&out_frame[i], &_err_flags, 2); i += 2; + out_frame[i++] = queue_len; + _serial->writeFrame(out_frame, i); + } else if (stats_type == STATS_TYPE_RADIO) { + int i = 0; + out_frame[i++] = RESP_CODE_STATS; + out_frame[i++] = STATS_TYPE_RADIO; + int16_t noise_floor = (int16_t)_radio->getNoiseFloor(); + int8_t last_rssi = (int8_t)radio_driver.getLastRSSI(); + int8_t last_snr = (int8_t)(radio_driver.getLastSNR() * 4); // scaled by 4 for 0.25 dB precision + uint32_t tx_air_secs = getTotalAirTime() / 1000; + uint32_t rx_air_secs = getReceiveAirTime() / 1000; + memcpy(&out_frame[i], &noise_floor, 2); i += 2; + out_frame[i++] = last_rssi; + out_frame[i++] = last_snr; + memcpy(&out_frame[i], &tx_air_secs, 4); i += 4; + memcpy(&out_frame[i], &rx_air_secs, 4); i += 4; + _serial->writeFrame(out_frame, i); + } else if (stats_type == STATS_TYPE_PACKETS) { + int i = 0; + out_frame[i++] = RESP_CODE_STATS; + out_frame[i++] = STATS_TYPE_PACKETS; + uint32_t recv = radio_driver.getPacketsRecv(); + uint32_t sent = radio_driver.getPacketsSent(); + uint32_t n_sent_flood = getNumSentFlood(); + uint32_t n_sent_direct = getNumSentDirect(); + uint32_t n_recv_flood = getNumRecvFlood(); + uint32_t n_recv_direct = getNumRecvDirect(); + memcpy(&out_frame[i], &recv, 4); i += 4; + memcpy(&out_frame[i], &sent, 4); i += 4; + memcpy(&out_frame[i], &n_sent_flood, 4); i += 4; + memcpy(&out_frame[i], &n_sent_direct, 4); i += 4; + memcpy(&out_frame[i], &n_recv_flood, 4); i += 4; + memcpy(&out_frame[i], &n_recv_direct, 4); i += 4; + _serial->writeFrame(out_frame, i); + } else { + writeErrFrame(ERR_CODE_ILLEGAL_ARG); // invalid stats sub-type + } } else if (cmd_frame[0] == CMD_FACTORY_RESET && memcmp(&cmd_frame[1], "reset", 5) == 0) { bool success = _store->formatFileSystem(); if (success) { diff --git a/examples/simple_repeater/MyMesh.cpp b/examples/simple_repeater/MyMesh.cpp index 4136818c..a9be6c40 100644 --- a/examples/simple_repeater/MyMesh.cpp +++ b/examples/simple_repeater/MyMesh.cpp @@ -82,7 +82,7 @@ void MyMesh::putNeighbour(const mesh::Identity &id, uint32_t timestamp, float sn #endif } -uint8_t MyMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data) { +uint8_t MyMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data, bool is_flood) { ClientInfo* client = NULL; if (data[0] == 0) { // blank password, just check if sender is in ACL client = acl.getClient(sender.pub_key, PUB_KEY_SIZE); @@ -123,6 +123,10 @@ uint8_t MyMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* secr } } + if (is_flood) { + client->out_path_len = -1; // need to rediscover out_path + } + uint32_t now = getRTCClock()->getCurrentTimeUnique(); memcpy(reply_data, &now, 4); // response packets always prefixed with timestamp reply_data[4] = RESP_SERVER_LOGIN_OK; @@ -438,7 +442,7 @@ void MyMesh::onAnonDataRecv(mesh::Packet *packet, const uint8_t *secret, const m data[len] = 0; // ensure null terminator uint8_t reply_len; if (data[4] == 0 || data[4] >= ' ') { // is password, ie. a login request - reply_len = handleLoginReq(sender, secret, timestamp, &data[4]); + reply_len = handleLoginReq(sender, secret, timestamp, &data[4], packet->isRouteFlood()); //} else if (data[4] == ANON_REQ_TYPE_*) { // future type codes // TODO } else { @@ -710,6 +714,8 @@ MyMesh::MyMesh(mesh::MainBoard &board, mesh::Radio &radio, mesh::MillisecondCloc _prefs.gps_enabled = 0; _prefs.gps_interval = 0; _prefs.advert_loc_policy = ADVERT_LOC_PREFS; + + _prefs.adc_multiplier = 0.0f; // 0.0f means use default board multiplier } void MyMesh::begin(FILESYSTEM *fs) { @@ -733,6 +739,8 @@ void MyMesh::begin(FILESYSTEM *fs) { updateAdvertTimer(); updateFloodAdvertTimer(); + board.setAdcMultiplier(_prefs.adc_multiplier); + #if ENV_INCLUDE_GPS == 1 applyGpsPrefs(); #endif diff --git a/examples/simple_repeater/MyMesh.h b/examples/simple_repeater/MyMesh.h index d8a20486..98bce787 100644 --- a/examples/simple_repeater/MyMesh.h +++ b/examples/simple_repeater/MyMesh.h @@ -113,7 +113,7 @@ class MyMesh : public mesh::Mesh, public CommonCLICallbacks { #endif void putNeighbour(const mesh::Identity& id, uint32_t timestamp, float snr); - uint8_t handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data); + uint8_t handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data, bool is_flood); int handleRequest(ClientInfo* sender, uint32_t sender_timestamp, uint8_t* payload, size_t payload_len); mesh::Packet* createSelfAdvert(); diff --git a/examples/simple_room_server/MyMesh.cpp b/examples/simple_room_server/MyMesh.cpp index de06b4c6..89505a3b 100644 --- a/examples/simple_room_server/MyMesh.cpp +++ b/examples/simple_room_server/MyMesh.cpp @@ -332,6 +332,10 @@ void MyMesh::onAnonDataRecv(mesh::Packet *packet, const uint8_t *secret, const m dirty_contacts_expiry = futureMillis(LAZY_CONTACTS_WRITE_DELAY); } + if (packet->isRouteFlood()) { + client->out_path_len = -1; // need to rediscover out_path + } + uint32_t now = getRTCClock()->getCurrentTimeUnique(); memcpy(reply_data, &now, 4); // response packets always prefixed with timestamp // TODO: maybe reply with count of messages waiting to be synced for THIS client? @@ -641,6 +645,8 @@ void MyMesh::begin(FILESYSTEM *fs) { updateAdvertTimer(); updateFloodAdvertTimer(); + board.setAdcMultiplier(_prefs.adc_multiplier); + #if ENV_INCLUDE_GPS == 1 applyGpsPrefs(); #endif diff --git a/examples/simple_sensor/SensorMesh.cpp b/examples/simple_sensor/SensorMesh.cpp index 20d9921b..6116c4de 100644 --- a/examples/simple_sensor/SensorMesh.cpp +++ b/examples/simple_sensor/SensorMesh.cpp @@ -326,7 +326,7 @@ int SensorMesh::getAGCResetInterval() const { return ((int)_prefs.agc_reset_interval) * 4000; // milliseconds } -uint8_t SensorMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data) { +uint8_t SensorMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data, bool is_flood) { ClientInfo* client; if (data[0] == 0) { // blank password, just check if sender is in ACL client = acl.getClient(sender.pub_key, PUB_KEY_SIZE); @@ -359,6 +359,10 @@ uint8_t SensorMesh::handleLoginReq(const mesh::Identity& sender, const uint8_t* dirty_contacts_expiry = futureMillis(LAZY_CONTACTS_WRITE_DELAY); } + if (is_flood) { + client->out_path_len = -1; // need to rediscover out_path + } + uint32_t now = getRTCClock()->getCurrentTimeUnique(); memcpy(reply_data, &now, 4); // response packets always prefixed with timestamp reply_data[4] = RESP_SERVER_LOGIN_OK; @@ -451,7 +455,7 @@ void SensorMesh::onAnonDataRecv(mesh::Packet* packet, const uint8_t* secret, con data[len] = 0; // ensure null terminator uint8_t reply_len; if (data[4] == 0 || data[4] >= ' ') { // is password, ie. a login request - reply_len = handleLoginReq(sender, secret, timestamp, &data[4]); + reply_len = handleLoginReq(sender, secret, timestamp, &data[4], packet->isRouteFlood()); //} else if (data[4] == ANON_REQ_TYPE_*) { // future type codes // TODO } else { @@ -740,6 +744,8 @@ void SensorMesh::begin(FILESYSTEM* fs) { updateAdvertTimer(); updateFloodAdvertTimer(); + board.setAdcMultiplier(_prefs.adc_multiplier); + #if ENV_INCLUDE_GPS == 1 applyGpsPrefs(); #endif diff --git a/examples/simple_sensor/SensorMesh.h b/examples/simple_sensor/SensorMesh.h index 00d9c698..627ef549 100644 --- a/examples/simple_sensor/SensorMesh.h +++ b/examples/simple_sensor/SensorMesh.h @@ -148,7 +148,7 @@ private: uint8_t pending_sf; uint8_t pending_cr; - uint8_t handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data); + uint8_t handleLoginReq(const mesh::Identity& sender, const uint8_t* secret, uint32_t sender_timestamp, const uint8_t* data, bool is_flood); uint8_t handleRequest(uint8_t perms, uint32_t sender_timestamp, uint8_t req_type, uint8_t* payload, size_t payload_len); mesh::Packet* createSelfAdvert(); diff --git a/src/MeshCore.h b/src/MeshCore.h index 94bf351d..11a6a5b4 100644 --- a/src/MeshCore.h +++ b/src/MeshCore.h @@ -42,6 +42,8 @@ namespace mesh { class MainBoard { public: virtual uint16_t getBattMilliVolts() = 0; + virtual bool setAdcMultiplier(float multiplier) { return false; }; + virtual float getAdcMultiplier() const { return 0.0f; } virtual const char* getManufacturerName() const = 0; virtual void onBeforeTransmit() { } virtual void onAfterTransmit() { } diff --git a/src/helpers/CommonCLI.cpp b/src/helpers/CommonCLI.cpp index 93773cce..17b2b753 100644 --- a/src/helpers/CommonCLI.cpp +++ b/src/helpers/CommonCLI.cpp @@ -70,7 +70,8 @@ void CommonCLI::loadPrefsInt(FILESYSTEM* fs, const char* filename) { file.read((uint8_t *)&_prefs->gps_interval, sizeof(_prefs->gps_interval)); // 157 file.read((uint8_t *)&_prefs->advert_loc_policy, sizeof (_prefs->advert_loc_policy)); // 161 file.read((uint8_t *)&_prefs->discovery_mod_timestamp, sizeof(_prefs->discovery_mod_timestamp)); // 162 - // 166 + file.read((uint8_t *)&_prefs->adc_multiplier, sizeof(_prefs->adc_multiplier)); // 166 + // 170 // sanitise bad pref values _prefs->rx_delay_base = constrain(_prefs->rx_delay_base, 0, 20.0f); @@ -83,6 +84,7 @@ void CommonCLI::loadPrefsInt(FILESYSTEM* fs, const char* filename) { _prefs->cr = constrain(_prefs->cr, 5, 8); _prefs->tx_power_dbm = constrain(_prefs->tx_power_dbm, 1, 30); _prefs->multi_acks = constrain(_prefs->multi_acks, 0, 1); + _prefs->adc_multiplier = constrain(_prefs->adc_multiplier, 0.0f, 10.0f); // sanitise bad bridge pref values _prefs->bridge_enabled = constrain(_prefs->bridge_enabled, 0, 1); @@ -148,7 +150,8 @@ void CommonCLI::savePrefs(FILESYSTEM* fs) { file.write((uint8_t *)&_prefs->gps_interval, sizeof(_prefs->gps_interval)); // 157 file.write((uint8_t *)&_prefs->advert_loc_policy, sizeof(_prefs->advert_loc_policy)); // 161 file.write((uint8_t *)&_prefs->discovery_mod_timestamp, sizeof(_prefs->discovery_mod_timestamp)); // 162 - // 166 + file.write((uint8_t *)&_prefs->adc_multiplier, sizeof(_prefs->adc_multiplier)); // 166 + // 170 file.close(); } @@ -331,6 +334,13 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch } else if (memcmp(config, "bridge.secret", 13) == 0) { sprintf(reply, "> %s", _prefs->bridge_secret); #endif + } else if (memcmp(config, "adc.multiplier", 14) == 0) { + float adc_mult = _board->getAdcMultiplier(); + if (adc_mult == 0.0f) { + strcpy(reply, "Error: unsupported by this board"); + } else { + sprintf(reply, "> %.3f", adc_mult); + } } else { sprintf(reply, "??: %s", config); } @@ -523,6 +533,19 @@ void CommonCLI::handleCommand(uint32_t sender_timestamp, const char* command, ch savePrefs(); strcpy(reply, "OK"); #endif + } else if (memcmp(config, "adc.multiplier ", 15) == 0) { + _prefs->adc_multiplier = atof(&config[15]); + if (_board->setAdcMultiplier(_prefs->adc_multiplier)) { + savePrefs(); + if (_prefs->adc_multiplier == 0.0f) { + strcpy(reply, "OK - using default board multiplier"); + } else { + sprintf(reply, "OK - multiplier set to %.3f", _prefs->adc_multiplier); + } + } else { + _prefs->adc_multiplier = 0.0f; + strcpy(reply, "Error: unsupported by this board"); + }; } else { sprintf(reply, "unknown config: %s", config); } diff --git a/src/helpers/CommonCLI.h b/src/helpers/CommonCLI.h index a665e014..068783ab 100644 --- a/src/helpers/CommonCLI.h +++ b/src/helpers/CommonCLI.h @@ -47,6 +47,7 @@ struct NodePrefs { // persisted to file uint32_t gps_interval; // in seconds uint8_t advert_loc_policy; uint32_t discovery_mod_timestamp; + float adc_multiplier; }; class CommonCLICallbacks { diff --git a/variants/promicro/PromicroBoard.h b/variants/promicro/PromicroBoard.h index e4b67415..dc20e550 100644 --- a/variants/promicro/PromicroBoard.h +++ b/variants/promicro/PromicroBoard.h @@ -23,6 +23,7 @@ class PromicroBoard : public mesh::MainBoard { protected: uint8_t startup_reason; uint8_t btn_prev_state; + float adc_mult = ADC_MULTIPLIER; public: void begin(); @@ -39,7 +40,23 @@ public: raw += analogRead(PIN_VBAT_READ); } raw = raw / BATTERY_SAMPLES; - return (ADC_MULTIPLIER * raw); + return (adc_mult * raw); + } + + bool setAdcMultiplier(float multiplier) override { + if (multiplier == 0.0f) { + adc_mult = ADC_MULTIPLIER;} + else { + adc_mult = multiplier; + } + return true; + } + float getAdcMultiplier() const override { + if (adc_mult == 0.0f) { + return ADC_MULTIPLIER; + } else { + return adc_mult; + } } const char* getManufacturerName() const override { diff --git a/variants/promicro/platformio.ini b/variants/promicro/platformio.ini index b1c0c4ea..78ea5fa1 100644 --- a/variants/promicro/platformio.ini +++ b/variants/promicro/platformio.ini @@ -1,9 +1,9 @@ -[Faketec] +[Promicro] extends = nrf52_base board = promicro_nrf52840 build_flags = ${nrf52_base.build_flags} -I variants/promicro - -D FAKETEC + -D PROMICRO -D RADIO_CLASS=CustomSX1262 -D WRAPPER_CLASS=CustomSX1262Wrapper -D LORA_TX_POWER=22 @@ -34,15 +34,15 @@ lib_deps= ${nrf52_base.lib_deps} adafruit/Adafruit BMP280 Library@^2.6.8 stevemarple/MicroNMEA @ ^2.0.6 -[env:Faketec_repeater] -extends = Faketec -build_src_filter = ${Faketec.build_src_filter} +[env:ProMicro_repeater] +extends = Promicro +build_src_filter = ${Promicro.build_src_filter} +<../examples/simple_repeater> + + build_flags = - ${Faketec.build_flags} - -D ADVERT_NAME='"Faketec Repeater"' + ${Promicro.build_flags} + -D ADVERT_NAME='"ProMicro Repeater"' -D ADVERT_LAT=0.0 -D ADVERT_LON=0.0 -D ADMIN_PASSWORD='"password"' @@ -50,17 +50,17 @@ build_flags = -D DISPLAY_CLASS=SSD1306Display ; -D MESH_PACKET_LOGGING=1 ; -D MESH_DEBUG=1 -lib_deps = ${Faketec.lib_deps} +lib_deps = ${Promicro.lib_deps} adafruit/RTClib @ ^2.1.3 -[env:Faketec_room_server] -extends = Faketec -build_src_filter = ${Faketec.build_src_filter} +[env:ProMicro_room_server] +extends = Promicro +build_src_filter = ${Promicro.build_src_filter} +<../examples/simple_room_server> + + -build_flags = ${Faketec.build_flags} - -D ADVERT_NAME='"Faketec Room"' +build_flags = ${Promicro.build_flags} + -D ADVERT_NAME='"ProMicro Room"' -D ADVERT_LAT=0.0 -D ADVERT_LON=0.0 -D ADMIN_PASSWORD='"password"' @@ -68,47 +68,47 @@ build_flags = ${Faketec.build_flags} -D DISPLAY_CLASS=SSD1306Display ; -D MESH_PACKET_LOGGING=1 ; -D MESH_DEBUG=1 -lib_deps = ${Faketec.lib_deps} +lib_deps = ${Promicro.lib_deps} adafruit/RTClib @ ^2.1.3 -[env:Faketec_terminal_chat] -extends = Faketec -build_flags = ${Faketec.build_flags} +[env:ProMicro_terminal_chat] +extends = Promicro +build_flags = ${Promicro.build_flags} -D MAX_CONTACTS=100 -D MAX_GROUP_CHANNELS=1 ; -D MESH_PACKET_LOGGING=1 ; -D MESH_DEBUG=1 -build_src_filter = ${Faketec.build_src_filter} +build_src_filter = ${Promicro.build_src_filter} +<../examples/simple_secure_chat/main.cpp> -lib_deps = ${Faketec.lib_deps} +lib_deps = ${Promicro.lib_deps} densaugeo/base64 @ ~1.4.0 adafruit/RTClib @ ^2.1.3 -[env:Faketec_companion_radio_usb] -extends = Faketec +[env:ProMicro_companion_radio_usb] +extends = Promicro board_build.ldscript = boards/nrf52840_s140_v6_extrafs.ld board_upload.maximum_size = 712704 -build_flags = ${Faketec.build_flags} +build_flags = ${Promicro.build_flags} -I examples/companion_radio/ui-new -D MAX_CONTACTS=350 -D MAX_GROUP_CHANNELS=40 -D DISPLAY_CLASS=SSD1306Display ; NOTE: DO NOT ENABLE --> -D MESH_PACKET_LOGGING=1 ; NOTE: DO NOT ENABLE --> -D MESH_DEBUG=1 -build_src_filter = ${Faketec.build_src_filter} +build_src_filter = ${Promicro.build_src_filter} + + +<../examples/companion_radio/*.cpp> +<../examples/companion_radio/ui-new/*.cpp> -lib_deps = ${Faketec.lib_deps} +lib_deps = ${Promicro.lib_deps} adafruit/RTClib @ ^2.1.3 densaugeo/base64 @ ~1.4.0 -[env:Faketec_companion_radio_ble] -extends = Faketec +[env:ProMicro_companion_radio_ble] +extends = Promicro board_build.ldscript = boards/nrf52840_s140_v6_extrafs.ld board_upload.maximum_size = 712704 -build_flags = ${Faketec.build_flags} +build_flags = ${Promicro.build_flags} -I examples/companion_radio/ui-new -D MAX_CONTACTS=350 -D MAX_GROUP_CHANNELS=40 @@ -118,30 +118,30 @@ build_flags = ${Faketec.build_flags} -D DISPLAY_CLASS=SSD1306Display ; -D MESH_PACKET_LOGGING=1 -D MESH_DEBUG=1 -build_src_filter = ${Faketec.build_src_filter} +build_src_filter = ${Promicro.build_src_filter} + + + +<../examples/companion_radio/*.cpp> +<../examples/companion_radio/ui-new/*.cpp> -lib_deps = ${Faketec.lib_deps} +lib_deps = ${Promicro.lib_deps} adafruit/RTClib @ ^2.1.3 densaugeo/base64 @ ~1.4.0 -[env:Faketec_sensor] -extends = Faketec +[env:ProMicro_sensor] +extends = Promicro build_flags = - ${Faketec.build_flags} - -D ADVERT_NAME='"Faketec Sensor"' + ${Promicro.build_flags} + -D ADVERT_NAME='"ProMicro Sensor"' -D ADVERT_LAT=0.0 -D ADVERT_LON=0.0 -D ADMIN_PASSWORD='"password"' -D DISPLAY_CLASS=SSD1306Display ; -D MESH_PACKET_LOGGING=1 ; -D MESH_DEBUG=1 -build_src_filter = ${Faketec.build_src_filter} +build_src_filter = ${Promicro.build_src_filter} + + +<../examples/simple_sensor> lib_deps = - ${Faketec.lib_deps} + ${Promicro.lib_deps}