diff --git a/integration_tests/src/tps_test_utils.rs b/integration_tests/src/tps_test_utils.rs index 6f597e2..e9e7a82 100644 --- a/integration_tests/src/tps_test_utils.rs +++ b/integration_tests/src/tps_test_utils.rs @@ -167,7 +167,8 @@ fn build_privacy_transaction() -> PrivacyPreservingTransaction { (sender_npk.clone(), sender_ss), (recipient_npk.clone(), recipient_ss), ], - &[(sender_nsk, proof)], + &[sender_nsk], + &[proof], &program.into(), ) .unwrap(); diff --git a/nssa/core/src/circuit_io.rs b/nssa/core/src/circuit_io.rs index 848fe3e..2abf7b5 100644 --- a/nssa/core/src/circuit_io.rs +++ b/nssa/core/src/circuit_io.rs @@ -14,7 +14,8 @@ pub struct PrivacyPreservingCircuitInput { pub visibility_mask: Vec, pub private_account_nonces: Vec, pub private_account_keys: Vec<(NullifierPublicKey, SharedSecretKey)>, - pub private_account_auth: Vec<(NullifierSecretKey, MembershipProof)>, + pub private_account_nsks: Vec, + pub private_account_membership_proofs: Vec, pub program_id: ProgramId, } diff --git a/nssa/program_methods/guest/src/bin/privacy_preserving_circuit.rs b/nssa/program_methods/guest/src/bin/privacy_preserving_circuit.rs index 29162db..289d271 100644 --- a/nssa/program_methods/guest/src/bin/privacy_preserving_circuit.rs +++ b/nssa/program_methods/guest/src/bin/privacy_preserving_circuit.rs @@ -16,7 +16,8 @@ fn main() { visibility_mask, private_account_nonces, private_account_keys, - private_account_auth, + private_account_nsks, + private_account_membership_proofs, mut program_id, } = env::read(); @@ -63,7 +64,8 @@ fn main() { for (i, program_output) in program_outputs.iter().enumerate() { let mut program_output = program_output.clone(); - // Check that `program_output` is consistent with the execution of the corresponding program. + // Check that `program_output` is consistent with the execution of the corresponding + // program. let program_output_words = &to_vec(&program_output).expect("program_output must be serializable"); env::verify(program_id, program_output_words) @@ -131,7 +133,8 @@ fn main() { let mut private_nonces_iter = private_account_nonces.iter(); let mut private_keys_iter = private_account_keys.iter(); - let mut private_auth_iter = private_account_auth.iter(); + let mut private_nsks_iter = private_account_nsks.iter(); + let mut private_membership_proofs_iter = private_account_membership_proofs.iter(); let mut output_index = 0; for i in 0..n_accounts { @@ -158,8 +161,11 @@ fn main() { if visibility_mask[i] == 1 { // Private account with authentication - let (nsk, membership_proof) = - private_auth_iter.next().expect("Missing private auth"); + let nsk = private_nsks_iter.next().expect("Missing nsk"); + + let membership_proof = private_membership_proofs_iter + .next() + .expect("Missing membership proof"); // Verify the nullifier public key let expected_npk = NullifierPublicKey::from(nsk); @@ -223,15 +229,19 @@ fn main() { } if private_nonces_iter.next().is_some() { - panic!("Too many nonces."); + panic!("Too many nonces"); } if private_keys_iter.next().is_some() { - panic!("Too many private account keys."); + panic!("Too many private account keys"); } - if private_auth_iter.next().is_some() { - panic!("Too many private account authentication keys."); + if private_nsks_iter.next().is_some() { + panic!("Too many private account authentication keys"); + } + + if private_membership_proofs_iter.next().is_some() { + panic!("Too many private account membership proofs"); } let output = PrivacyPreservingCircuitOutput { diff --git a/nssa/src/privacy_preserving_transaction/circuit.rs b/nssa/src/privacy_preserving_transaction/circuit.rs index 95933a3..b45f17c 100644 --- a/nssa/src/privacy_preserving_transaction/circuit.rs +++ b/nssa/src/privacy_preserving_transaction/circuit.rs @@ -44,13 +44,15 @@ impl From for ProgramWithDependencies { /// Generates a proof of the execution of a NSSA program inside the privacy preserving execution /// circuit +#[expect(clippy::too_many_arguments, reason = "TODO: fix later")] pub fn execute_and_prove( pre_states: &[AccountWithMetadata], instruction_data: &InstructionData, visibility_mask: &[u8], private_account_nonces: &[u128], private_account_keys: &[(NullifierPublicKey, SharedSecretKey)], - private_account_auth: &[(NullifierSecretKey, MembershipProof)], + private_account_nsks: &[NullifierSecretKey], + private_account_membership_proofs: &[MembershipProof], program_with_dependencies: &ProgramWithDependencies, ) -> Result<(PrivacyPreservingCircuitOutput, Proof), NssaError> { let mut program = &program_with_dependencies.program; @@ -105,7 +107,8 @@ pub fn execute_and_prove( visibility_mask: visibility_mask.to_vec(), private_account_nonces: private_account_nonces.to_vec(), private_account_keys: private_account_keys.to_vec(), - private_account_auth: private_account_auth.to_vec(), + private_account_nsks: private_account_nsks.to_vec(), + private_account_membership_proofs: private_account_membership_proofs.to_vec(), program_id: program_with_dependencies.program.id(), }; @@ -218,6 +221,7 @@ mod tests { &[0xdeadbeef], &[(recipient_keys.npk(), shared_secret.clone())], &[], + &[], &Program::authenticated_transfer_program().into(), ) .unwrap(); @@ -315,10 +319,8 @@ mod tests { (sender_keys.npk(), shared_secret_1.clone()), (recipient_keys.npk(), shared_secret_2.clone()), ], - &[( - sender_keys.nsk, - commitment_set.get_proof_for(&commitment_sender).unwrap(), - )], + &[sender_keys.nsk], + &[commitment_set.get_proof_for(&commitment_sender).unwrap()], &program.into(), ) .unwrap(); diff --git a/nssa/src/state.rs b/nssa/src/state.rs index 86df3a5..408b7e9 100644 --- a/nssa/src/state.rs +++ b/nssa/src/state.rs @@ -868,6 +868,7 @@ pub mod tests { &[0xdeadbeef], &[(recipient_keys.npk(), shared_secret)], &[], + &[], &Program::authenticated_transfer_program().into(), ) .unwrap(); @@ -916,10 +917,8 @@ pub mod tests { (sender_keys.npk(), shared_secret_1), (recipient_keys.npk(), shared_secret_2), ], - &[( - sender_keys.nsk, - state.get_proof_for_commitment(&sender_commitment).unwrap(), - )], + &[sender_keys.nsk], + &[state.get_proof_for_commitment(&sender_commitment).unwrap()], &program.into(), ) .unwrap(); @@ -968,10 +967,8 @@ pub mod tests { &[1, 0], &[new_nonce], &[(sender_keys.npk(), shared_secret)], - &[( - sender_keys.nsk, - state.get_proof_for_commitment(&sender_commitment).unwrap(), - )], + &[sender_keys.nsk], + &[state.get_proof_for_commitment(&sender_commitment).unwrap()], &program.into(), ) .unwrap(); @@ -1185,6 +1182,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1211,6 +1209,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1237,6 +1236,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1263,6 +1263,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1291,6 +1292,7 @@ pub mod tests { &[], &[], &[], + &[], &program.to_owned().into(), ); @@ -1317,6 +1319,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1352,6 +1355,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1378,6 +1382,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1413,6 +1418,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1450,6 +1456,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1490,7 +1497,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1524,7 +1532,8 @@ pub mod tests { &[1, 2], &[0xdeadbeef1, 0xdeadbeef2], &private_account_keys, - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1549,7 +1558,7 @@ pub mod tests { AccountWithMetadata::new(Account::default(), false, &recipient_keys.npk()); // Setting no auth key for an execution with one non default private accounts. - let private_account_auth = []; + let private_account_nsks = []; let result = execute_and_prove( &[private_account_1, private_account_2], &Program::serialize_instruction(10u128).unwrap(), @@ -1565,7 +1574,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &private_account_auth, + &private_account_nsks, + &[], &program.into(), ); @@ -1601,19 +1611,20 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ]; - let private_account_auth = [ - // Setting the recipient key to authorize the sender. - // This should be set to the sender private account in - // a normal circumstance. The recipient can't authorize this. - (recipient_keys.nsk, (0, vec![])), - ]; + + // Setting the recipient key to authorize the sender. + // This should be set to the sender private account in + // a normal circumstance. The recipient can't authorize this. + let private_account_nsks = [recipient_keys.nsk]; + let private_account_membership_proofs = [(0, vec![])]; let result = execute_and_prove( &[private_account_1, private_account_2], &Program::serialize_instruction(10u128).unwrap(), &[1, 2], &[0xdeadbeef1, 0xdeadbeef2], &private_account_keys, - &private_account_auth, + &private_account_nsks, + &private_account_membership_proofs, &program.into(), ); @@ -1659,7 +1670,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1706,7 +1718,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1752,7 +1765,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1798,7 +1812,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1842,7 +1857,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1872,6 +1888,7 @@ pub mod tests { &[], &[], &[], + &[], &program.into(), ); @@ -1913,7 +1930,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1959,7 +1977,8 @@ pub mod tests { &[1, 2], &[0xdeadbeef1, 0xdeadbeef2], &private_account_keys, - &[(sender_keys.nsk, (0, vec![]))], + &[sender_keys.nsk], + &[(0, vec![])], &program.into(), ); @@ -1986,10 +2005,8 @@ pub mod tests { // Setting two private account keys for a circuit execution with only one non default // private account (visibility mask equal to 1 means that auth keys are expected). let visibility_mask = [1, 2]; - let private_account_auth = [ - (sender_keys.nsk, (0, vec![])), - (recipient_keys.nsk, (1, vec![])), - ]; + let private_account_nsks = [sender_keys.nsk, recipient_keys.nsk]; + let private_account_membership_proofs = [(0, vec![]), (1, vec![])]; let result = execute_and_prove( &[private_account_1, private_account_2], &Program::serialize_instruction(10u128).unwrap(), @@ -2005,7 +2022,8 @@ pub mod tests { SharedSecretKey::new(&[56; 32], &recipient_keys.ivk()), ), ], - &private_account_auth, + &private_account_nsks, + &private_account_membership_proofs, &program.into(), ); @@ -2082,10 +2100,8 @@ pub mod tests { ); let visibility_mask = [1, 1]; - let private_account_auth = [ - (sender_keys.nsk, (1, vec![])), - (sender_keys.nsk, (1, vec![])), - ]; + let private_account_nsks = [sender_keys.nsk, sender_keys.nsk]; + let private_account_membership_proofs = [(1, vec![]), (1, vec![])]; let shared_secret = SharedSecretKey::new(&[55; 32], &sender_keys.ivk()); let result = execute_and_prove( &[private_account_1.clone(), private_account_1], @@ -2096,7 +2112,8 @@ pub mod tests { (sender_keys.npk(), shared_secret.clone()), (sender_keys.npk(), shared_secret), ], - &private_account_auth, + &private_account_nsks, + &private_account_membership_proofs, &program.into(), ); @@ -2397,15 +2414,10 @@ pub mod tests { &[1, 1], &[from_new_nonce, to_new_nonce], &[(from_keys.npk(), to_ss), (to_keys.npk(), from_ss)], + &[from_keys.nsk, to_keys.nsk], &[ - ( - from_keys.nsk, - state.get_proof_for_commitment(&from_commitment).unwrap(), - ), - ( - to_keys.nsk, - state.get_proof_for_commitment(&to_commitment).unwrap(), - ), + state.get_proof_for_commitment(&from_commitment).unwrap(), + state.get_proof_for_commitment(&to_commitment).unwrap(), ], &program_with_deps, ) diff --git a/wallet/src/lib.rs b/wallet/src/lib.rs index bc28311..237b2f2 100644 --- a/wallet/src/lib.rs +++ b/wallet/src/lib.rs @@ -283,6 +283,7 @@ impl WalletCore { .map(|keys| (keys.npk.clone(), keys.ssk.clone())) .collect::>(), &acc_manager.private_account_auth(), + &acc_manager.private_account_membership_proofs(), &program.to_owned().into(), ) .unwrap(); @@ -303,7 +304,7 @@ impl WalletCore { nssa::privacy_preserving_transaction::witness_set::WitnessSet::for_message( &message, proof, - &acc_manager.witness_signing_keys(), + &acc_manager.public_account_auth(), ); let tx = PrivacyPreservingTransaction::new(message, witness_set); diff --git a/wallet/src/pinata_interactions.rs b/wallet/src/pinata_interactions.rs index 65a67b7..5804768 100644 --- a/wallet/src/pinata_interactions.rs +++ b/wallet/src/pinata_interactions.rs @@ -58,7 +58,8 @@ impl WalletCore { &[0, 1], &produce_random_nonces(1), &[(winner_npk.clone(), shared_secret_winner.clone())], - &[(winner_nsk.unwrap(), winner_proof)], + &[(winner_nsk.unwrap())], + &[winner_proof], &program.into(), ) .unwrap(); @@ -125,6 +126,7 @@ impl WalletCore { &produce_random_nonces(1), &[(winner_npk.clone(), shared_secret_winner.clone())], &[], + &[] &program.into(), ) .unwrap(); diff --git a/wallet/src/privacy_preserving_tx.rs b/wallet/src/privacy_preserving_tx.rs index e79bbac..4ddf5e6 100644 --- a/wallet/src/privacy_preserving_tx.rs +++ b/wallet/src/privacy_preserving_tx.rs @@ -133,11 +133,21 @@ impl AccountManager { .collect() } - pub fn private_account_auth(&self) -> Vec<(NullifierSecretKey, MembershipProof)> { + pub fn private_account_auth(&self) -> Vec { self.states .iter() .filter_map(|state| match state { - State::Private(pre) => Some((pre.nsk?, pre.proof.clone()?)), + State::Private(pre) => pre.nsk, + _ => None, + }) + .collect() + } + + pub fn private_account_membership_proofs(&self) -> Vec { + self.states + .iter() + .filter_map(|state| match state { + State::Private(pre) => pre.proof.clone(), _ => None, }) .collect() @@ -153,7 +163,7 @@ impl AccountManager { .collect() } - pub fn witness_signing_keys(&self) -> Vec<&PrivateKey> { + pub fn public_account_auth(&self) -> Vec<&PrivateKey> { self.states .iter() .filter_map(|state| match state {