move zone_id into {input,output}witness

This commit is contained in:
Giacomo Pasini 2024-11-27 17:17:27 +01:00
parent 3646971fd9
commit 720836e7f2
No known key found for this signature in database
GPG Key ID: FC08489D2D895D4B
11 changed files with 140 additions and 163 deletions

View File

@ -1,9 +1,6 @@
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use crate::{ use crate::{cl::partial_tx::PartialTx, zone_layer::notes::ZoneId};
cl::{partial_tx::PartialTx, BalanceWitness, PartialTxWitness},
zone_layer::notes::ZoneId,
};
use sha2::{Digest, Sha256}; use sha2::{Digest, Sha256};
use std::collections::HashSet; use std::collections::HashSet;
@ -45,27 +42,10 @@ impl Bundle {
} }
} }
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct BundleWitness {
pub partials: Vec<PartialTxWitness>,
}
impl BundleWitness {
pub fn balance(&self) -> BalanceWitness {
BalanceWitness::combine(self.partials.iter().map(|ptx| ptx.balance()), [0u8; 16])
}
// pub fn commit(&self) -> Bundle {
// Bundle {
// partials: Vec::from_iter(self.partials.iter().map(|ptx| ptx.commit())),
// }
// }
}
#[cfg(test)] #[cfg(test)]
mod test { mod test {
use crate::cl::{ use crate::cl::{
balance::UnitBalance, balance::{BalanceWitness, UnitBalance},
input::InputWitness, input::InputWitness,
note::{derive_unit, NoteWitness}, note::{derive_unit, NoteWitness},
nullifier::NullifierSecret, nullifier::NullifierSecret,
@ -73,25 +53,35 @@ mod test {
partial_tx::PartialTxWitness, partial_tx::PartialTxWitness,
}; };
use super::*;
#[test] #[test]
fn test_bundle_balance() { fn test_bundle_balance() {
let mut rng = rand::thread_rng(); let mut rng = rand::thread_rng();
let zone_id = [0; 32];
let (nmo, eth, crv) = (derive_unit("NMO"), derive_unit("ETH"), derive_unit("CRV")); let (nmo, eth, crv) = (derive_unit("NMO"), derive_unit("ETH"), derive_unit("CRV"));
let nf_a = NullifierSecret::random(&mut rng); let nf_a = NullifierSecret::random(&mut rng);
let nf_b = NullifierSecret::random(&mut rng); let nf_b = NullifierSecret::random(&mut rng);
let nf_c = NullifierSecret::random(&mut rng); let nf_c = NullifierSecret::random(&mut rng);
let nmo_10_utxo = OutputWitness::new(NoteWitness::basic(10, nmo, &mut rng), nf_a.commit()); let nmo_10_utxo = OutputWitness::new(
NoteWitness::basic(10, nmo, &mut rng),
nf_a.commit(),
zone_id,
);
let nmo_10_in = InputWitness::from_output(nmo_10_utxo, nf_a); let nmo_10_in = InputWitness::from_output(nmo_10_utxo, nf_a);
let eth_23_utxo = OutputWitness::new(NoteWitness::basic(23, eth, &mut rng), nf_b.commit()); let eth_23_utxo = OutputWitness::new(
NoteWitness::basic(23, eth, &mut rng),
nf_b.commit(),
zone_id,
);
let eth_23_in = InputWitness::from_output(eth_23_utxo, nf_b); let eth_23_in = InputWitness::from_output(eth_23_utxo, nf_b);
let crv_4840_out = let crv_4840_out = OutputWitness::new(
OutputWitness::new(NoteWitness::basic(4840, crv, &mut rng), nf_c.commit()); NoteWitness::basic(4840, crv, &mut rng),
nf_c.commit(),
zone_id,
);
let ptx_unbalanced = PartialTxWitness { let ptx_unbalanced = PartialTxWitness {
inputs: vec![nmo_10_in, eth_23_in], inputs: vec![nmo_10_in, eth_23_in],
@ -99,13 +89,9 @@ mod test {
balance_blinding: BalanceWitness::random_blinding(&mut rng), balance_blinding: BalanceWitness::random_blinding(&mut rng),
}; };
let bundle_witness = BundleWitness { assert!(!ptx_unbalanced.balance().is_zero());
partials: vec![ptx_unbalanced.clone()],
};
assert!(!bundle_witness.balance().is_zero());
assert_eq!( assert_eq!(
bundle_witness.balance().balances, ptx_unbalanced.balance().balances,
vec![ vec![
UnitBalance { UnitBalance {
unit: nmo, unit: nmo,
@ -129,10 +115,12 @@ mod test {
let nmo_10_out = OutputWitness::new( let nmo_10_out = OutputWitness::new(
NoteWitness::basic(10, nmo, &mut rng), NoteWitness::basic(10, nmo, &mut rng),
NullifierSecret::random(&mut rng).commit(), // transferring to a random owner NullifierSecret::random(&mut rng).commit(), // transferring to a random owner
zone_id,
); );
let eth_23_out = OutputWitness::new( let eth_23_out = OutputWitness::new(
NoteWitness::basic(23, eth, &mut rng), NoteWitness::basic(23, eth, &mut rng),
NullifierSecret::random(&mut rng).commit(), // transferring to a random owner NullifierSecret::random(&mut rng).commit(), // transferring to a random owner
zone_id,
); );
let ptx_solved = PartialTxWitness { let ptx_solved = PartialTxWitness {
@ -141,11 +129,10 @@ mod test {
balance_blinding: BalanceWitness::random_blinding(&mut rng), balance_blinding: BalanceWitness::random_blinding(&mut rng),
}; };
let witness = BundleWitness { let bundle_balance =
partials: vec![ptx_unbalanced, ptx_solved], BalanceWitness::combine([ptx_unbalanced.balance(), ptx_solved.balance()], [0; 16]);
};
assert!(witness.balance().is_zero()); assert!(bundle_balance.is_zero());
assert_eq!(witness.balance().balances, vec![]); assert_eq!(bundle_balance.balances, vec![]);
} }
} }

View File

@ -24,59 +24,65 @@ pub struct Input {
pub struct InputWitness { pub struct InputWitness {
pub note: NoteWitness, pub note: NoteWitness,
pub nf_sk: NullifierSecret, pub nf_sk: NullifierSecret,
pub zone_id: ZoneId,
} }
impl InputWitness { impl InputWitness {
pub fn new(note: NoteWitness, nf_sk: NullifierSecret) -> Self { pub fn new(note: NoteWitness, nf_sk: NullifierSecret, zone_id: ZoneId) -> Self {
Self { note, nf_sk } Self {
note,
nf_sk,
zone_id,
}
} }
pub fn from_output(output: OutputWitness, nf_sk: NullifierSecret) -> Self { pub fn from_output(output: OutputWitness, nf_sk: NullifierSecret) -> Self {
assert_eq!(nf_sk.commit(), output.nf_pk); assert_eq!(nf_sk.commit(), output.nf_pk);
Self::new(output.note, nf_sk) Self::new(output.note, nf_sk, output.zone_id)
} }
pub fn public(output: OutputWitness) -> Self { pub fn public(output: OutputWitness) -> Self {
let nf_sk = NullifierSecret::zero(); let nf_sk = NullifierSecret::zero();
assert_eq!(nf_sk.commit(), output.nf_pk); // ensure the output was a public UTXO assert_eq!(nf_sk.commit(), output.nf_pk); // ensure the output was a public UTXO
Self::new(output.note, nf_sk) Self::new(output.note, nf_sk, output.zone_id)
} }
pub fn evolved_nonce(&self, tag: &dyn AsRef<[u8]>, domain: &[u8]) -> Nonce { pub fn evolved_nonce(&self, domain: &[u8]) -> Nonce {
let mut hasher = Sha256::new(); let mut hasher = Sha256::new();
hasher.update(b"NOMOS_COIN_EVOLVE"); hasher.update(b"NOMOS_COIN_EVOLVE");
hasher.update(domain); hasher.update(domain);
hasher.update(self.nf_sk.0); hasher.update(self.nf_sk.0);
hasher.update(self.note.commit(tag, self.nf_sk.commit()).0); hasher.update(self.note.commit(&self.zone_id, self.nf_sk.commit()).0);
let nonce_bytes: [u8; 32] = hasher.finalize().into(); let nonce_bytes: [u8; 32] = hasher.finalize().into();
Nonce::from_bytes(nonce_bytes) Nonce::from_bytes(nonce_bytes)
} }
pub fn evolve_output(&self, tag: &dyn AsRef<[u8]>, domain: &[u8]) -> OutputWitness { pub fn evolve_output(&self, domain: &[u8]) -> OutputWitness {
OutputWitness { OutputWitness {
note: NoteWitness { note: NoteWitness {
nonce: self.evolved_nonce(tag, domain), nonce: self.evolved_nonce(domain),
..self.note ..self.note
}, },
nf_pk: self.nf_sk.commit(), nf_pk: self.nf_sk.commit(),
zone_id: self.zone_id,
} }
} }
pub fn nullifier(&self, tag: &dyn AsRef<[u8]>) -> Nullifier { pub fn nullifier(&self) -> Nullifier {
Nullifier::new(tag, self.nf_sk, self.note_commitment(tag)) Nullifier::new(&self.zone_id, self.nf_sk, self.note_commitment())
} }
pub fn commit(&self, zone_id: ZoneId) -> Input { pub fn commit(&self) -> Input {
Input { Input {
nullifier: self.nullifier(&zone_id), nullifier: self.nullifier(),
constraint: self.note.constraint, constraint: self.note.constraint,
zone_id, zone_id: self.zone_id,
} }
} }
pub fn note_commitment(&self, tag: &dyn AsRef<[u8]>) -> NoteCommitment { pub fn note_commitment(&self) -> NoteCommitment {
self.note.commit(tag, self.nf_sk.commit()) self.note.commit(&self.zone_id, self.nf_sk.commit())
} }
} }

View File

@ -65,10 +65,11 @@ impl MMR {
} }
pub fn commit(&self) -> [u8; 32] { pub fn commit(&self) -> [u8; 32] {
// todo: baggin the peaks
let mut hasher = Sha256::new(); let mut hasher = Sha256::new();
for mrr_root in self.roots.iter() { for mmr_root in self.roots.iter() {
hasher.update(mrr_root.root); hasher.update(mmr_root.root);
hasher.update(mrr_root.height.to_le_bytes()); hasher.update(mmr_root.height.to_le_bytes());
} }
hasher.finalize().into() hasher.finalize().into()
} }

View File

@ -11,7 +11,7 @@ pub mod output;
pub mod partial_tx; pub mod partial_tx;
pub use balance::{Balance, BalanceWitness}; pub use balance::{Balance, BalanceWitness};
pub use bundle::{Bundle, BundleWitness}; pub use bundle::Bundle;
pub use input::{Input, InputWitness}; pub use input::{Input, InputWitness};
pub use note::{Constraint, Nonce, NoteCommitment, NoteWitness}; pub use note::{Constraint, Nonce, NoteCommitment, NoteWitness};
pub use nullifier::{Nullifier, NullifierCommitment, NullifierSecret}; pub use nullifier::{Nullifier, NullifierCommitment, NullifierSecret};

View File

@ -19,26 +19,35 @@ pub struct Output {
pub struct OutputWitness { pub struct OutputWitness {
pub note: NoteWitness, pub note: NoteWitness,
pub nf_pk: NullifierCommitment, pub nf_pk: NullifierCommitment,
pub zone_id: ZoneId,
} }
impl OutputWitness { impl OutputWitness {
pub fn new(note: NoteWitness, nf_pk: NullifierCommitment) -> Self { pub fn new(note: NoteWitness, nf_pk: NullifierCommitment, zone_id: ZoneId) -> Self {
Self { note, nf_pk } Self {
} note,
nf_pk,
pub fn public(note: NoteWitness) -> Self {
let nf_pk = NullifierSecret::zero().commit();
Self { note, nf_pk }
}
pub fn commit_note(&self, tag: &dyn AsRef<[u8]>) -> NoteCommitment {
self.note.commit(tag, self.nf_pk)
}
pub fn commit(&self, zone_id: ZoneId) -> Output {
Output {
zone_id, zone_id,
note_comm: self.commit_note(&zone_id), }
}
pub fn public(note: NoteWitness, zone_id: ZoneId) -> Self {
let nf_pk = NullifierSecret::zero().commit();
Self {
note,
nf_pk,
zone_id,
}
}
pub fn commit_note(&self) -> NoteCommitment {
self.note.commit(&self.zone_id, self.nf_pk)
}
pub fn commit(&self) -> Output {
Output {
zone_id: self.zone_id,
note_comm: self.commit_note(),
} }
} }
} }

View File

@ -1,14 +1,11 @@
use rand_core::{CryptoRngCore, RngCore}; use rand_core::{CryptoRngCore, RngCore};
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use crate::{ use crate::cl::{
cl::{ balance::{Balance, BalanceWitness},
balance::{Balance, BalanceWitness}, input::{Input, InputWitness},
input::{Input, InputWitness}, merkle,
merkle, output::{Output, OutputWitness},
output::{Output, OutputWitness},
},
zone_layer::notes::ZoneId,
}; };
pub const MAX_INPUTS: usize = 8; pub const MAX_INPUTS: usize = 8;
@ -68,33 +65,17 @@ impl PartialTxWitness {
BalanceWitness::from_ptx(self, self.balance_blinding) BalanceWitness::from_ptx(self, self.balance_blinding)
} }
pub fn commit(&self, input_zones: &[ZoneId], output_zones: &[ZoneId]) -> PartialTx { pub fn commit(&self) -> PartialTx {
assert_eq!(self.inputs.len(), input_zones.len());
assert_eq!(self.outputs.len(), output_zones.len());
PartialTx { PartialTx {
inputs: self inputs: self.inputs.iter().map(InputWitness::commit).collect(),
.inputs outputs: self.outputs.iter().map(OutputWitness::commit).collect(),
.iter()
.zip(input_zones.iter())
.map(|(i, z)| i.commit(*z))
.collect(),
outputs: self
.outputs
.iter()
.zip(output_zones.iter())
.map(|(o, z)| o.commit(*z))
.collect(),
balance: self.balance().commit(), balance: self.balance().commit(),
} }
} }
pub fn input_witness(&self, zone_id: ZoneId, idx: usize) -> PartialTxInputWitness { pub fn input_witness(&self, idx: usize) -> PartialTxInputWitness {
let input_bytes = Vec::from_iter( let input_bytes =
self.inputs Vec::from_iter(self.inputs.iter().map(|i| i.commit().to_bytes().to_vec()));
.iter()
.map(|i| i.commit(zone_id).to_bytes().to_vec()),
);
let input_merkle_leaves = merkle::padded_leaves::<MAX_INPUTS>(&input_bytes); let input_merkle_leaves = merkle::padded_leaves::<MAX_INPUTS>(&input_bytes);
let path = merkle::path(input_merkle_leaves, idx); let path = merkle::path(input_merkle_leaves, idx);
@ -102,12 +83,9 @@ impl PartialTxWitness {
PartialTxInputWitness { input, path } PartialTxInputWitness { input, path }
} }
pub fn output_witness(&self, zone_id: ZoneId, idx: usize) -> PartialTxOutputWitness { pub fn output_witness(&self, idx: usize) -> PartialTxOutputWitness {
let output_bytes = Vec::from_iter( let output_bytes =
self.outputs Vec::from_iter(self.outputs.iter().map(|o| o.commit().to_bytes().to_vec()));
.iter()
.map(|o| o.commit(zone_id).to_bytes().to_vec()),
);
let output_merkle_leaves = merkle::padded_leaves::<MAX_OUTPUTS>(&output_bytes); let output_merkle_leaves = merkle::padded_leaves::<MAX_OUTPUTS>(&output_bytes);
let path = merkle::path(output_merkle_leaves, idx); let path = merkle::path(output_merkle_leaves, idx);
@ -151,8 +129,8 @@ pub struct PartialTxInputWitness {
} }
impl PartialTxInputWitness { impl PartialTxInputWitness {
pub fn input_root(&self, zone_id: ZoneId) -> [u8; 32] { pub fn input_root(&self) -> [u8; 32] {
let leaf = merkle::leaf(&self.input.commit(zone_id).to_bytes()); let leaf = merkle::leaf(&self.input.commit().to_bytes());
merkle::path_root(leaf, &self.path) merkle::path_root(leaf, &self.path)
} }
} }
@ -165,8 +143,8 @@ pub struct PartialTxOutputWitness {
} }
impl PartialTxOutputWitness { impl PartialTxOutputWitness {
pub fn output_root(&self, zone_id: ZoneId) -> [u8; 32] { pub fn output_root(&self) -> [u8; 32] {
let leaf = merkle::leaf(&self.output.commit(zone_id).to_bytes()); let leaf = merkle::leaf(&self.output.commit().to_bytes());
merkle::path_root(leaf, &self.path) merkle::path_root(leaf, &self.path)
} }
} }

View File

@ -1,16 +1,20 @@
use cl::cl::{ use cl::{
note::derive_unit, BalanceWitness, BundleWitness, InputWitness, NoteWitness, cl::{
NullifierCommitment, NullifierSecret, OutputWitness, PartialTxWitness, note::derive_unit, BalanceWitness, InputWitness, NoteWitness, NullifierCommitment,
NullifierSecret, OutputWitness, PartialTxWitness,
},
zone_layer::notes::ZoneId,
}; };
fn receive_utxo(note: NoteWitness, nf_pk: NullifierCommitment) -> OutputWitness { fn receive_utxo(note: NoteWitness, nf_pk: NullifierCommitment, zone_id: ZoneId) -> OutputWitness {
OutputWitness::new(note, nf_pk) OutputWitness::new(note, nf_pk, zone_id)
} }
#[test] #[test]
fn test_simple_transfer() { fn test_simple_transfer() {
let nmo = derive_unit("NMO"); let nmo = derive_unit("NMO");
let mut rng = rand::thread_rng(); let mut rng = rand::thread_rng();
let zone_id = [0; 32];
let sender_nf_sk = NullifierSecret::random(&mut rng); let sender_nf_sk = NullifierSecret::random(&mut rng);
let sender_nf_pk = sender_nf_sk.commit(); let sender_nf_pk = sender_nf_sk.commit();
@ -18,12 +22,16 @@ fn test_simple_transfer() {
let recipient_nf_pk = NullifierSecret::random(&mut rng).commit(); let recipient_nf_pk = NullifierSecret::random(&mut rng).commit();
// Assume the sender has received an unspent output from somewhere // Assume the sender has received an unspent output from somewhere
let utxo = receive_utxo(NoteWitness::basic(10, nmo, &mut rng), sender_nf_pk); let utxo = receive_utxo(NoteWitness::basic(10, nmo, &mut rng), sender_nf_pk, zone_id);
// and wants to send 8 NMO to some recipient and return 2 NMO to itself. // and wants to send 8 NMO to some recipient and return 2 NMO to itself.
let recipient_output = let recipient_output = OutputWitness::new(
OutputWitness::new(NoteWitness::basic(8, nmo, &mut rng), recipient_nf_pk); NoteWitness::basic(8, nmo, &mut rng),
let change_output = OutputWitness::new(NoteWitness::basic(2, nmo, &mut rng), sender_nf_pk); recipient_nf_pk,
zone_id,
);
let change_output =
OutputWitness::new(NoteWitness::basic(2, nmo, &mut rng), sender_nf_pk, zone_id);
let ptx_witness = PartialTxWitness { let ptx_witness = PartialTxWitness {
inputs: vec![InputWitness::from_output(utxo, sender_nf_sk)], inputs: vec![InputWitness::from_output(utxo, sender_nf_sk)],
@ -31,10 +39,5 @@ fn test_simple_transfer() {
balance_blinding: BalanceWitness::random_blinding(&mut rng), balance_blinding: BalanceWitness::random_blinding(&mut rng),
}; };
let bundle = BundleWitness { assert!(ptx_witness.balance().is_zero())
partials: vec![ptx_witness],
};
assert!(bundle.balance().is_zero())
} }

View File

@ -20,7 +20,7 @@ pub struct ProvedLedgerTransition {
// TODO: find a better name // TODO: find a better name
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub struct ProvedBundle { pub struct ProvedBundle {
pub bundle: ProvedBalance, pub balance: ProvedBalance,
pub ptxs: Vec<ProvedPartialTx>, pub ptxs: Vec<ProvedPartialTx>,
} }
@ -30,7 +30,7 @@ impl ProvedBundle {
} }
fn proofs(&self) -> Vec<risc0_zkvm::Receipt> { fn proofs(&self) -> Vec<risc0_zkvm::Receipt> {
let mut proofs = vec![self.bundle.risc0_receipt.clone()]; let mut proofs = vec![self.balance.risc0_receipt.clone()];
proofs.extend(self.ptxs.iter().map(|p| p.risc0_receipt.clone())); proofs.extend(self.ptxs.iter().map(|p| p.risc0_receipt.clone()));
proofs proofs
} }

View File

@ -2,7 +2,6 @@ use ledger_proof_statements::ptx::{PtxPrivate, PtxPublic};
use crate::error::{Error, Result}; use crate::error::{Error, Result};
use cl::cl::{merkle, PartialTxWitness}; use cl::cl::{merkle, PartialTxWitness};
use cl::zone_layer::notes::ZoneId;
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
pub struct ProvedPartialTx { pub struct ProvedPartialTx {
@ -15,15 +14,11 @@ impl ProvedPartialTx {
ptx_witness: PartialTxWitness, ptx_witness: PartialTxWitness,
input_cm_paths: Vec<Vec<merkle::PathNode>>, input_cm_paths: Vec<Vec<merkle::PathNode>>,
cm_roots: Vec<[u8; 32]>, cm_roots: Vec<[u8; 32]>,
from: Vec<ZoneId>,
to: Vec<ZoneId>,
) -> Result<ProvedPartialTx> { ) -> Result<ProvedPartialTx> {
let ptx_private = PtxPrivate { let ptx_private = PtxPrivate {
ptx: ptx_witness, ptx: ptx_witness,
input_cm_paths, input_cm_paths,
cm_roots: cm_roots.clone(), cm_roots: cm_roots.clone(),
from,
to,
}; };
let env = risc0_zkvm::ExecutorEnv::builder() let env = risc0_zkvm::ExecutorEnv::builder()

View File

@ -1,12 +1,11 @@
use cl::{ use cl::{
cl::{ cl::{
balance::Unit, merkle, mmr::MMR, note::derive_unit, BalanceWitness, BundleWitness, balance::Unit, merkle, mmr::MMR, note::derive_unit, BalanceWitness, InputWitness,
InputWitness, NoteWitness, NullifierCommitment, NullifierSecret, OutputWitness, NoteWitness, NullifierCommitment, NullifierSecret, OutputWitness, PartialTxWitness,
PartialTxWitness,
}, },
zone_layer::{ zone_layer::{
ledger::LedgerWitness, ledger::LedgerWitness,
notes::ZoneNote, notes::{ZoneId, ZoneNote},
tx::{UpdateBundle, ZoneUpdate}, tx::{UpdateBundle, ZoneUpdate},
}, },
}; };
@ -43,8 +42,8 @@ impl User {
} }
} }
fn receive_utxo(note: NoteWitness, nf_pk: NullifierCommitment) -> OutputWitness { fn receive_utxo(note: NoteWitness, nf_pk: NullifierCommitment, zone_id: ZoneId) -> OutputWitness {
OutputWitness::new(note, nf_pk) OutputWitness::new(note, nf_pk, zone_id)
} }
fn cross_transfer_transition( fn cross_transfer_transition(
@ -52,18 +51,23 @@ fn cross_transfer_transition(
input_path: Vec<merkle::PathNode>, input_path: Vec<merkle::PathNode>,
to: User, to: User,
amount: u64, amount: u64,
zone_a: [u8; 32], zone_a: ZoneId,
zone_b: [u8; 32], zone_b: ZoneId,
mut ledger_a: LedgerWitness, mut ledger_a: LedgerWitness,
mut ledger_b: LedgerWitness, mut ledger_b: LedgerWitness,
) -> (ProvedLedgerTransition, ProvedLedgerTransition) { ) -> (ProvedLedgerTransition, ProvedLedgerTransition) {
let mut rng = rand::thread_rng(); let mut rng = rand::thread_rng();
assert!(amount <= input.note.value); assert!(amount <= input.note.value);
let change = input.note.value - amount; let change = input.note.value - amount;
let transfer = OutputWitness::new(NoteWitness::basic(amount, *nmo(), &mut rng), to.pk()); let transfer = OutputWitness::new(
NoteWitness::basic(amount, *nmo(), &mut rng),
to.pk(),
zone_b,
);
let change = OutputWitness::new( let change = OutputWitness::new(
NoteWitness::basic(change, *nmo(), &mut rng), NoteWitness::basic(change, *nmo(), &mut rng),
input.nf_sk.commit(), input.nf_sk.commit(),
zone_a,
); );
// Construct the ptx consuming the input and producing the two outputs. // Construct the ptx consuming the input and producing the two outputs.
@ -76,24 +80,22 @@ fn cross_transfer_transition(
ptx_witness.clone(), ptx_witness.clone(),
vec![input_path], vec![input_path],
vec![ledger_a.commitments.roots[0].root], vec![ledger_a.commitments.roots[0].root],
vec![zone_a],
vec![zone_b, zone_a],
) )
.unwrap(); .unwrap();
let bundle = ProvedBalance::prove(&BalancePrivate { let balance = ProvedBalance::prove(&BalancePrivate {
balances: vec![ptx_witness.balance()], balances: vec![ptx_witness.balance()],
}) })
.unwrap(); .unwrap();
let zone_tx = ProvedBundle { let zone_tx = ProvedBundle {
ptxs: vec![proved_ptx.clone()], ptxs: vec![proved_ptx.clone()],
bundle, balance,
}; };
// Prove the constraints for alices input (she uses the no-op constraint) // Prove the constraints for alices input (she uses the no-op constraint)
let constraint_proof = let constraint_proof =
ConstraintProof::prove_nop(input.nullifier(&zone_a), proved_ptx.public.ptx.root()); ConstraintProof::prove_nop(input.nullifier(), proved_ptx.public.ptx.root());
let ledger_a_transition = ProvedLedgerTransition::prove( let ledger_a_transition = ProvedLedgerTransition::prove(
ledger_a.clone(), ledger_a.clone(),
@ -106,10 +108,10 @@ fn cross_transfer_transition(
let ledger_b_transition = let ledger_b_transition =
ProvedLedgerTransition::prove(ledger_b.clone(), zone_b, vec![zone_tx], vec![]).unwrap(); ProvedLedgerTransition::prove(ledger_b.clone(), zone_b, vec![zone_tx], vec![]).unwrap();
ledger_a.commitments.push(&change.commit_note(&zone_a).0); ledger_a.commitments.push(&change.commit_note().0);
ledger_a.nullifiers.push(input.nullifier(&zone_a)); ledger_a.nullifiers.push(input.nullifier());
ledger_b.commitments.push(&transfer.commit_note(&zone_b).0); ledger_b.commitments.push(&transfer.commit_note().0);
assert_eq!(ledger_a_transition.public.ledger, ledger_a.commit()); assert_eq!(ledger_a_transition.public.ledger, ledger_a.commit());
assert_eq!(ledger_b_transition.public.ledger, ledger_b.commit()); assert_eq!(ledger_b_transition.public.ledger, ledger_b.commit());
@ -121,6 +123,9 @@ fn cross_transfer_transition(
fn zone_update_cross() { fn zone_update_cross() {
let mut rng = rand::thread_rng(); let mut rng = rand::thread_rng();
let zone_a_id = [0; 32];
let zone_b_id = [1; 32];
// alice is sending 8 NMO to bob. // alice is sending 8 NMO to bob.
let alice = User::random(&mut rng); let alice = User::random(&mut rng);
@ -130,15 +135,13 @@ fn zone_update_cross() {
let utxo = receive_utxo( let utxo = receive_utxo(
NoteWitness::stateless(10, *nmo(), ConstraintProof::nop_constraint(), &mut rng), NoteWitness::stateless(10, *nmo(), ConstraintProof::nop_constraint(), &mut rng),
alice.pk(), alice.pk(),
zone_a_id,
); );
let alice_input = InputWitness::from_output(utxo, alice.sk()); let alice_input = InputWitness::from_output(utxo, alice.sk());
let zone_a_id = [0; 32];
let zone_b_id = [1; 32];
let mut mmr = MMR::new(); let mut mmr = MMR::new();
let input_cm_path = mmr.push(&utxo.commit_note(&zone_a_id).0).path; let input_cm_path = mmr.push(&utxo.commit_note().0).path;
let ledger_a = LedgerWitness { let ledger_a = LedgerWitness {
commitments: mmr, commitments: mmr,

View File

@ -1,7 +1,4 @@
use cl::{ use cl::cl::{merkle, PartialTx, PartialTxWitness};
cl::{merkle, PartialTx, PartialTxWitness},
zone_layer::notes::ZoneId,
};
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)] #[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
@ -15,6 +12,4 @@ pub struct PtxPrivate {
pub ptx: PartialTxWitness, pub ptx: PartialTxWitness,
pub input_cm_paths: Vec<Vec<merkle::PathNode>>, pub input_cm_paths: Vec<Vec<merkle::PathNode>>,
pub cm_roots: Vec<[u8; 32]>, pub cm_roots: Vec<[u8; 32]>,
pub from: Vec<ZoneId>,
pub to: Vec<ZoneId>,
} }