security: scrub on-screen secrets on lock; redact lite console secret args; no-shell wallet rebuild

- Locking the wallet (manual / auto / lite) now calls wipeDisplayedSecrets(),
  which scrubs + closes any revealed seed phrase, migration seed, or exported
  key — previously a locked wallet could leave the phrase/key on screen and
  resident. Runs synchronously, before the async lock round-trip.
- The console secret-arg redaction list only had full-node RPC names, so lite
  verbs (import / timport / encrypt / decrypt / unlock) echoed keys and
  passphrases into the scrollback and up-arrow history; added them.
- The offline wallet-rebuild helper was invoked via a shell string
  (popen "sh -c") built from paths including the wallet filename, so a crafted
  name could inject a command; it now refuses any path with a shell
  metacharacter (rc stays -1 and the existing verify-before-swap fails safe).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
2026-10-19 09:28:25 -05:00
co-authored by Claude Opus 4.8
parent dc1617a2c1
commit 6b0f2eda22
5 changed files with 40 additions and 2 deletions
+4
View File
@@ -15,6 +15,10 @@ const char* const kSecretConsoleCommands[] = {
"importprivkey", "importwallet", "importmulti",
"z_importkey", "z_importviewingkey", "z_importwallet",
"signrawtransaction", "magicrecoverkey", "sethdseed", "importmnemonic",
// Lite-wallet verbs (console_command_reference kLiteKeyCommands): these take a spending/viewing key
// or a password as their argument. Full-node has no bare import/encrypt/decrypt/unlock verb, so a
// flat match is safe.
"import", "timport", "encrypt", "decrypt", "unlock",
};
std::string firstConsoleTokenLower(const std::string& cmd, size_t& tokenEnd) {