Files
zeekay e85a5385b0 pqsafe: real X-Wing + capsule + manifest + AEAD + E2E tests + example
Decomplected into orthogonal leaf packages, each with one and only one
way to do its job:

  pkg/ctx      single source of truth for domain-separation context
               strings (PQSAFE-DEK-WRAP-v1, PQSAFE-CHUNK-AEAD-v1,
               PQSAFE-MANIFEST-SIG-v1, PQSAFE-REWRAP-v1,
               PQSAFE-RECOVERY-SHARE-v1, PQSAFE-QCHAIN-AUDIT-ANCHOR-v1).
               No two layers ever derive a key from the same transcript.

  pkg/xwing    X-Wing hybrid KEM (X25519 + ML-KEM-768 per IETF
               draft-connolly-cfrg-xwing-kem). One Encap, one Decap;
               SHA3-256 combiner with the IETF-prescribed label.

  pkg/identity hybrid sender/recipient identity (Ed25519 + ML-DSA-65
               + X-Wing). Single Generate / Sign / Verify surface.

  pkg/aead     bulk-chunk AEAD: AES-256-GCM (FIPS) or
               ChaCha20-Poly1305 (software), nonce = nonce_seed
               (8 B) || chunk_idx (4 B BE). AAD binds profile + idx
               + envelope_id so chunks can't be replayed across files.

  pkg/manifest deterministic core-deterministic CBOR per RFC 8949
               ยง4.2.1; Hash() returns SHA-384 of canonical bytes.

  pkg/capsule  per-recipient X-Wing-wrapped DEK with AEAD AAD =
               manifest_hash so a capsule can't be replayed into a
               different manifest.

  pkg/envelope Seal/Open. Stable envelope_id computed BEFORE chunk
               encryption (binds profile, version, sender pub,
               nonce_seed, ordered recipient pubs, created). Capsule
               AEAD AAD = manifest_hash; chunk AEAD AAD = envelope_id.
               Hybrid signature over manifest_hash with
               PQSAFE-MANIFEST-SIG-v1 context.

  _examples/basic  end-to-end demo: seal 200 KB to 2 recipients,
                   both recover byte-identical plaintext, tampered
                   chunk fails closed.

E2E tests pass (`go test -count=1 ./...`):
  TestRoundTrip                    X-Wing round-trip
  TestSizes                        wire-size pins
  TestCorruptCiphertextFails       implicit-rejection on KEM
  TestTwoKeysDoNotShare            no key collision
  TestSealOpenRoundTrip            full envelope round-trip
  TestWrongRecipientCannotOpen     wrong key fails closed
  TestCorruptChunkFails            chunk SHA mismatch detected
  TestTamperedManifestFails        hybrid sig refuses
  TestSwapCapsulesFails            X-Wing decap fails for wrong key
  TestExpiredEnvelopeRefused       TTL gate at Open time

Total: ~470 LOC of real crypto + ~280 LOC of tests + an example that
ships.
2026-05-12 19:52:19 -07:00
..