Skip to content

feat(quorumd): BLS macro-quorum over the k3s master triad (Lazerus quorum_sigs) - #324

Merged
mdheller merged 1 commit into
mainfrom
feat/bls-macro-quorum-triad
Aug 4, 2026
Merged

feat(quorumd): BLS macro-quorum over the k3s master triad (Lazerus quorum_sigs)#324
mdheller merged 1 commit into
mainfrom
feat/bls-macro-quorum-triad

Conversation

@mdheller

@mdheller mdheller commented Aug 4, 2026

Copy link
Copy Markdown
Contributor

What

verify_bls_quorum — the on-device verifier for the macro-quorum over the k3s master triad. The "k3 regime" is the real k8s control plane: three k3s HA masters, each head of one cluster in the mesh. Each master publishes a Lazerus Integrity Receipt carrying an aggregatable BLS quorum (quorum_sigs) over the state_root it commits to. This verifies that quorum on-device: rule parses, enough distinct masters, each quorum_sig is a well-formed bls: token by a listed master, threshold met, and — when a state_root is supplied to bind against — the quorum signs exactly that state (so a macro-quorum vote can't be replayed onto another state).

It is the BLS twin of verify_quorum (the Ed25519 side), and the on-device counterpart to the consumer-side failback in sociosphere #587 (automation/lazerus.py + macro_triad.py). The bls: token grammar (96/192 hex) matches RE_BLS_SIG there, so both ends agree on the shape.

Why the cryptographic pairing check is deferred (on purpose)

The real check — e(sig, G2) == e(H(state_root), aggregated_pk) — is blocked on pinning the Lazerus BLS ciphersuite (curve side G1/G2 + the hash-to-curve DST). Building a "real" verifier before that suite is fixed produces something that cannot be shown to interoperate — an unfalsifiable guess, worse than an honest shape gate on the boot/control-plane path. This is the exact layering already in this file: verify_quorum (shape/threshold) shipped before verify_quorum_signed (Ed25519 crypto). When the Lazerus ciphersuite is pinned, the pairing check drops in on top of this verified shape.

Cross-silicon

Pure Rust, no new dependencies, no arch-specific code — the identical logic runs on aarch64 / x86_64 / riscv64 (the way an on-device control-plane check must). attest-verifier.yml compile-checks aarch64 + riscv64.

Tests

7 new (22 quorumd total, all green): 2-of-3 masters pass, below-threshold fails, unbound-state rejected, unlisted master doesn't count, duplicate master counts once, malformed bls: token rejected, bad state_root rejected.

Follow-up

Cryptographic BLS aggregate verification once the Lazerus ciphersuite is pinned (this PR is the verifiable shape it will sit on).

🤖 Generated with Claude Code

…orum_sigs)

The k3 regime is three k3s HA masters, each head of one cluster; each publishes a Lazerus
Integrity Receipt carrying an aggregatable BLS quorum (quorum_sigs) over the state_root it
commits to. verify_bls_quorum is the on-device SHAPE + M-of-N threshold + state-binding
verifier for that macro-quorum — the BLS twin of verify_quorum (Ed25519 side). It binds the
quorum to the exact state being admitted/failed-back-to, so a vote can't be replayed onto
another state. bls: token grammar (96/192 hex) matches the consumer side (sociosphere
automation/lazerus.py RE_BLS_SIG) so both ends agree.

The cryptographic pairing check is DEFERRED on purpose: it's blocked on pinning the Lazerus
BLS ciphersuite (curve side G1/G2 + hash-to-curve DST); a 'real' verifier before that suite is
fixed can't be shown to interoperate — an unfalsifiable guess, worse than an honest shape gate.
Same layering already in this file: verify_quorum (shape) preceded verify_quorum_signed
(Ed25519 crypto). Pure Rust, no new deps -> identical on aarch64/x86_64/riscv64.

7 new tests (2-of-3 pass, below-threshold, unbound-state, unlisted/duplicate master, malformed
sig token, bad state_root); 22 quorumd tests total.
@mdheller
mdheller merged commit 7fe344d into main Aug 4, 2026
6 checks passed
@mdheller
mdheller deleted the feat/bls-macro-quorum-triad branch August 4, 2026 09:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant