Security architecture · last updated 16 Jun 2026

Exactly how Farewell protects your data.

Below are the precise algorithms, parameters, and on-disk format Farewell uses.

Design principles

Encryption at rest

All vault contents are sealed with AES-256-GCM-SIV, an authenticated cipher (AEAD). GCM-SIV is chosen over plain AES-GCM for nonce-misuse resistance: even if a nonce were ever reused, it does not catastrophically leak the key or plaintext relationships the way GCM does.

CipherAES-256-GCM-SIV (RFC 8452)
Key size256 bits
Nonce96 bits (12 bytes)
Auth tag128 bits (16 bytes)
Associated databound per record (position-tied, prevents reordering)

File contents are split into 64 KiB chunks; each chunk is encrypted independently with its own key derived from the master key via BLAKE3, so random access never requires decrypting the whole vault, and chunks can't be swapped between positions.

Key derivation (passphrase)

Your passphrase is stretched into a key with Argon2id — the memory-hard KDF recommended for password hashing — making offline guessing ruinously expensive.

AlgorithmArgon2id, version 1.3 (0x13)
Memory cost1 GiB (1 048 576 KiB)
Iterations (t)4
Parallelism (p)4 lanes
Output32 bytes (256-bit key)
Salt32 random bytes, unique per vault
Cost≈ 2 s on Apple silicon (M2)

Hardware-key vaults use a lighter KDF on purpose. When a vault is bound to a FIDO2 key, the key's hardware secret — not the passphrase — carries the brute-force resistance, so a copied file is uncrackable without the physical key regardless of KDF cost. The chosen profile is not stored on disk (that would be a fingerprint); on open, Farewell simply tries the candidates in order.

Hashing & sub-keys

BLAKE3 (256-bit) is used for integrity hashing, as a keyed MAC, and to derive per-chunk sub-keys from the master key via its derive_key context mechanism.

Post-quantum posture

Your content is protected by a 256-bit symmetric key, which remains far beyond the reach of foreseeable quantum attacks. It is sealed with 256-bit AES-256-GCM-SIV; the best known quantum attack (Grover) only halves that to ~128-bit effective security — out of reach. And because a local vault is unlocked symmetrically from your passphrase (no public-key step), there is nothing for Shor's algorithm to attack.

The integrity stamp survives independently of your passphrase, but the signing key does not.

For defence in depth, each vault is stamped at creation with a one-shot ML-DSA-87 signature (NIST FIPS 204, the post-quantum signature standard) over its fixed metadata (format version, capacity, salt, and the verifying key).

“Where is the private signing key?” Nowhere — by design. The signing key is ephemeral: a fresh keypair is generated at creation, used once to sign, then the secret key is wiped from memory immediately. It is never written to disk, never reused, and lives nowhere afterwards — there is no signing key to steal, leak, or be compelled to produce. Only the verifying key (public by nature) and the signature remain, and they live inside the AEAD-encrypted metadata.

The vault’s confidentiality and authenticity rest on the AEAD plus your passphrase or hardware key: the metadata cannot be read or altered without them. The ML-DSA-87 stamp sits on top of that as an independent, algorithm-diverse integrity check, and yields a stable per-vault fingerprint (a hash of the verifying key) you can record and re-check.

“If the verifying key ships inside the very blob it signs, what does the signature buy?” Once an attacker possesses the vault key, confidentiality and integrity are already compromised; the signature is not intended to defend against that scenario, so we don't claim it adds third-party authenticity (the AEAD + your passphrase do that). Its honest value is narrower and threefold: (1) algorithm diversity — an independent post-quantum check over the metadata that would catch a fault in the AES-GCM-SIV path the GCM tag itself missed; (2) a stable, verifiable fingerprint for the vault; (3) a forward-compatible slot — the same field is built to carry a non-ephemeral signer (a release- or device-bound key) in a later version, which would add third-party authenticity, with no format break. Today's ephemeral form is that machinery in its simplest case.

Content cipherAES-256-GCM-SIV — 256-bit, Grover-safe
Integrity signatureML-DSA-87 (FIPS 204), one-shot per vault
Signing keyephemeral — generated at creation, then destroyed
Verifying key / signature2592 B / 4627 B (stored inside the encrypted metadata)
Implementationlibcrux (formally verified)

Vault format (v6)

A vault is a single fixed-layout file. Apart from the leading random salt, every byte is ciphertext or random padding — there are no headers or markers that would identify it as a Farewell vault.

# on-disk layout — nothing in cleartext except the salt
[0      .. 32)        salt            32 bytes, uniform random (plaintext)
[32     .. 4128)      slot            4096 bytes — AEAD-wrapped master key,
                                      or random padding (deniable)
[4128   .. +blob)     metadata        AEAD blob: chunk count + the one-shot
                                      ML-DSA-87 attestation
[..     .. EOF)       chunks          64 KiB plaintext each, stored as
                                      12-byte nonce + ciphertext + 4 + 16-byte tag
Format versionv6 (0x0006) — not written in cleartext
Master key256-bit, AEAD-wrapped in the slot
Hardware keysup to 3 FIDO2 keys per vault (any one opens it)
Chunk plaintext65 536 bytes (64 KiB)
Auto-wipenone — see below

There is deliberately no “wipe after N failures” feature: a counter that updates on a wrong passphrase would have to live outside passphrase-gated encryption, making the file detectable — incompatible with byte-level deniability, and useless against an adversary who imaged the disk first. Offline-guessing resistance rests on Argon2id + passphrase entropy (and the optional hardware key) instead.

In-memory key hygiene

Keys exist in RAM only while a vault is open. Farewell bounds and scrubs that exposure with the standard defences — and is honest about the line past which no user-space program can reach.

Live master keyheld in an mlock-pinned buffer (SecureBuffer)
Anti-swapmlock(2) — key pages aren't written to swap (best-effort)
On lock / dropzeroized: master key, derived keys, AEAD keys
Transient secretspassphrase & wrapping keys wiped immediately after use
Wipe primitivezeroize crate — volatile writes + compiler fence

“How do you verify the wipe is effective?” The part that can be guaranteed is at the compiler level: the zeroize crate overwrites secrets with volatile writes plus a compiler fence, so the optimizer cannot quietly drop the zeroing the way it can with a naïve memset on memory that's about to be freed. That crate is widely used and audited, and you can confirm it by reading the source. Keys are also mlocked, so they never reach swap where they would outlive the process. What no user-space program can fully guarantee is the rest of the machine — a hibernation image, kernel page copies, CPU registers and stack spills, or the passphrase as it briefly transits the OS text field and USB stack. We mitigate (mlock against swap, zeroize-on-drop, auto-lock to shrink the window) and we disclose the limit rather than claim a perfection no one can deliver.

And we test it, in CI. A regression test seeds a key buffer with a known sentinel, drops it, and asserts the backing store is all-zero afterwards. To do this soundly — reading freed memory would itself be undefined behaviour — the snapshot is taken from inside the allocator's dealloc, while the memory is still live, and it watches one specific allocation rather than scanning the whole heap (so there are no false positives from transient copies). Removing the wipe makes the test fail immediately, so a future change can't silently drop it. This guards the part that's actually at risk — a key copy escaping the buffer, or a missing wipe — not the OS-level limits above, which no test can reach.

What Farewell deliberately does not do

Threat model

Encryption is only as useful as the threats it actually addresses. Here is the honest scope — what Farewell is built to defeat, and what it cannot.

What it protects

What it does not protect

The short version: Farewell protects the file, not the live machine. Keep the vault locked when you're not using it, and run it on a device you trust.

Questions or want to scrutinize the cryptography? Write to security@farewell.pro.