fix(companion): reset NaN/inf radio params before constrain() on load

constrain() is a min/max macro and NaN compares false against both bounds,
so a corrupted or layout-shifted prefs file that decodes a float field as
NaN/inf would pass it straight through to setParams() and could hang the
radio at boot (stuck after "Loading...", recoverable only by erasing flash).
Reset freq/bw/airtime_factor/rx_delay_base to safe defaults before the
existing constrain() so a non-finite value can never reach the driver.

Note: a defensive hardening of the boot path, not a confirmed root cause for
the reported brick.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
MarekZegare4
2026-06-23 02:03:19 +02:00
parent 9b4c8431c9
commit c935287627

View File

@@ -1407,7 +1407,14 @@ void MyMesh::begin(bool has_display) {
// load persisted prefs
_store->loadPrefs(_prefs, sensors.node_lat, sensors.node_lon);
// sanitise bad pref values
// sanitise bad pref values. NaN/inf must be reset BEFORE constrain(): constrain
// is a min/max macro and NaN compares false against both bounds, so it would
// pass a NaN straight through to setParams() and hang the radio (a corrupted or
// layout-shifted prefs file easily decodes a float field as NaN/inf).
if (isnan(_prefs.freq) || isinf(_prefs.freq)) _prefs.freq = LORA_FREQ;
if (isnan(_prefs.bw) || isinf(_prefs.bw)) _prefs.bw = LORA_BW;
if (isnan(_prefs.airtime_factor) || isinf(_prefs.airtime_factor)) _prefs.airtime_factor = 0;
if (isnan(_prefs.rx_delay_base) || isinf(_prefs.rx_delay_base)) _prefs.rx_delay_base = 0;
_prefs.rx_delay_base = constrain(_prefs.rx_delay_base, 0, 20.0f);
_prefs.airtime_factor = constrain(_prefs.airtime_factor, 0, 9.0f);
_prefs.freq = constrain(_prefs.freq, 150.0f, 2500.0f);