Refresh checkpoint with key zeroization
This commit is contained in:
parent
130d7e29bc
commit
d90b6e53d4
1 changed files with 29 additions and 13 deletions
|
|
@ -1,4 +1,4 @@
|
|||
# Checkpoint — Owner-only-from-first-byte file writes (2026-08-21)
|
||||
# Checkpoint — Key material zeroization (2026-08-21)
|
||||
|
||||
A stopping point you can return to if this session is closed. Everything below was
|
||||
verified green at the moment this file was written.
|
||||
|
|
@ -6,13 +6,12 @@ verified green at the moment this file was written.
|
|||
## Where things are
|
||||
|
||||
- Project: `/home/avi/Projects/0_Nostr`
|
||||
- Git repo: `master` @ `4461307` ("Create vault files owner-only from the first byte").
|
||||
Before it: `4bd7660` (legacy vault perms), `4d4dfde` (CSP + navigation guards),
|
||||
`6e627a3` (upload pick tokens), `4bde395` (IPC allowlist), on top of contact-aware
|
||||
feed (`a1445d1`) etc.
|
||||
- Git repo: `master` @ `130d7e2` ("Zeroize transient secret key material in memory").
|
||||
Before it: `4461307` (owner-only writes), `4bd7660` (legacy vault perms), `4d4dfde`
|
||||
(CSP + navigation guards), `6e627a3` (upload pick tokens), `4bde395` (IPC allowlist).
|
||||
- Working tree is **clean** apart from this checkpoint update, which is committed right after.
|
||||
|
||||
## What was completed: security hardening items #1–#5
|
||||
## What was completed: security hardening items #1–#6
|
||||
|
||||
Fixes from the 2026-08-21 security audit.
|
||||
|
||||
|
|
@ -80,8 +79,24 @@ page could read+publish arbitrary local files to nostr.build. Now:
|
|||
with a manual open-at-0600 + `io::copy`, making backups owner-only from their first byte.
|
||||
- New test: backup of a 0664 source comes out 0600 with identical content.
|
||||
|
||||
**#6 Key material zeroization (`130d7e2`, adds `zeroize = "1"`):**
|
||||
Decrypted secrets and derived keys no longer linger in unscrubbed heap memory:
|
||||
- `crypto.rs`: `decrypt_secret` returns `Zeroizing<String>` (self-shredding on drop); the
|
||||
UTF-8 error path wipes the raw bytes too; a failed Argon2 derivation wipes its key buffer.
|
||||
- `profiles.rs`: `resolve_secret_key` / `resolve_active_secret_key` now return
|
||||
`Zeroizing<String>`, so every transient plaintext key flowing to publish/upload/signer is
|
||||
wiped when its scope ends. Newly generated keys in `create_profile` are wrapped the same
|
||||
way. `reveal_secret_key` still hands a display copy to the UI by design.
|
||||
- `app.rs`: `lock()` and a new `Drop for App` zeroize the session vault key; wrong-password
|
||||
derivations wipe their throwaway keys; password change wipes the previous vault key and
|
||||
the old unlock key; `remove_password` moves decrypted values into storage via
|
||||
`std::mem::take` without extra copies (plaintext-at-rest is that feature's purpose).
|
||||
- Callers in `publish.rs`, `uploads.rs`, `signer.rs` needed no changes (deref coercion).
|
||||
|
||||
## Commits
|
||||
|
||||
- `130d7e2` "Zeroize transient secret key material in memory" — Cargo.toml, crypto.rs,
|
||||
profiles.rs, app.rs (+77/−23).
|
||||
- `4461307` "Create vault files owner-only from the first byte" — src/vault.rs (+48/−2).
|
||||
- `4bd7660` "Tighten permissions on leftover legacy vault files" — src/vault.rs (+79/−3).
|
||||
- `4d4dfde` "Enforce header-based CSP and block window open/navigation" — main.ts + index.html.
|
||||
|
|
@ -122,12 +137,13 @@ Manual protocol checks worth doing once:
|
|||
|
||||
## Outstanding / next steps (if you continue)
|
||||
|
||||
Remaining audit items in priority order:
|
||||
Remaining smaller hardening items from the audit:
|
||||
|
||||
1. **Zeroize** — wipe decrypted key material via the `zeroize` crate (`VaultKey`,
|
||||
decrypted hex strings in `crypto.rs`/`profiles.rs`).
|
||||
2. Smaller: link-preview SSRF guard (block loopback/private IPs), signer pending-cap,
|
||||
NIP-46 secret echo check, backend request timeout.
|
||||
1. Link-preview SSRF guard — block loopback/private IPs in `fetchLinkPreview` (`main.ts`).
|
||||
2. Signer pending-cap — bound the approval queue (e.g. max 10) against relay spam.
|
||||
3. NIP-46 secret echo check — verify the client echoes the handshake `secret`.
|
||||
4. Backend request timeout — `backendRequest` in `main.ts` has no timeout; hung backend
|
||||
leaks pending promises.
|
||||
|
||||
All five medium findings from the audit are closed (#1 IPC allowlist, #2 upload tokens,
|
||||
#3 CSP + navigation, #4 legacy vault perms, #5 write-race windows).
|
||||
All six primary findings are closed (#1 IPC allowlist, #2 upload tokens, #3 CSP +
|
||||
navigation, #4 legacy vault perms, #5 write-race windows, #6 zeroization).
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue