Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Post-quantum posture

One page, three claims, each of them checkable against the code: what is already quantum-resistant by construction, what was not and how it was closed, and what this posture deliberately does not claim.

The inventory: symmetric-first, so mostly done before it started

Undercroft’s cryptography is symmetric wherever data rests. Grover’s algorithm halves effective symmetric security; Shor’s breaks elliptic-curve and RSA asymmetric cryptography outright. That asymmetry-of-impact is the whole posture:

mechanismprimitivePQ status
content/artifact sealingXChaCha20-Poly1305, 256-bit keys~128-bit effective under Grover — the accepted PQ bar
record tags, audit chain, tokens, attestation replayHMAC-SHA256PQ-safe (no useful quantum speedup beyond Grover)
key derivationHKDF-SHA256, Argon2idPQ-safe
dedup fingerprints, blind indexes, audited read-query fingerprintskeyed HMAC (truncated)PQ-safe
export-bundle recipient encryptionwas X25519 alonethe one vulnerable spot — closed, hybrid since C3.4
bundle/attestation signaturesEd25519quantum-forgeable in the future; not a harvest risk (see below)

The closed spot: hybrid X25519 + ML-KEM-768 bundles

An exported bundle is a file that leaves the machine, which makes it the one place harvest-now-decrypt-later applies: an adversary who records the file today decrypts it whenever a cryptographically relevant quantum computer exists, because X25519 falls to Shor. Since C3.4, undercroft bundle keygen produces a hybrid identity — X25519 and ML-KEM-768 (FIPS 203 final, the RustCrypto ml-kem implementation) — and a bundle sealed to it derives its file key from both shared secrets:

UNDERCROFT-BUNDLE-2 ‖ eph_x25519_pub (32) ‖ mlkem_ct (1088) ‖ nonce (24) ‖ ciphertext
file_key = HKDF-SHA256(salt = eph_pub ‖ recipient_x_pub,
                       ikm  = DH(eph, recipient_x) ‖ kem_shared,
                       info = "undercroft.v2/bundle")

Breaking the bundle requires breaking the curve and the lattice. The magic, the ephemeral key and the KEM ciphertext are all bound as AAD, so a spliced header, a swapped encapsulation, or a magic rewritten to impersonate the other version fails to open — the downgrade-refusal tests pin every direction.

Compatibility is total and explicit, never inferred:

bundleX25519-only identity (legacy, bare hex)hybrid identity (pq1…)
v1 (UNDERCROFT-BUNDLE-1)opensopens (curve half) — upgrading an identity never orphans old backups
v2 (UNDERCROFT-BUNDLE-2)typed refusal naming the hybrid formatopens

A legacy bare-hex recipient still receives a v1 bundle it can actually open; a hybrid recipient always receives v2 — a new identity has no reason to be harvestable, and no silent downgrade exists.

Deployment guidance: the wire is the proxy’s job

The engine’s own transport rule (TLS-or-loopback on every content egress path, CA declarations as pins) says nothing about the TLS key exchange, because that is terminated by your reverse proxy. To extend the harvest-now posture to the wire, enable a hybrid KEM group (X25519MLKEM768) at the terminator — current OpenSSL (3.5+), BoringSSL, and the servers built on them (recent Caddy and nginx builds) support it, and browsers already offer it by default. This covers the /v1 surface, the orchestrator, and the served-embedder hop alike; nothing in undercroft needs to change for it.

Signatures, stated honestly

Ed25519 signs bundle manifests and forgetting attestations. Shor forges Ed25519 — but a signature is not a harvest target: recording a signed manifest today does not let a future adversary alter what you verified in the past, it lets them mint new forgeries once a CRQC exists. That is a real but later problem, and the migration path (ML-DSA alongside Ed25519, the same hybrid pattern) is recorded here as future work rather than silently omitted.

Both signing paths are optional and operator-held, which bounds the exposure: a bundle manifest is signed only when the exporter supplies an identity, a forgetting attestation only when forget --sign is given, and an unsigned document is imported or verified as unattested-and-said-so rather than as trusted. The release path carries no signing key at all — every binary asset ships beside a SHA-256 checksum (PQ-safe), and the workflow emits no build-provenance attestation today, so there is nothing there to migrate and nothing there to over-claim either.

The honest boundary

This page describes quantum-resistant cryptography: mathematics that resists a quantum adversary, running on ordinary hardware. Nothing in undercroft processes anything on a quantum computer. “Quantum retrieval”, “quantum memory” and their marketing relatives are vapor, and this project does not claim them — a search here is BM25, cosine similarity and a reranker, exactly as documented, and it would be exactly as fast on the day a quantum computer exists as it was the day before.