Fix 4 bugs found in code review

- BotScreen keyboard: add explicit null-terminator after strncpy when
  trigger/reply text reaches max length (strncpy skips it in that case)
- BotScreen keyboard: clamp _kb_col to 3 when moving DOWN to special row,
  so the cursor doesn't become invisible (col > 3 has no special-row item)
- MyMesh: initialise _bot_last_reply_ms = 0 in constructor (was relying on
  BSS zero-init, which is technically UB for a non-trivial class member)
- RingtoneEditor: exit via CANCEL/Save/Discard goes to ToolsScreen instead
  of HomeScreen — consistent with BotScreen and expected navigation flow

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Jakub
2026-05-13 21:09:47 +02:00
co-authored by Claude Sonnet 4.6
parent 58afc23df3
commit 9756bb062c
2 changed files with 14 additions and 6 deletions
+1
View File
@@ -871,6 +871,7 @@ MyMesh::MyMesh(mesh::Radio &radio, mesh::RNG &rng, mesh::RTCClock &rtc, SimpleMe
_cli_rescue = false; _cli_rescue = false;
offline_queue_len = 0; offline_queue_len = 0;
app_target_ver = 0; app_target_ver = 0;
_bot_last_reply_ms = 0;
clearPendingReqs(); clearPendingReqs();
next_ack_idx = 0; next_ack_idx = 0;
sign_data = NULL; sign_data = NULL;
+13 -6
View File
@@ -2021,18 +2021,18 @@ public:
the_mesh.savePrefs(); the_mesh.savePrefs();
} }
_task->stopMelody(); _task->stopMelody();
_task->gotoHomeScreen(); _task->gotoToolsScreen();
break; break;
case M_DISCARD: case M_DISCARD:
_task->stopMelody(); _task->stopMelody();
_task->gotoHomeScreen(); _task->gotoToolsScreen();
break; break;
default: break; default: break;
} }
return true; return true;
} }
if (cancel) { _task->stopMelody(); _task->gotoHomeScreen(); return true; } if (cancel) { _task->stopMelody(); _task->gotoToolsScreen(); return true; }
if (menu_key) { _menu_open = true; _menu_sel = 0; _menu_scroll = 0; return true; } if (menu_key) { _menu_open = true; _menu_sel = 0; _menu_scroll = 0; return true; }
if (left && _cursor > 0) { _cursor--; clampScroll(); return true; } if (left && _cursor > 0) { _cursor--; clampScroll(); return true; }
@@ -2245,7 +2245,11 @@ public:
// keyboard input // keyboard input
if (cancel) { _kb_field = -1; return true; } if (cancel) { _kb_field = -1; return true; }
if (up && _kb_row > 0) { _kb_row--; return true; } if (up && _kb_row > 0) { _kb_row--; return true; }
if (down && _kb_row < KB_ROWS) { _kb_row++; return true; } if (down && _kb_row < KB_ROWS) {
_kb_row++;
if (_kb_row == KB_ROWS && _kb_col > 3) _kb_col = 3;
return true;
}
if (left && _kb_col > 0) { _kb_col--; return true; } if (left && _kb_col > 0) { _kb_col--; return true; }
if (right && _kb_col < (_kb_row < KB_ROWS ? KB_COLS - 1 : 3)) { _kb_col++; return true; } if (right && _kb_col < (_kb_row < KB_ROWS ? KB_COLS - 1 : 3)) { _kb_col++; return true; }
if (enter) { if (enter) {
@@ -2265,10 +2269,13 @@ public:
case 2: if (_kb_len > 0) { _kb_buf[--_kb_len] = '\0'; } break; case 2: if (_kb_len > 0) { _kb_buf[--_kb_len] = '\0'; } break;
case 3: case 3:
// commit // commit
if (_kb_field == 2) if (_kb_field == 2) {
strncpy(_prefs->bot_trigger, _kb_buf, sizeof(_prefs->bot_trigger) - 1); strncpy(_prefs->bot_trigger, _kb_buf, sizeof(_prefs->bot_trigger) - 1);
else _prefs->bot_trigger[sizeof(_prefs->bot_trigger) - 1] = '\0';
} else {
strncpy(_prefs->bot_reply, _kb_buf, sizeof(_prefs->bot_reply) - 1); strncpy(_prefs->bot_reply, _kb_buf, sizeof(_prefs->bot_reply) - 1);
_prefs->bot_reply[sizeof(_prefs->bot_reply) - 1] = '\0';
}
_kb_field = -1; _kb_field = -1;
break; break;
} }