Skip to content

Changes to support DKG resharing - #374

Open
hsaleemsupra wants to merge 2 commits into
devfrom
dkg-resharing
Open

Changes to support DKG resharing#374
hsaleemsupra wants to merge 2 commits into
devfrom
dkg-resharing

Conversation

@hsaleemsupra

@hsaleemsupra hsaleemsupra commented Jul 2, 2026

Copy link
Copy Markdown

Move framework support for DKG resharing

Adds the on-chain layer for DKG resharing: restricting the dealer set of a resharing DKG to validators that hold prior key material, rejecting invalid resharing configs at proposal time, and exposing the view/accessor functions the node software and integration tests need.

Companion Rust-side changes (per-committee dealer opt-out, runner fixes, and the integration test suite) land separately in smr-moonshot, which pins this revision.

Problem

A dealer in a resharing DKG must hold secret shares from the last completed session — that is only true of validators that were receivers in that session. Without restriction, a newly joined validator gets selected as a dealer, has no prior share on disk, and the DKG degrades or stalls. Additionally, nothing prevented governance from enabling is_resharing before any DKG had ever completed, which would abort deep inside reconfiguration_with_dkg::try_start at epoch transition instead of failing at proposal time.

Changes

configs/dkg_config.move

  • New error ERESHARING_WITHOUT_PRIOR_SESSION (3): set_for_next_epoch now rejects any config containing is_resharing = true when supra_dkg::last_completed_session() is None. Checked once per proposal (only reads DKGState when some receiver actually enables resharing).
  • Existing per-committee check (ERESHARING_FOR_NONEXISTENT_THRESHOLD_TYPE) is unchanged.
  • Tests updated to install a fake completed session; new
    test_set_for_next_epoch_resharing_without_prior_session_fails asserts the
    new guard (abort code 196611 = error::invalid_state(3)).

reconfiguration_with_dkg.move

  • try_start now branches on whether any receiver committee has is_resharing = true:
    • Resharing: dealer committee = current validator consensus infos filtered to supra_dkg::last_completed_receivers_addresses() (see below), via new private helper filter_consensus_infos_by_addresses (preserves input order — committee indexing is positional).
    • Non-resharing: unchanged.
  • New defensive error ENO_PRIOR_DKG_FOR_RESHARING (1) — unreachable in practice because of the proposal-time guard above; protects against state corruption only.

supra_dkg.move

  • New last_completed_receivers_addresses(): Option<vector<address>> — the intersection of member addresses across all receiver committees of the last completed session. Intersection because the framework builds a single dealer committee that must satisfy every reshared committee's prior-data requirement simultaneously (today all receiver committees share membership, so this equals any one of them; the intersection future-proofs divergent configs).
  • New #[view] last_completed_threshold_pubkeys(): vector<vector<u8>> — returns (threshold_type || pubkey_bytes) per receiver committee of the last completed session. Used by integration tests to assert the resharing invariant (threshold pubkey preserved across reshares).
  • New #[test_only] setup_fake_last_completed_session_for_test(...) so downstream module tests can satisfy the proposal-time guard without running a real DKG.

dkg_committee.move

  • New accessors get_is_resharing(&ReceiverCommittee): bool and get_receiver_dkg_committee(&ReceiverCommittee): &DkgCommittee for the two modules above.

doc/*.md

  • Auto-regenerated framework docs.

Design decisions

  • Membership from the prior DKG, credentials from the current epoch: the dealer set is derived from prior receivers' addresses, but each dealer's consensus info/keys come from stake::cur_validator_consensus_infos(), avoiding stale dkg_pubkeys after mid-epoch key rotation.
  • No filter against the current validator set: a prior receiver that initiated leave_validator_set stays pending_inactive until on_new_epoch (leaving is blocked during reconfiguration), so it still appears in cur_validator_consensus_infos() for the duration of the DKG.
  • Reject at proposal time, not DKG-start time: misconfigured governance proposals abort in set_for_next_epoch rather than halting the epoch transition later.

Testing

  • Move unit tests in dkg_config.move cover the new guard (positive + expected-failure paths).

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.

2 participants