Merge branch 'master' into use_detected_ina_addr

This commit is contained in:
Michael Gjelsø 2025-07-07 15:42:18 +02:00 committed by GitHub
commit dc8b7a2b63
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
21 changed files with 248 additions and 79 deletions

View File

@ -9,14 +9,14 @@ plugins:
lint:
enabled:
- checkov@3.2.447
- renovate@41.17.2
- renovate@41.19.0
- prettier@3.6.2
- trufflehog@3.89.2
- yamllint@1.37.1
- bandit@1.8.5
- trivy@0.64.0
- trivy@0.64.1
- taplo@0.9.3
- ruff@0.12.1
- ruff@0.12.2
- isort@6.0.1
- markdownlint@0.45.0
- oxipng@9.1.5

View File

@ -49,13 +49,13 @@ lib_deps =
${environmental_extra.lib_deps}
${radiolib_base.lib_deps}
# renovate: datasource=git-refs depName=meshtastic-esp32_https_server packageName=https://github.com/meshtastic/esp32_https_server gitBranch=master
https://github.com/meshtastic/esp32_https_server/archive/896f1771ceb5979987a0b41028bf1b4e7aad419b.zip
https://github.com/meshtastic/esp32_https_server/archive/3223704846752e6d545139204837bdb2a55459ca.zip
# renovate: datasource=custom.pio depName=NimBLE-Arduino packageName=h2zero/library/NimBLE-Arduino
h2zero/NimBLE-Arduino@^1.4.3
# renovate: datasource=git-refs depName=libpax packageName=https://github.com/dbinfrago/libpax gitBranch=master
https://github.com/dbinfrago/libpax/archive/3cdc0371c375676a97967547f4065607d4c53fd1.zip
# renovate: datasource=custom.pio depName=XPowersLib packageName=lewisxhe/library/XPowersLib
lewisxhe/XPowersLib@^0.2.7
lewisxhe/XPowersLib@0.3.0
# renovate: datasource=git-refs depName=meshtastic-ESP32_Codec2 packageName=https://github.com/meshtastic/ESP32_Codec2 gitBranch=master
https://github.com/meshtastic/ESP32_Codec2/archive/633326c78ac251c059ab3a8c430fcdf25b41672f.zip
# renovate: datasource=custom.pio depName=rweather/Crypto packageName=rweather/library/Crypto

View File

@ -28,7 +28,7 @@ lib_deps =
${environmental_extra.lib_deps}
${radiolib_base.lib_deps}
# renovate: datasource=custom.pio depName=XPowersLib packageName=lewisxhe/library/XPowersLib
lewisxhe/XPowersLib@^0.2.7
lewisxhe/XPowersLib@0.3.0
# renovate: datasource=git-refs depName=meshtastic-ESP32_Codec2 packageName=https://github.com/meshtastic/ESP32_Codec2 gitBranch=master
https://github.com/meshtastic/ESP32_Codec2/archive/633326c78ac251c059ab3a8c430fcdf25b41672f.zip
# renovate: datasource=custom.pio depName=rweather/Crypto packageName=rweather/library/Crypto

View File

@ -30,6 +30,18 @@ Flash image file to device, leave existing system intact."
EOF
}
# Check for --change-mode and remove it from arguments
NEW_ARGS=""
for arg in "$@"; do
if [ "$arg" = "--change-mode" ]; then
CHANGE_MODE=true
else
NEW_ARGS="$NEW_ARGS \"\$arg\""
fi
done
# Reset positional parameters to filtered list
eval set -- $NEW_ARGS
while getopts ":hp:P:f:" opt; do
case "${opt}" in
@ -43,9 +55,6 @@ while getopts ":hp:P:f:" opt; do
;;
f) FILENAME=${OPTARG}
;;
--change-mode)
CHANGE_MODE=true
;;
*)
echo "Invalid flag."
show_help >&2
@ -55,7 +64,7 @@ while getopts ":hp:P:f:" opt; do
done
shift "$((OPTIND-1))"
if [[ $CHANGE_MODE == true ]]; then
if [ "$CHANGE_MODE" = true ]; then
$ESPTOOL_CMD --baud 1200 --after no_reset read_flash_status
exit 0
fi

View File

@ -87,6 +87,9 @@
</screenshots>
<releases>
<release version="2.7.2" date="2025-07-04">
<url type="details">https://github.com/meshtastic/firmware/releases?q=tag%3Av2.7.2</url>
</release>
<release version="2.7.1" date="2025-06-27">
<url type="details">https://github.com/meshtastic/firmware/releases?q=tag%3Av2.7.1</url>
</release>

View File

@ -11,7 +11,8 @@
["0x239A", "0x8029"],
["0x239A", "0x0029"],
["0x239A", "0x002A"],
["0x239A", "0x802A"]
["0x239A", "0x802A"],
["0x2886", "0x0057"]
],
"usb_product": "T1000-E-BOOT",
"mcu": "nrf52840",

7
debian/changelog vendored
View File

@ -1,4 +1,4 @@
meshtasticd (2.7.1.0) UNRELEASED; urgency=medium
meshtasticd (2.7.2.0) UNRELEASED; urgency=medium
[ Austin Lane ]
* Initial packaging
@ -25,4 +25,7 @@ meshtasticd (2.7.1.0) UNRELEASED; urgency=medium
[ ]
* GitHub Actions Automatic version bump
-- <github-actions[bot]@users.noreply.github.com> Fri, 27 Jun 2025 20:12:21 +0000
[ ]
* GitHub Actions Automatic version bump
-- <github-actions[bot]@users.noreply.github.com> Fri, 04 Jul 2025 11:58:01 +0000

View File

@ -109,7 +109,7 @@ lib_deps =
[device-ui_base]
lib_deps =
# renovate: datasource=git-refs depName=meshtastic/device-ui packageName=https://github.com/meshtastic/device-ui gitBranch=master
https://github.com/meshtastic/device-ui/archive/4b7bf369adfa5a7bd419fa8293d21206576d52d0.zip
https://github.com/meshtastic/device-ui/archive/8c7092c73425adfda1aac8c6960df06cd85f6d92.zip
; Common libs for environmental measurements in telemetry module
[environmental_base]

View File

@ -1373,6 +1373,8 @@ int Screen::handleInputEvent(const InputEvent *event)
this->ui->getUiState()->currentFrame == framesetInfo.positions.nodelist_hopsignal ||
this->ui->getUiState()->currentFrame == framesetInfo.positions.nodelist_bearings) {
menuHandler::nodeListMenu();
} else if (this->ui->getUiState()->currentFrame == framesetInfo.positions.wifi) {
menuHandler::wifiBaseMenu();
}
} else if (event->inputEvent == INPUT_BROKER_BACK) {
showPrevFrame();

View File

@ -99,10 +99,17 @@ void drawCommonHeader(OLEDDisplay *display, int16_t x, int16_t y, const char *ti
// === Battery State ===
int chargePercent = powerStatus->getBatteryChargePercent();
bool isCharging = powerStatus->getIsCharging() == meshtastic::OptionalBool::OptTrue;
if (chargePercent == 100) {
bool isCharging = powerStatus->getIsCharging();
bool usbPowered = powerStatus->getHasUSB();
if (chargePercent >= 100) {
isCharging = false;
}
if (chargePercent == 101) {
usbPowered = true; // Forcing this flag on for the express purpose that some devices have no concept of having a USB cable
// plugged in
}
uint32_t now = millis();
#ifndef USE_EINK
@ -115,48 +122,63 @@ void drawCommonHeader(OLEDDisplay *display, int16_t x, int16_t y, const char *ti
bool useHorizontalBattery = (isHighResolution && screenW >= screenH);
const int textY = y + (highlightHeight - FONT_HEIGHT_SMALL) / 2;
int batteryX = 1;
int batteryY = HEADER_OFFSET_Y + 1;
// === Battery Icons ===
if (useHorizontalBattery) {
int batteryX = 2;
int batteryY = HEADER_OFFSET_Y + 3;
display->drawXbm(batteryX, batteryY, 9, 13, batteryBitmap_h_bottom);
display->drawXbm(batteryX + 9, batteryY, 9, 13, batteryBitmap_h_top);
if (isCharging && isBoltVisibleShared)
display->drawXbm(batteryX + 4, batteryY, 9, 13, lightning_bolt_h);
else {
display->drawLine(batteryX + 5, batteryY, batteryX + 10, batteryY);
display->drawLine(batteryX + 5, batteryY + 12, batteryX + 10, batteryY + 12);
int fillWidth = 14 * chargePercent / 100;
display->fillRect(batteryX + 1, batteryY + 1, fillWidth, 11);
if (usbPowered && !isCharging) { // This is a basic check to determine USB Powered is flagged but not charging
batteryX += 1;
batteryY += 2;
if (isHighResolution) {
display->drawXbm(batteryX, batteryY, 19, 12, imgUSB_HighResolution);
batteryX += 20; // Icon + 1 pixel
} else {
display->drawXbm(batteryX, batteryY, 10, 8, imgUSB);
batteryX += 11; // Icon + 1 pixel
}
} else {
int batteryX = 1;
int batteryY = HEADER_OFFSET_Y + 1;
if (useHorizontalBattery) {
batteryX += 1;
batteryY += 2;
display->drawXbm(batteryX, batteryY, 9, 13, batteryBitmap_h_bottom);
display->drawXbm(batteryX + 9, batteryY, 9, 13, batteryBitmap_h_top);
if (isCharging && isBoltVisibleShared)
display->drawXbm(batteryX + 4, batteryY, 9, 13, lightning_bolt_h);
else {
display->drawLine(batteryX + 5, batteryY, batteryX + 10, batteryY);
display->drawLine(batteryX + 5, batteryY + 12, batteryX + 10, batteryY + 12);
int fillWidth = 14 * chargePercent / 100;
display->fillRect(batteryX + 1, batteryY + 1, fillWidth, 11);
}
batteryX += 18; // Icon + 2 pixels
} else {
#ifdef USE_EINK
batteryY += 2;
batteryY += 2;
#endif
display->drawXbm(batteryX, batteryY, 7, 11, batteryBitmap_v);
if (isCharging && isBoltVisibleShared)
display->drawXbm(batteryX + 1, batteryY + 3, 5, 5, lightning_bolt_v);
else {
display->drawXbm(batteryX - 1, batteryY + 4, 8, 3, batteryBitmap_sidegaps_v);
int fillHeight = 8 * chargePercent / 100;
int fillY = batteryY - fillHeight;
display->fillRect(batteryX + 1, fillY + 10, 5, fillHeight);
display->drawXbm(batteryX, batteryY, 7, 11, batteryBitmap_v);
if (isCharging && isBoltVisibleShared)
display->drawXbm(batteryX + 1, batteryY + 3, 5, 5, lightning_bolt_v);
else {
display->drawXbm(batteryX - 1, batteryY + 4, 8, 3, batteryBitmap_sidegaps_v);
int fillHeight = 8 * chargePercent / 100;
int fillY = batteryY - fillHeight;
display->fillRect(batteryX + 1, fillY + 10, 5, fillHeight);
}
batteryX += 9; // Icon + 2 pixels
}
}
// === Battery % Display ===
char chargeStr[4];
snprintf(chargeStr, sizeof(chargeStr), "%d", chargePercent);
int chargeNumWidth = display->getStringWidth(chargeStr);
const int batteryOffset = useHorizontalBattery ? 19 : 9;
const int percentX = x + batteryOffset;
display->drawString(percentX, textY, chargeStr);
display->drawString(percentX + chargeNumWidth - 1, textY, "%");
if (isBold) {
display->drawString(percentX + 1, textY, chargeStr);
display->drawString(percentX + chargeNumWidth, textY, "%");
if (chargePercent != 101) {
// === Battery % Display ===
char chargeStr[4];
snprintf(chargeStr, sizeof(chargeStr), "%d", chargePercent);
int chargeNumWidth = display->getStringWidth(chargeStr);
display->drawString(batteryX, textY, chargeStr);
display->drawString(batteryX + chargeNumWidth - 1, textY, "%");
if (isBold) {
display->drawString(batteryX + 1, textY, chargeStr);
display->drawString(batteryX + chargeNumWidth, textY, "%");
}
}
// === Time and Right-aligned Icons ===

View File

@ -283,6 +283,9 @@ void drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *state, int1
xOffset += (isHighResolution) ? 32 : 18;
}
int yOffset = (isHighResolution) ? 3 : 1;
#ifdef SENSECAP_INDICATOR
yOffset -= 3;
#endif
if (config.display.use_12h_clock) {
display->drawString(startingHourMinuteTextX + xOffset, (display->getHeight() - hourMinuteTextY) - yOffset - 2,
isPM ? "pm" : "am");

View File

@ -48,12 +48,14 @@ void menuHandler::LoraRegionPicker(uint32_t duration)
"PH_433",
"PH_868",
"PH_915",
"ANZ_433"};
"ANZ_433",
"KZ_433",
"KZ_863"};
BannerOverlayOptions bannerOptions;
bannerOptions.message = "Set the LoRa region";
bannerOptions.durationMs = duration;
bannerOptions.optionsArrayPtr = optionsArray;
bannerOptions.optionsCount = 23;
bannerOptions.optionsCount = 25;
bannerOptions.InitialSelected = 0;
bannerOptions.bannerCallback = [](int selected) -> void {
if (selected != 0 && config.lora.region != _meshtastic_Config_LoRaConfig_RegionCode(selected)) {
@ -602,32 +604,28 @@ void menuHandler::BuzzerModeMenu()
void menuHandler::BrightnessPickerMenu()
{
static const char *optionsArray[] = {"Back", "Low", "Medium", "High", "Very High"};
static const char *optionsArray[] = {"Back", "Low", "Medium", "High"};
// Get current brightness level to set initial selection
int currentSelection = 1; // Default to Low
int currentSelection = 1; // Default to Medium
if (uiconfig.screen_brightness >= 255) {
currentSelection = 4; // Very High
currentSelection = 3; // Very High
} else if (uiconfig.screen_brightness >= 128) {
currentSelection = 3; // High
} else if (uiconfig.screen_brightness >= 64) {
currentSelection = 2; // Medium
currentSelection = 2; // High
} else {
currentSelection = 1; // Low
currentSelection = 1; // Medium
}
BannerOverlayOptions bannerOptions;
bannerOptions.message = "Brightness";
bannerOptions.optionsArrayPtr = optionsArray;
bannerOptions.optionsCount = 5;
bannerOptions.optionsCount = 4;
bannerOptions.bannerCallback = [](int selected) -> void {
if (selected == 1) { // Low
uiconfig.screen_brightness = 1;
} else if (selected == 2) { // Medium
if (selected == 1) { // Medium
uiconfig.screen_brightness = 64;
} else if (selected == 3) { // High
} else if (selected == 2) { // High
uiconfig.screen_brightness = 128;
} else if (selected == 4) { // Very High
} else if (selected == 3) { // Very High
uiconfig.screen_brightness = 255;
}
@ -833,6 +831,44 @@ void menuHandler::numberTest()
[](int number_picked) -> void { LOG_WARN("Nodenum: %u", number_picked); });
}
void menuHandler::wifiBaseMenu()
{
enum optionsNumbers { Back, Wifi_toggle };
static const char *optionsArray[] = {"Back", "WiFi Toggle"};
BannerOverlayOptions bannerOptions;
bannerOptions.message = "WiFi Menu";
bannerOptions.optionsArrayPtr = optionsArray;
bannerOptions.optionsCount = 2;
bannerOptions.bannerCallback = [](int selected) -> void {
if (selected == Wifi_toggle) {
menuQueue = wifi_toggle_menu;
screen->runNow();
}
};
screen->showOverlayBanner(bannerOptions);
}
void menuHandler::wifiToggleMenu()
{
enum optionsNumbers { Back, Wifi_toggle };
static const char *optionsArray[] = {"Back", "Disable"};
BannerOverlayOptions bannerOptions;
bannerOptions.message = "Disable Wifi and\nEnable Bluetooth?";
bannerOptions.optionsArrayPtr = optionsArray;
bannerOptions.optionsCount = 2;
bannerOptions.bannerCallback = [](int selected) -> void {
if (selected == Wifi_toggle) {
config.network.wifi_enabled = false;
config.bluetooth.enabled = true;
service->reloadConfig(SEGMENT_CONFIG);
rebootAtMsec = (millis() + DEFAULT_REBOOT_SECONDS * 1000);
}
};
screen->showOverlayBanner(bannerOptions);
}
void menuHandler::handleMenuSwitch(OLEDDisplay *display)
{
if (menuQueue != menu_none)
@ -896,6 +932,9 @@ void menuHandler::handleMenuSwitch(OLEDDisplay *display)
case number_test:
numberTest();
break;
case wifi_toggle_menu:
wifiToggleMenu();
break;
}
menuQueue = menu_none;
}

View File

@ -13,9 +13,7 @@ class menuHandler
clock_face_picker,
clock_menu,
position_base_menu,
#if !MESHTASTIC_EXCLUDE_GPS
gps_toggle_menu,
#endif
compass_point_north_menu,
reset_node_db_menu,
buzzermodemenupicker,
@ -26,7 +24,8 @@ class menuHandler
add_favorite,
remove_favorite,
test_menu,
number_test
number_test,
wifi_toggle_menu
};
static screenMenus menuQueue;
@ -54,6 +53,8 @@ class menuHandler
static void removeFavoriteMenu();
static void testMenu();
static void numberTest();
static void wifiBaseMenu();
static void wifiToggleMenu();
};
} // namespace graphics

View File

@ -12,7 +12,10 @@ const uint8_t imgSatellite[] PROGMEM = {
0b00000000, 0b00000000, 0b00000000, 0b00011000, 0b11011011, 0b11111111, 0b11011011, 0b00011000,
};
const uint8_t imgUSB[] PROGMEM = {0x60, 0x60, 0x30, 0x18, 0x18, 0x18, 0x24, 0x42, 0x42, 0x42, 0x42, 0x7E, 0x24, 0x24, 0x24, 0x3C};
const uint8_t imgUSB[] PROGMEM = {0x00, 0xfc, 0xf0, 0xfc, 0x88, 0xff, 0x86, 0xfe, 0x85, 0xfe, 0x89, 0xff, 0xf1, 0xfc, 0x00, 0xfc};
const uint8_t imgUSB_HighResolution[] PROGMEM = {0x00, 0x3e, 0xf8, 0x80, 0x43, 0xf8, 0xc0, 0xc2, 0xff, 0x60, 0x42, 0xfc,
0x3c, 0xc2, 0xff, 0x22, 0x42, 0xf8, 0x3d, 0x42, 0xf8, 0x22, 0xc2, 0xff,
0x61, 0x42, 0xfc, 0xc0, 0xc2, 0xff, 0x80, 0x43, 0xf8, 0x00, 0x3e, 0xf8};
const uint8_t imgPower[] PROGMEM = {0x40, 0x40, 0x40, 0x58, 0x48, 0x08, 0x08, 0x08,
0x1C, 0x22, 0x22, 0x41, 0x7F, 0x22, 0x22, 0x22};
const uint8_t imgUser[] PROGMEM = {0x3C, 0x42, 0x99, 0xA5, 0xA5, 0x99, 0x42, 0x3C};

View File

@ -52,6 +52,40 @@ void InkHUD::LogoApplet::onRender()
setTextColor(WHITE);
}
#ifdef USERPREFS_OEM_IMAGE_DATA // Custom boot screen, if defined in userPrefs.jsonc
// Only show the custom screen at startup
// This allows us to draw the usual Meshtastic logo at shutdown
// The effect is similar to the two-stage userPrefs boot screen used by BaseUI
if (millis() < 10 * 1000UL) {
// Draw the custom logo
const uint8_t logo[] = USERPREFS_OEM_IMAGE_DATA;
drawXBitmap(logoCX - (USERPREFS_OEM_IMAGE_WIDTH / 2), // Left
logoCY - (USERPREFS_OEM_IMAGE_HEIGHT / 2), // Top
logo, // XBM data
USERPREFS_OEM_IMAGE_WIDTH, // Width
USERPREFS_OEM_IMAGE_HEIGHT, // Height
inverted ? WHITE : BLACK // Color
);
// Select the largest font which will still comfortably fit the custom text
setFont(fontLarge);
if (getTextWidth(USERPREFS_OEM_TEXT) > 0.8 * width())
setFont(fontMedium);
if (getTextWidth(USERPREFS_OEM_TEXT) > 0.8 * width())
setFont(fontSmall);
// Draw custom text below logo
int16_t logoB = logoCY + (USERPREFS_OEM_IMAGE_HEIGHT / 2); // Bottom of the logo
printAt(X(0.5), logoB + Y(0.1), USERPREFS_OEM_TEXT, CENTER, TOP);
// Don't draw the normal boot screen, we've already drawn our custom version
return;
}
#endif
drawLogo(logoCX, logoCY, logoW, logoH, inverted ? WHITE : BLACK);
if (!textLeft.empty()) {

View File

@ -369,6 +369,14 @@ NodeDB::NodeDB()
config.device.rebroadcast_mode = meshtastic_Config_DeviceConfig_RebroadcastMode_LOCAL_ONLY;
}
#if !HAS_TFT
if (config.display.displaymode == meshtastic_Config_DisplayConfig_DisplayMode_COLOR) {
// On a device without MUI, this display mode makes no sense, and will break logic.
config.display.displaymode = meshtastic_Config_DisplayConfig_DisplayMode_DEFAULT;
config.bluetooth.enabled = true;
}
#endif
if (devicestateCRC != crc32Buffer(&devicestate, sizeof(devicestate)))
saveWhat |= SEGMENT_DEVICESTATE;
if (nodeDatabaseCRC != crc32Buffer(&nodeDatabase, sizeof(nodeDatabase)))

View File

@ -161,6 +161,14 @@ const RegionInfo regions[] = {
RDEF(PH_433, 433.0f, 434.7f, 100, 0, 10, true, false, false), RDEF(PH_868, 868.0f, 869.4f, 100, 0, 14, true, false, false),
RDEF(PH_915, 915.0f, 918.0f, 100, 0, 24, true, false, false),
/*
Kazakhstan
433.075 - 434.775 MHz <10 mW EIRP, Low Powered Devices (LPD)
863 - 868 MHz <25 mW EIRP, 500kHz channels allowed, must not be used at airfields
https://github.com/meshtastic/firmware/issues/7204
*/
RDEF(KZ_433, 433.075f, 434.775f, 100, 0, 10, true, false, false), RDEF(KZ_863, 863.0f, 868.0f, 100, 0, 30, true, false, true),
/*
2.4 GHZ WLAN Band equivalent. Only for SX128x chips.
*/
@ -637,10 +645,6 @@ void RadioInterface::limitPower(int8_t loraMaxPower)
if (power > loraMaxPower) // Clamp power to maximum defined level
power = loraMaxPower;
if (TX_GAIN_LORA == 0) { // Setting power in config with defined TX_GAIN_LORA will cause decreasing power on each reboot
config.lora.tx_power = power; // Set limited power in config
}
LOG_INFO("Final Tx power: %d dBm", power);
}
@ -681,4 +685,4 @@ size_t RadioInterface::beginSending(meshtastic_MeshPacket *p)
sendingPacket = p;
return p->encrypted.size + sizeof(PacketHeader);
}
}

View File

@ -10,6 +10,32 @@
#include "aes-ccm.h"
#if !MESHTASTIC_EXCLUDE_PKI
/**
* Constant-time comparison of two byte arrays
*
* @param a First byte array to compare
* @param b Second byte array to compare
* @param len Number of bytes to compare
* @return 0 if arrays are equal, -1 if different or if inputs are invalid
*/
static int constant_time_compare(const void *a_, const void *b_, size_t len)
{
/* Cast to volatile to prevent the compiler from optimizing out their comparison. */
const volatile uint8_t *volatile a = (const volatile uint8_t *volatile)a_;
const volatile uint8_t *volatile b = (const volatile uint8_t *volatile)b_;
if (len == 0)
return 0;
if (a == NULL || b == NULL)
return -1;
size_t i;
volatile uint8_t d = 0U;
for (i = 0U; i < len; i++) {
d |= (a[i] ^ b[i]);
}
/* Constant time bit arithmetic to convert d > 0 to -1 and d = 0 to 0. */
return (1 & ((d - 1) >> 8)) - 1;
}
static void WPA_PUT_BE16(uint8_t *a, uint16_t val)
{
a[0] = val >> 8;
@ -146,7 +172,7 @@ bool aes_ccm_ad(const uint8_t *key, size_t key_len, const uint8_t *nonce, size_t
aes_ccm_encr(L, crypt, crypt_len, plain, a);
aes_ccm_auth_start(M, L, nonce, aad, aad_len, crypt_len, x);
aes_ccm_auth(plain, crypt_len, x);
if (memcmp(x, t, M) != 0) { // FIXME make const comp
if (constant_time_compare(x, t, M) != 0) {
return false;
}
return true;

View File

@ -630,6 +630,7 @@ void AdminModule::handleSetConfig(const meshtastic_Config &c)
#if USERPREFS_EVENT_MODE
// If we're in event mode, nobody is a Router or Repeater
if (config.device.role == meshtastic_Config_DeviceConfig_Role_ROUTER ||
config.device.role == meshtastic_Config_DeviceConfig_Role_ROUTER_LATE ||
config.device.role == meshtastic_Config_DeviceConfig_Role_REPEATER) {
config.device.role = meshtastic_Config_DeviceConfig_Role_CLIENT;
}

View File

@ -29,6 +29,7 @@ class BluetoothPhoneAPI : public PhoneAPI, public concurrency::OSThread
uint8_t fromRadioBytes[meshtastic_FromRadio_size] = {0};
size_t numBytes = 0;
bool hasChecked = false;
bool phoneWants = false;
protected:
virtual int32_t runOnce() override
@ -38,10 +39,10 @@ class BluetoothPhoneAPI : public PhoneAPI, public concurrency::OSThread
for (uint8_t i = 0; i < queue_size; i++) {
handleToRadio(nimble_queue.at(i).data(), nimble_queue.at(i).length());
}
LOG_WARN("Queue_size %u", queue_size);
LOG_DEBUG("Queue_size %u", queue_size);
queue_size = 0;
}
if (hasChecked == false) {
if (hasChecked == false && phoneWants == true) {
numBytes = getFromRadio(fromRadioBytes);
hasChecked = true;
}
@ -98,9 +99,12 @@ class NimbleBluetoothFromRadioCallback : public NimBLECharacteristicCallbacks
{
virtual void onRead(NimBLECharacteristic *pCharacteristic)
{
while (!bluetoothPhoneAPI->hasChecked) {
int tries = 0;
bluetoothPhoneAPI->phoneWants = true;
while (!bluetoothPhoneAPI->hasChecked && tries < 100) {
bluetoothPhoneAPI->setIntervalFromNow(0);
delay(20);
tries++;
}
std::lock_guard<std::mutex> guard(bluetoothPhoneAPI->nimble_mutex);
std::string fromRadioByteString(bluetoothPhoneAPI->fromRadioBytes,
@ -111,6 +115,7 @@ class NimbleBluetoothFromRadioCallback : public NimBLECharacteristicCallbacks
bluetoothPhoneAPI->setIntervalFromNow(0);
bluetoothPhoneAPI->numBytes = 0;
bluetoothPhoneAPI->hasChecked = false;
bluetoothPhoneAPI->phoneWants = false;
}
};
@ -186,7 +191,12 @@ class NimbleBluetoothServerCallback : public NimBLEServerCallbacks
new meshtastic::BluetoothStatus(meshtastic::BluetoothStatus::ConnectionState::DISCONNECTED));
if (bluetoothPhoneAPI) {
std::lock_guard<std::mutex> guard(bluetoothPhoneAPI->nimble_mutex);
bluetoothPhoneAPI->close();
bluetoothPhoneAPI->hasChecked = false;
bluetoothPhoneAPI->phoneWants = false;
bluetoothPhoneAPI->numBytes = 0;
bluetoothPhoneAPI->queue_size = 0;
}
}
};

View File

@ -1,4 +1,4 @@
[VERSION]
major = 2
minor = 7
build = 1
build = 2