pqthreshold 1.1.0
pqthreshold: ^1.1.0 copied to clipboard
Pure-Dart threshold cryptography: verifiable secret sharing, distributed key generation and FROST threshold signatures, so no single party ever holds the full secret.
Changelog #
1.1.0 #
Added #
ShareMetadataandShareMetadata.fromBytes— read a serialized share'sthreshold(t),totalParticipants(n),index,participantId,ceremonyId,schemeandformatVersionwithout materializing the secret scalar.- Previously the only way to read those fields was
Share.fromBytes, which fully decodes the 32-byte scalar into a liveSecretBuffer. A third-party key store holding shares as opaque sealed bytes could therefore not describe or validate what it held without first exposing what it held — which inverts the custody modeldoc/TERMINAL.mdrequires ("unwrap only in process"). - The decoder stops at the end of the metadata prefix. The secret share and the verification blob are never read, so the scalar never exists in the reading process.
- Reading metadata is not authentication. It reports what the bytes claim
to be. A caller needing authenticity must unwrap and use
VerifiableSecretSharing.verifyShare. This type is for describing and indexing shares, never for trusting them.
- Previously the only way to read those fields was
validateShareIndex(index, params)andvalidateParticipantId(id)are now public, along withmaxParticipantIdCodeUnits. Both checks previously lived only inside@internal Share.create, so a caller could not validate a participant index or label without constructing aShare— which requires the secret.Share.disposeSecret()is public. A custodian that unwraps a share to hand it to a signing ceremony had no reachable way to wipe it. Metadata (params,ceremonyId,participantId,index,verificationData) remains readable afterwards; operations needing the scalar throwStateError.
Changed #
SecretBuffer.use(fn)andSecretBuffer.mutate(fn)— read-only and read/write windows onto the managed buffer, mirroringpackage:zeroize'sSecretBytes.SecretBuffer.bytesreturns a plain copy that nothing owns or wipes — the exact pattern that makes a buffer survive in the heap until collection. It remains for APIs that require a bareUint8List, and its documentation now says to wipe it.use/mutatehand out the managed backing store, sodispose()wipes exactly what the caller was given.
No wire-format change. ShareMetadata parses the existing PQTH layout and
Share.toBytes() output is byte-identical. t/n are still re-validated on
the wire path by ThresholdParams.fromBytes.
Fixed #
- pubspec
descriptionshortened to 166 characters. It was 475, which is outside pub.dev's 20-180 scoring window and cost the description points. The longer text was accurate but did not belong in the one-line summary; the detail lives inREADME.mdanddoc/ARCHITECTURE.md. - The
quickrelease gate no longer fails onpackages/crypto_shared. The rootdart analyzewalks the whole repository, but a nested package has no entry in the rootpackage_config.json, so everypackage:crypto_shared/...import failed to resolve and CI went red on the root package's own gate.packages/**is now excluded from the rootanalysis_options.yaml, andtool/verify.dart quickresolves, analyses and tests each nested package in its own directory. The nested package is covered by the gate, not skipped by it — coverage is now stronger than before, because crypto_shared is also analyzed rather than only tested. - Corrected the stale claim that
crypto_sharedis unpublished. It is published aspackage:crypto_shared1.0.0. SeeREADME.md.
1.0.1 #
- Exclude the separately published
crypto_sharedcompanion package from thepqthresholdpub.dev archive. (crypto_sharedis published on its own aspackage:crypto_shared1.0.0; earlier notes in this file described it as unpublished, which was incorrect.) - Move ML-DSA and Mithril APIs behind explicit experimental library barrels.
- Document the stable FROST-only API boundary and companion package location.
Unreleased #
Operator CLI #
- ✅
dkg participant step— multi-round C1 over--ceremony-dirwithtransport/inbox/outbox. - ✅
sign partial→sign round2→sign combine— disk round-trip for distributed FROST (binding-factor round). - ✅
sign ml-dsa run|verify— ML-DSA-44 threshold sign + optional--wire-direxport (M3 beta). - ✅
sign ml-dsa partial|round2|round3|combine— per-officer distributed ML-DSA wire rounds (M3+).
Tier 1 API #
- ✅
FrostSigningMessagewire codec (doc/PROTOCOL_MESSAGES.md§5). - ✅
MlDsaSigningMessagewire codec (doc/PROTOCOL_MESSAGES.md§6). - ✅
MlDsaSigningSession— three-round ML-DSA with officer-local checkpoint. - ✅
SigningSession— two-round FROST with officer-local checkpoint. - ✅
CeremonySession.exportCheckpoint/fromCheckpoint— DKG dir-transport persistence.
Ceremonies (planned) #
- ❌ C6 proactive share refresh.
- ❌ C4-B re-share without full reconstruct.
Cryptography (v2 PQ — M2 beta) #
- ✅ ADR-004 + profiles +
SchemeIdregistry (M1) - ✅
MlDsaShare/MlDsaPublicKeyPQTH kinds0x07–0x09 - ✅
MlDsaThresholdSigner+MlDsaRootCeremony/MlDsaThresholdSigningCeremony(Tier 2 simulate) - ✅
tool/mithril_bridge— Mithril ML-DSA-44 threshold via threshold-ml-dsa - ✅
MlDsaSigningMessagewire codec +signWithWire/sign ml-dsa run(M3 beta — Mithril coordinator exports rounds) - ✅
MlDsaSigningSession+ distributed CLI (M3+ — deterministic party RNG, officer checkpoints) - ❌ Per-party RSS export without shared ceremony seed (production DKG)
- ❌ Pure Dart ML-DSA-65 lattice MPC (M4)
- ❌ Pedersen VSS (new verification mode).
Integration (planned) #
- ❌ Wrapped share CLI (
*.share.wrapped.json) aligned with pqforge custody. - ❌ Persistent Serverpod relay (beyond in-memory sketch).
1.0.0 #
Stable Tier 1 release — frostEd25519V1 only; PQTH ver=0x01 frozen per doc/API.md §7.
Operator CLI (0.7.0 scope) #
vss split|verify|reconstruct— C2 dealer ceremony on terminal.dkg simulate— in-process C1 DKG with PQTH artifact export (CI/operator).sign run|partial|combine|verify— C3 threshold signing;sign runis the primary path from share files.ceremony run --flow c1|c3|c5|full— orchestrated in-process ceremony workflows.- Tier 1
DealerCeremony(C2) andRecoveryCeremony(C4) helpers.
Distributed integration (0.8.0 scope) #
packages/crypto_shared— relay,OfficerDkgClient,DistributedDkgCoordinator,OfficerSigningClient,DistributedSigningCoordinator, share wrap/unwrap aligned with pqforgePqWrappedKey.example/serverpod_integration/— Serverpod endpoint sketch withThresholdCeremonyService.PublicKey.fromShareSet()— public API for joint key derivation from shares.- Relay-based C3 tests without
SigningSimulator;crypto_sharedtests intool/verify.dart full.
Pre-1.0 hardening (0.9.0 scope) #
- 77 tests in main package + 6 in
crypto_shared;dart run tool/verify.dart fullpasses. - REVIEW_CHECKLIST.md published — independent cryptographic sign-off recommended before high-assurance deployment.
Requires pqforge ^0.4.4.
0.6.0 #
- Feldman VSS — split, verify, reconstruct (C2 dealer-based sharing).
- Gennaro DKG —
CeremonySession, transcripts, wire messages (C1). - FROST threshold signing — Ed25519-compatible aggregate signatures (C3).
- Ceremony helpers —
RootCeremony,RotationCeremony,ContinuityProof(C5). - Tier 2 simulators in
package:pqthreshold/testing.dart. - Acceptance vectors under
test/vectors/;dart run tool/verify.dart fullpasses. - Requires pqforge ^0.4.4 (
PqBytes.sha512for FROST profile hashes). - Independent cryptographic review checklist:
doc/REVIEW_CHECKLIST.md(recommended before production). - Phase 5 ceremony helpers: C1/C3/C5 orchestration per
doc/API.md§4.4. RootCeremony.startSession/simulate,ThresholdSigningCeremony.simulate,RotationCeremony.simulate.ContinuityProoftype with PQTH wire codec (doc/SERIALIZATION.md§4.6).- Example app runs C1 → C3 → C5 via Tier 2 simulators.
- FROST SHA-512 via
PqBytes.sha512from pqforge 0.4.4 (no directcryptodependency). - Six ceremony tests in
test/ceremony/ceremony_test.dart;dart run tool/verify.dart fullpasses.
0.5.0 #
- Phase 4 FROST threshold signing: Ed25519-compatible aggregate signatures (C3).
ThresholdSigner.signPartial,combine,verifyperdoc/API.md§4.3.PartialSignaturetype with PQTH wire codec (doc/SERIALIZATION.md§4.4).- FROST core under
lib/src/scheme/frost/(binding factors, group commitment, Lagrange shares). - Challenge hash uses RFC 8032 FROST-Ed25519 H2 so
PqClassical.provider.ed25519Verifysucceeds. - FROST acceptance vector in
test/vectors/frost/;tool/generate_frost_vectors.dartfor regeneration. - Five signing tests in
test/signing/frost_test.dart;dart run tool/verify.dart fullpasses.
0.4.0 #
- Phase 3 distributed key generation: Gennaro DKG over Ed25519 (C1).
CeremonySessionwith swissarmyknifeStateMachineperdoc/PROTOCOL_MESSAGES.md§3.1.- DKG wire messages (
DkgMessage) for Round1/Round2 packages. Transcripthash-chain append, seal, verify, and PQTH wire codec.- Tier 2
DkgSimulatorinpackage:pqthreshold/testing.dart. - DKG acceptance vectors in
test/vectors/dkg/;tool/generate_dkg_vectors.dartfor regeneration. - Five integration tests in
test/dkg/dkg_simulation_test.dart;dart run tool/verify.dart fullpasses.
0.3.0 #
- Phase 2 verifiable secret sharing: Feldman VSS over Ed25519.
VerifiableSecretSharing.split,verifyShare,reconstructperdoc/API.md§4.2.ShareandPublicKeytypes with PQTH wire codecs (doc/SERIALIZATION.md§4.2–4.3).- In-tree Ed25519 curve/field ops under
lib/src/scheme/feldman/(pqforge has no group API). - Feldman acceptance vectors in
test/vectors/feldman/;tool/generate_feldman_vectors.dartfor regeneration. - Six unit tests in
test/sharing/feldman_test.dart;dart run tool/verify.dart fullpasses.
0.2.0 #
- Phase 1 foundation: params, errors, PQTH serialization, and util modules.
ThresholdParams/SchemeIdwith swissarmyknifeValidatorand canonical 16-byte wire format.- Sealed
ThresholdExceptionhierarchy; internalResultbridged at public API boundary. PqthHeader,ThresholdParamsCodec,BinaryReader/BinaryWriterperdoc/SERIALIZATION.md.SecretBuffer(Disposable wipe),validateCeremonyId/generateCeremonyId.- Phase 1 CLI (
pqthreshold params,pqthreshold inspect) perdoc/TERMINAL.md. - 32+ unit tests across params, serialization, util, CLI, and package smoke;
dart run tool/verify.dart fullpasses.
0.1.0 #
- Planning release: formative architecture, security, ceremony, and integration docs.
- Locked v1 scheme stack (FROST Ed25519, Feldman VSS, Gennaro DKG) in
doc/SCHEMES.md. - Added implementer index (
doc/INDEX.md), protocol specs, params, test vector plan, implementation guide, tooling, release checklist. - CI (
.github/workflows/ci.yml) andtool/verify.dartrelease gate. - ADRs for scheme selection, runtime dependencies, and serialization format.
- Implementation scaffold only; no cryptographic functionality yet.