feat: GroupKeyHolder for GMS key management#449
Open
moudyellaz wants to merge 37 commits intomainfrom
Open
Conversation
12ef35b to
4938373
Compare
9822584 to
1fdc2da
Compare
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.
🎯 Purpose
This PR adds GroupKeyHolder to the wallet for group-owned private PDAs. A group of controllers shares a Group Master Secret (GMS). From it, each controller independently derives identical keys for any PDA the group owns, enabling private multisig and k-of-n patterns over existing PDA-based programs without changing those programs.
⚙️ Approach
key_protocol: GroupKeyHolder (core cryptography)
SHA256(domain_prefix || gms || pda_seed)producing NSK/NPK/VSK/VPK through the existing derivation chain.epochcounter +ratchet(rotation_salt)forward-hashes the GMS so removed members cannot derive future keys.seal_for(recipient_vpk)/unseal(sealed, own_vsk)encrypts GMS+epoch via ephemeral ECDH + domain-separated KDF + AES-256-GCM for distribution over untrusted channels.dangerous_raw_gmsto flag intent.key_protocol: NSSAUserData storage
group_key_holders: BTreeMap<String, GroupKeyHolder>field with#[serde(default)]for backward compatibility.get_group_key_holder/insert_group_key_holderaccessors.wallet: mask-3 transaction construction
PrivateGroupPda { group_label, program_id, seed }variant onPrivacyPreservingAccount.group_pda_preparationderives keys from GroupKeyHolder, computesAccountId::for_private_pda, fetches account state, sets mask 3.🧪 How to Test
20 tests covering: derivation determinism, collision resistance, degenerate inputs, pinned end-to-end derivation, serde round-trip, ratchet (epoch advance, key change, salt divergence, forward secrecy), seal/unseal (round-trip, wrong VSK, tampered ciphertext, randomness, too-short input), NSSAUserData storage.
🔗 Dependencies
🔜 Future Work
📋 PR Completion Checklist