From 57e1fd019832a55bfca0e3dc53fec97ca972de19 Mon Sep 17 00:00:00 2001 From: clawbot Date: Tue, 11 Aug 2026 13:14:35 +0000 Subject: [PATCH] fix: enforce the base58 checksum and reject non-master extended keys (closes #210) Two ways an xprv import could silently produce a wallet that is not the user's, with no error shown. Checksum: ethers' HDNodeWallet.fromExtendedKey skips base58 checksum verification when the decoded payload is the usual 82 bytes, which is exactly the case the checksum exists to catch. Every extended key now goes through parseExtendedKey, which re-encodes the parsed node and requires the round trip to reproduce the input exactly. Over every single-character substitution of the BIP-32 vector 1 master key, 199 parsed before and 0 parse now; the xpub path shared the hole (101 accepted typos) and is fixed by the same helper. Depth: hdWalletFromXprv and getSignerForAddress derived the relative path 44'/60'/0'/0, which is the BIP-44 Ethereum account path only for a depth-0 master key. Under an account-level (depth-3) key it derived m/44'/60'/0'/44'/60'/0'/0 instead of refusing. Both now derive the absolute BIP44_ETH_PATH from a key checked to be at depth 0. The extended-key format carries depth, parent fingerprint and child index but not the path a key sits at, so a non-master key cannot be placed in the tree without guessing; it is rejected, and the import screen says an account-level or child key is not supported. Import errors are full sentences per the README Language & Labeling rules, and the skipped one-character-typo test is unskipped. --- TODO.md | 4 + src/popup/index.html | 4 +- src/popup/views/addWallet.js | 16 +++- src/shared/wallet.js | 86 +++++++++++++++---- tests/wallet.test.js | 158 ++++++++++++++++++++++++++++++++--- 5 files changed, 238 insertions(+), 30 deletions(-) diff --git a/TODO.md b/TODO.md index 8b17986..985e5b6 100644 --- a/TODO.md +++ b/TODO.md @@ -57,6 +57,10 @@ undefined identifiers, which is how from the wallet row in Settings, wiped on leaving the screen and excluded from the views the popup can reopen onto ([#161](https://git.eeqj.de/sneak/AutistMask/issues/161)). +- 2026-08-11: Extended-key import hardened — the base58 checksum is now enforced + on every xprv and xpub, and a non-master key is refused with an explanation + instead of being derived beneath + ([#210](https://git.eeqj.de/sneak/AutistMask/issues/210)). - 2026-08-11: Policy compliance sweep — conditional verbose test rerun, local Tailwind binary instead of `npx`, `--frozen-lockfile` on `make install`, and the Makefile-only targets documented in the README diff --git a/src/popup/index.html b/src/popup/index.html index 361e864..b40e098 100644 --- a/src/popup/index.html +++ b/src/popup/index.html @@ -136,7 +136,9 @@