Repository navigation
feat(groups): repair a member's lost share - #42
Merged
Merged
Conversation
A member who lost their device and backup gets their share back from as many members as the threshold, with FROST's repairable threshold scheme (frost_core::keys::repairable), without moving the funds. The helpers never learn the share, and a group where every member must sign can't repair one. core/src/repair.rs runs it over a session marked REPAIR_SESSION, holding the helpers and the member's new communication key: the helper who starts sends a Request; each helper sends every other a Delta (step 1), sums what it got and sends the member a Share (step 2) with the group's data (its public key package, members, viewing seed and where its wallet starts); the member's app rebuilds the key package (step 3), checks it against the group's public verifying share for them, and answers Done. A joining helper refuses a session that isn't exactly the named helpers plus one outside key, or whose member is a helper or isn't a member. The member's app keeps nothing unless every helper describes the same group naming its key (start heights aside: the earliest is kept). The member comes back with a new key, so helpers compare its safety code with them before approving, the trust decision. Each helper's app vouches for the new key in the group's records (MemberKey), delivered to the members as they were, then switches; the other members' apps switch once as many members vouch as a payment needs. The starting helper keeps the session open a minute after success, so the others can still read the member's confirmation. Repair rebuilds the same share, so the interface says to move the funds instead if a device may have been stolen. Interface: Recover a group on the new device (its contact code, then the repair code), Repair a member's share on the group's page, requests with the new key's safety code in Approvals. Tested: unit tests rebuild a dealer-made share exactly (RedPallas and Ed25519) and refuse a wrong part; a live test over frostd repairs Carol's share in a 2-of-4 group onto a new device, byte for byte with its viewing seed, and Erin's app, which didn't help, switches to the new key. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Stacked on #41 (accounting), and through it on #34–#40. Merge those first; until then this diff also shows their changes.
Summary
Share repair. A member who lost their device and has no backup gets their share back from as many members as the threshold, without moving the funds.
frost_core::keys::repairable.The flow
Protocol
It runs over a frostd session marked
REPAIR_SESSIONthat holds the helpers and the member's new key.RequestDeltaShareDoneChecks
The member's new key
MemberKey), then switches. The vouch goes out to the members as they were before the switch: an app that doesn't know the new key yet would refuse a session that includes it.polls::vouched_member_keys). One member alone can't redirect another's identity.Stolen, not lost
Repair rebuilds the same share. If a device may have been stolen, whoever has it still holds the share. The UI and the user guide say to move the funds to a new group instead. Share refresh (new shares for the same key) is listed in TODO.md as a follow-up.
Changes
repair.rs: the protocol,RepairCode(with chat-safe decoding), and the puredeltasandrebuildfunctions.polls.rs:MemberKeyandvouched_member_keys.dkg.rs:SessionIohelpers made crate-visible.commands/repair.rs:start_repair,join_repair(approved withrespond_to_signing),read_repair_code,receive_repair,apply_vouched_keys.contacts.rs:read_contact.repair, matched to a group with exactly one outside key.Testing
cargo clippy --workspace --all-targets -- -D warningscargo test --workspacetsc, thenvitest(55 tests)helpers_rebuild_a_lost_share_that_matches_the_groups_record_of_it: RedPallas and Ed25519, with an exact key package and a wrong part refused.a_members_new_key_counts_once_enough_members_vouch_for_it.tests/repair.rs(passed 3 of 3 runs):🤖 Generated with Claude Code