# ADR-0002: chronogrid_crypto – Argon2id KDF & OS Keychain Strategy * **Status**: Accepted * **Date**: 2026-08-09 * **Deciders**: Michael Kell ## Context & Problem Statement Task 1.2 requires implementing a `chronogrid_crypto` crate that provides: 1. A master-key derivation function using Argon2id with parameters mandated by `docs/ARCHITECTURE/02-security-and-crypto.md`. 2. Cross-platform OS keychain bindings for secure credential persistence (Windows, Linux). Android is deferred to the Flutter KeyStore bridge. ## Options Considered 1. **Hand-roll Argon2id via raw `blake2` + memory-hard loop** — maximum control but high risk of implementation bugs in a security-critical path. 2. **Use the `argon2` crate (RustCrypto)** — well-audited, widely used, supports Argon2id with configurable parameters out of the box. 3. **Use `ring` or `sodiumoxide`** — neither provides Argon2id natively; would still need the `argon2` crate. For keychain: 1. **Direct Win32 / libsecret FFI** — full control, but significant per-platform maintenance burden. 2. **`keyring` crate** — abstracts Windows Credential Manager, Linux SecretService, and macOS Keychain behind a single API. ## Decision Outcome **Chosen Options:** * `argon2` crate v0.5 (RustCrypto) for KDF — spec-compliant, zero-copy output, and widely audited. * `keyring` crate v3 for cross-platform OS keychain — minimal code, covers Windows + Linux targets. Android is excluded via `cfg(not(target_os = "android"))` and will be handled by the Flutter KeyStore bridge. **Key design choices:** * Argon2id parameters: memory = 65 536 KiB (64 MiB), time_cost = 3, parallelism = 4, salt = 16 bytes, output = 32 bytes. * `DerivedKey` struct wraps key + salt and implements `Zeroize + Drop` for automatic memory scrubbing. * `Debug` impl on `DerivedKey` redacts key material to prevent accidental log leaks. * Raw bytes are Base64-encoded before keychain insertion for UTF-8 credential backend compatibility, using inline encode/decode helpers (no extra dependency). ## Consequences & Trade-offs * **Positive**: Spec-compliant crypto with secure memory handling; single cross-platform keychain API; 8 unit tests + 1 doc-test provide baseline confidence. * **Negative**: `keyring` v3 does not support Android — Android keychain must be wired separately via Flutter platform channels (planned for Task 1.5). Inline Base64 is minimal but could be replaced by `base64` crate if other crates need it later.