Files
Hanzo AI 34ed87534b magnetar: SECURITY.md --- threat model + strict-PQ profile closure
Adds the load-bearing prose statement for the strict-PQ chain-profile
gate landed in luxfi/threshold (commit b1218f3). Documents:

* Two canonical Combine paths (legacy-compat strict-atom vs strict-PQ
  TEE-attested) and the residency-window tradeoff that distinguishes
  them.
* The single-function profile gate (`magnetarRefuseUnderStrictPQ`)
  mirroring the precompile-side `contract.RefuseUnderStrictPQ`.
* The t-of-n attested-combiner pool's freshness gate (RotationWindow),
  quorum semantics (Threshold>=2), and byte-equality discipline (no
  silent winner-picking on divergence).
* Production attestation kinds: SEV-SNP is the only production-ready
  cc/attest verifier today; TDX + NRAS are stubs (lux/mpc#222 stages
  2-3) admitted by the pool's `KnownIssuers` once shipped.
* Adversary model (commodity-host vs strict-PQ) and why strict-PQ
  closes the microsecond residency window fully for institutional
  custody.

Cross-referenced from BLOCKERS.md's strict-atom closure block.
2026-06-01 21:29:52 -07:00

13 KiB

Magnetar --- Security Posture by Chain Profile

This document is the honest threat-model statement for Magnetar's two canonical Combine paths, parameterised by the chain-security profile the embedding consensus layer publishes.

It is the load-bearing prose for the strict-PQ profile gate landed at 2026-06-01 in luxfi/threshold/pkg/thresholdd/magnetar.go (Combine gate + t-of-n attested-combiner pool).


1. Two profiles, two threat models

Magnetar exposes ONE wire format (MAGS / MAGG, byte-identical to single-party FIPS 205) and exactly TWO Combine paths whose acceptance is gated by the chain-security profile in effect:

Profile Combine path TCB
legacy-compat strict-atom commodity-host (v1.1) public combiner host (microseconds)
strict-PQ TEE-attested t-of-n pool measured enclave (only)

Wire bytes are identical across both paths. The distinction is entirely in where the FIPS 205 master bytes are allowed to transiently exist during the SHAKE absorb step that emits the signature.


2. Residual gap closed by strict-PQ

2.1 Commodity-host Combine (legacy-compat)

Magnetar v1.1's strict-atom Combine path is implemented at ref/go/pkg/magnetar/thbsse_assemble.go::assembleSignatureBytes backed by slhdsa_internal.go::slhSignAtom. The discipline pins:

grep -rE "SK\.seed|SK\.prf|sk_seed|sk_prf" thbsse_assemble.go

returns zero matches. There is no named transient seed binder; the master is decomposed into per-atom positional slices of a SHAKE expansion buffer.

Residual gap. The bytes of the FIPS 205 master DO exist transiently inside derivedMaterial (the SHAKE-expansion output buffer) and derivedExpandInput (the Lagrange-reconstructed input to SHAKE) for the duration of the SHAKE absorb --- approximately a few microseconds on a modern host. A coredump or /proc/self/mem dump at exactly the right wall-clock instant would observe them. This is the strictest discipline available without crossing into either (a) MPC-over-SHAKE (open research; multi-second per signature) or (b) a TEE-attested host inside the TCB.

For the legacy-compat profile, this residency window is acceptable. The combiner role is PUBLIC --- any peer can run the strict-atom Combine on its own substrate. No host is privileged. The strict-atom discipline is materially stronger than the v1.0 reveal-and-aggregate model and is the recommended commodity-host posture.

2.2 TEE-attested Combine (strict-PQ)

For deployments that cannot tolerate the microsecond residency window --- regulated custody, sovereign settlement, high-value bridge --- the strict-PQ profile requires that every Combine route through the luxfi/threshold/protocols/slhdsa-tee package. In this path:

  1. The wrapped master seed lives at-rest in an HSM (luxfi/mpc/pkg/hsm.Provider --- file, AWS KMS, Azure Key Vault, GCP Cloud KMS).
  2. The seed is only unwrapped inside a hardware-attested TEE (SEV-SNP / TDX / NRAS) whose binary + firmware chain-validate to the vendor root (AMD KDS / Intel PCS / NVIDIA NRAS JWKS) and whose measurement matches the operator-asserted RIM digest.
  3. Each sign call is gated by luxfi/mpc/pkg/kms.ReleaseGate.Issue (fresh single-use nonce + epoch) and Release (RIM allowlist + hardware allowlist + Require* issuers).
  4. The FIPS 205 master bytes only ever exist inside the measured enclave. The host process never sees plaintext --- it sees only the AEAD-sealed session key, the wrapped seed ciphertext, and the resulting wire signature.

Output bytes are byte-identical to single-party FIPS 205 SignDeterministic on the same (seed, msg, ctx) tuple. Any verifier holding the canonical MAGG group public key validates without any awareness of the TEE substrate.


3. Profile gate (one function, one place)

The dispatcher-side gate is the single function magnetarRefuseUnderStrictPQ at luxfi/threshold/pkg/thresholdd/magnetar.go. It mirrors the precompile-side gate contract.RefuseUnderStrictPQ in luxfi/precompile/contract/strict_pq.go and follows the same discipline:

  • ONE function (no duplication across schemes).
  • ONE place (called at the top of Sign and Sign_Ctx).
  • ONE canonical refusal sentinel (slhdsatee.ErrMagnetarNoTEEAttestation, wire-stable identifier ERR_MAGNETAR_NO_TEE_ATTESTATION).

Under ProfileStrictPQ:

  • Sign → refuses with ErrMagnetarNoTEEAttestation.
  • Sign_Ctx → refuses with ErrMagnetarNoTEEAttestation.
  • Sign_TEE → allowed (single-host attested-release sign).
  • Combine_TEE → allowed (t-of-n attested-combiner pool sign).

Under ProfileLegacyCompat (default):

  • All four paths allowed.
  • Combine_TEE still works when a pool is wired --- the strict-PQ posture is opt-in even on legacy-compat chains.

4. T-of-n attested-combiner pool

The strict-PQ Combine path is not single-host. The pool at luxfi/threshold/protocols/slhdsa-tee/pool.go registers n attested combiner endpoints; each holds an independently provisioned slhdsa-tee.Signer (independent wrapped seed). Combine selects the first t members whose attestation freshness is inside the rotation window, drives each member's full Sign machinery, and refuses if the produced bytes are not byte-identical.

SLH-DSA SignDeterministic is byte-stable: same (seed, msg, ctx) → same bytes. Two attested combiners holding the same wrapped seed under the same RIM MUST produce identical output. Divergence indicates a misconfigured or compromised combiner; the pool refuses with ErrMagnetarSignatureDivergence --- no silent winner-picking.

4.1 Threshold-of-attested-combiners policy

The default deployment posture is t = 2, n = 3. Operator policy may pin higher t for higher-value deployments. The constructor refuses t < 2 (no single-attested-host quorum):

slhdsatee.NewCombinerPool(slhdsatee.CombinerPoolConfig{
    Threshold:      2,                        // t-of-n, t >= 2
    RotationWindow: 60 * time.Second,         // per-member attestation TTL
    KnownIssuers:   map[string]struct{}{      // vendor root pin
        "amd.sev.snp": {},
    },
})

4.2 Rotation window

Each pool member's attestation freshness is bounded by RotationWindow. Outside the window, the member is treated as stale and not eligible for the quorum. Combine refuses with ErrMagnetarStaleAttestation when insufficient fresh members exist.

Re-attestation is the operator control-plane's responsibility: a periodic tick captures fresh SNP_GUEST_REQUEST / TDREPORT / NRAS-JWT bytes from each combiner and submits via CombinerPool.Attest. The Combine path is then a freshness read --- it never blocks on KDS / PCS / NRAS network roundtrips.

Recommended cadence: every Lux block (~1s), with a 60s RotationWindow. This absorbs ~60 blocks of control-plane latency between attestation capture and the next sign request. Latency- sensitive deployments may shrink to 5s rotation; long-lived custody deployments may extend to 5min with periodic compensating audits.


5. Attestation kinds in production

The strict-PQ profile accepts evidence whose Vendor lies in the operator-configured KnownIssuers set. Today the three supported kinds are:

Kind Vendor string Verifier status
sev_snp amd.sev.snp PRODUCTION (luxfi/mpc/cc/attest/sev.go + go-sev-guest)
tdx intel.tdx STUB (luxfi/mpc/cc/attest/tdx.go, ErrNotImplemented; tracked #222 stage 2)
nras nvidia.nras.v1 STUB (luxfi/mpc/cc/attest/nras.go, ErrNotImplemented; tracked #222 stage 3)

Production today: strict-PQ deployments MUST use SEV-SNP. TDX and NRAS chain-validators are stubs that return ErrNotImplemented --- the pool refuses any Attest call routing through them. When the upstream verifiers ship, no code changes are required at the magnetar dispatcher --- the pool's KnownIssuers set is the only knob.


6. Defence in depth: each layer is independently complete

Composition: each step in the strict-PQ Combine path is independently complete and refuses on its own without relying on later steps:

Step Responsibility Refusal sentinel
Profile gate Sign / Sign_Ctx on strict-PQ ErrMagnetarNoTEEAttestation
Pool wired Combine_TEE requires pool errMagnetarPoolUnwired
Freshness Attestation < rotation window ErrMagnetarStaleAttestation
Quorum At least t fresh members ErrMagnetarInsufficientQuorum
Vendor pin KnownIssuers ∋ report.Vendor slhdsa-tee: vendor not in KnownIssuers
Approval (if ApprovalRequired) signed intent slhdsatee.ErrApprovalDenied
Chain attest.Dispatch validates evidence attest.ErrChainInvalid / ErrSignatureInvalid
RIM/HW gate.Release checks allowlists slhdsatee.ErrPolicyRefused
HSM wrapped seed unsealable inside TEE slhdsatee.ErrCorruptWrappedSeed
Divergence byte-equality across quorum ErrMagnetarSignatureDivergence

No silent fallback. A failure at any step is hard refusal at the pool level --- the strict-PQ profile cannot silently drop a member mid-flight.


7. Threat model summary

7.1 Adversary capabilities (strict-PQ)

We model an adversary that controls:

  • the operator's host process outside the TEE (compromised binary, malicious operator);
  • the operator's at-rest HSM ciphertext (compromised HSM admin, stolen volume snapshot);
  • the network between the operator and the chain (replay, reordering, drop).

We do NOT model an adversary that:

  • has compromised AMD / Intel / NVIDIA's vendor signing keys (assumed-out, defence-in-depth via vendor key rotation);
  • has physical access to the TEE die during sign (assumed-out for CSP-hosted deployments; mitigated by chassis-attest for on-prem);
  • has compromised the wall-clock or RotationWindow policy (assumed honest; the rotation is operator policy, not a cryptographic guarantee --- monitor for skew).

7.2 Adversary capabilities (legacy-compat)

Same as strict-PQ, MINUS the explicit acceptance that the master bytes transiently exist in the public combiner's SHAKE-expansion buffers for ~microseconds. This window is exposed to:

  • a coredump / /proc/self/mem snapshot fired during the Combine window;
  • a kernel exploit that reads user-space process memory while the Combine goroutine is suspended.

Neither is exploitable without root-equivalent access to the host running the public combiner. The combiner is public --- any peer can run it on its own substrate. The window IS finite microseconds. We ship this with full disclosure rather than hide it.

7.3 Why strict-PQ closes residual #1 fully

In strict-PQ mode the host running the Sign / Combine routine is a measured enclave. The kernel running on the enclave is the vendor- signed enclave runtime. There is no /proc/self/mem from the host side that observes enclave RAM --- the hardware encrypts pages in-place against a chip-rooted key the host CPU cannot read. The microsecond residency window still exists, but it exists inside the enclave's address space, which is cryptographically opaque to every party except the enclave itself.

This is the standard guarantee SEV-SNP / TDX provide and is the basis on which institutional-custody platforms (AWS Nitro, Google Cloud Confidential Computing, Azure Confidential VMs) build. Strict-PQ Magnetar is no more, and no less, secure than the underlying CSP enclave guarantee.


8. Verification

The gate is exercised end-to-end at luxfi/threshold/pkg/thresholdd/magnetar_tee_gate_test.go:

  • TestMagnetarCombine_StrictPQProfile_RequiresTEE --- strict-PQ refuses Sign / Sign_Ctx; permits Combine_TEE only when pool is wired.
  • TestMagnetarCombine_AttestationVerified_AllowsSign --- end-to-end pool drive against committed AMD Milan SEV-SNP fixture; output verifies under magnetar.VerifyBytes.
  • TestMagnetarCombine_StaleAttestation_RejectsSign --- members outside rotation window refused; partial re-attestation recovers.
  • TestMagnetarCombine_TwoOfThreeAttestedCombiners_MatchSig --- 2-of-3 quorum surfaces signature; 1-of-3 refuses.
  • TestMagnetarCombine_SignatureDivergence_HardRefusal --- pool refuses byte-divergent quorum output.

All five tests pass under -race against the committed Milan SEV-SNP fixture (pkg/thresholdd/testdata/sev_snp_attestation_milan.bin, sev_snp_vcek_milan.cer) replayed via dispatchKDSReplay().


9. Cross-references

  • Strict-atom Combine load-bearing prose: ASSEMBLE-INVARIANT.md.
  • Strict-atom KAT: TestSlhdsaInternal_ByteEqualToCirclSign.
  • Profile sentinel value: slhdsatee.ProfileStrictPQ (luxfi/threshold/protocols/slhdsa-tee/profile.go).
  • Precompile-side strict-PQ gate (analogous): luxfi/precompile/contract/strict_pq.go.
  • Pool implementation: luxfi/threshold/protocols/slhdsa-tee/pool.go.
  • Chain attestation verifiers: luxfi/mpc/cc/attest/{sev,tdx,nras}.go.
  • Magnetar v1.0 → v1.1 strict-atom closure: CHANGELOG.md v1.1.0.