diff --git a/core/CHANGELOG.md b/core/CHANGELOG.md index 3cec32f..7b53b28 100644 --- a/core/CHANGELOG.md +++ b/core/CHANGELOG.md @@ -10,8 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added - Add `elgamal::encrypt` and `elgamal::decrypt` -- Add `stealth_address` and `sync_address` functions directly to note [#208] -- Add a light sync method in the `ViewKey` [#199] +- Add `stealth_address` function directly to note [#208] - Add function `value_commitment` [#201] - Add function `transparent_value_commitment` [#201] - Add `owns()` and `owns_unchecked()` to `Secretkey` [#146] diff --git a/core/src/addresses.rs b/core/src/addresses.rs deleted file mode 100644 index c57b7c1..0000000 --- a/core/src/addresses.rs +++ /dev/null @@ -1,8 +0,0 @@ -// This Source Code Form is subject to the terms of the Mozilla Public -// License, v. 2.0. If a copy of the MPL was not distributed with this -// file, You can obtain one at http://mozilla.org/MPL/2.0/. -// -// Copyright (c) DUSK NETWORK. All rights reserved. - -pub mod stealth; -pub mod sync; diff --git a/core/src/addresses/sync.rs b/core/src/addresses/sync.rs deleted file mode 100644 index 86b7637..0000000 --- a/core/src/addresses/sync.rs +++ /dev/null @@ -1,93 +0,0 @@ -// This Source Code Form is subject to the terms of the Mozilla Public -// License, v. 2.0. If a copy of the MPL was not distributed with this -// file, You can obtain one at http://mozilla.org/MPL/2.0/. -// -// Copyright (c) DUSK NETWORK. All rights reserved. - -use crate::StealthAddress; -use dusk_jubjub::{JubJubAffine, JubJubExtended}; -use jubjub_schnorr::PublicKey as NotePublicKey; - -use dusk_bytes::{DeserializableSlice, Error, Serializable}; - -use subtle::{Choice, ConstantTimeEq}; - -#[cfg(feature = "rkyv-impl")] -use rkyv::{Archive, Deserialize, Serialize}; - -/// A `SyncAddress` allows for a fast sync of the wallet, and -/// is composed by a one-time DH point 'k' and an additional -/// random point `R`. -#[derive(Default, Debug, Clone, Copy)] -#[cfg_attr( - feature = "rkyv-impl", - derive(Archive, Serialize, Deserialize), - archive_attr(derive(bytecheck::CheckBytes)) -)] -pub struct SyncAddress { - pub(crate) R: JubJubExtended, - pub(crate) k: JubJubExtended, -} - -impl SyncAddress { - /// Create a sync address from its internal parts - /// For additional information, check [PublicKey::from_raw_unchecked]. - pub const fn from_raw_unchecked( - R: JubJubExtended, - k: JubJubExtended, - ) -> Self { - Self { R, k } - } - - /// Gets the random point `R` - pub const fn R(&self) -> &JubJubExtended { - &self.R - } - - /// Gets the DH `k` - pub const fn k(&self) -> &JubJubExtended { - &self.k - } -} - -impl ConstantTimeEq for SyncAddress { - fn ct_eq(&self, other: &Self) -> Choice { - self.k().ct_eq(other.k()) & self.R.ct_eq(&other.R) - } -} - -impl PartialEq for SyncAddress { - fn eq(&self, other: &Self) -> bool { - self.ct_eq(other).into() - } -} - -impl From<&StealthAddress> for SyncAddress { - fn from(sa: &StealthAddress) -> Self { - SyncAddress { - k: *sa.note_pk().as_ref(), - R: *sa.R(), - } - } -} - -impl Serializable<64> for SyncAddress { - type Error = Error; - /// Encode the `SyncAddress` to an array of 64 bytes - fn to_bytes(&self) -> [u8; Self::SIZE] { - let mut bytes = [0u8; Self::SIZE]; - bytes[..32].copy_from_slice(&JubJubAffine::from(self.R).to_bytes()); - bytes[32..].copy_from_slice(&JubJubAffine::from(self.k()).to_bytes()); - bytes - } - - /// Decode the `SyncAddress` from an array of 64 bytes - fn from_bytes(bytes: &[u8; Self::SIZE]) -> Result { - let R = JubJubExtended::from(JubJubAffine::from_slice(&bytes[..32])?); - let note_pk = - JubJubExtended::from(JubJubAffine::from_slice(&bytes[32..])?); - let k = NotePublicKey::from_raw_unchecked(note_pk); - - Ok(SyncAddress { R, k: *k.as_ref() }) - } -} diff --git a/core/src/keys/public.rs b/core/src/keys/public.rs index 8a438b7..ad0f19f 100644 --- a/core/src/keys/public.rs +++ b/core/src/keys/public.rs @@ -4,7 +4,7 @@ // // Copyright (c) DUSK NETWORK. All rights reserved. -use crate::{keys::hash, SecretKey, StealthAddress, SyncAddress, ViewKey}; +use crate::{keys::hash, SecretKey, StealthAddress, ViewKey}; use dusk_jubjub::{JubJubAffine, JubJubExtended, JubJubScalar}; @@ -58,14 +58,6 @@ impl PublicKey { StealthAddress { R, note_pk } } - - /// Generates new sync address from a given 'r' - pub fn gen_sync_address(&self, r: &JubJubScalar) -> SyncAddress { - let R = GENERATOR_EXTENDED * r; - let k = self.A * r; - - SyncAddress { R, k } - } } impl ConstantTimeEq for PublicKey { diff --git a/core/src/keys/secret.rs b/core/src/keys/secret.rs index 332cd76..94ee8a0 100644 --- a/core/src/keys/secret.rs +++ b/core/src/keys/secret.rs @@ -81,31 +81,23 @@ impl SecretKey { /// Generates a [`NoteSecretKey`] using the `R` of the given /// [`StealthAddress`]. With the formula: `note_sk = H(a · R) + b` - pub fn gen_note_sk(&self, sa: &StealthAddress) -> NoteSecretKey { - let aR = sa.R() * self.a; + pub fn gen_note_sk(&self, stealth: &StealthAddress) -> NoteSecretKey { + let aR = stealth.R() * self.a; NoteSecretKey::from(hash(&aR) + self.b) } /// Checks if `note_pk ?= (H(R · a) + b) · G` pub fn owns(&self, note: &Note) -> bool { - let sa = note.stealth_address(); + let stealth = note.stealth_address(); - let aR = sa.R() * self.a(); + let aR = stealth.R() * self.a(); let hash_aR = hash(&aR); let note_sk = hash_aR + self.b(); let note_pk = GENERATOR_EXTENDED * note_sk; - sa.note_pk().as_ref() == ¬e_pk - } - - /// Checks if `k_sync ?= R_sync · a` - pub fn owns_unchecked(&self, note: &Note) -> bool { - let sa = note.sync_address(); - let aR = sa.R() * self.a(); - - sa.k() == &aR + stealth.note_pk().as_ref() == ¬e_pk } } diff --git a/core/src/keys/view.rs b/core/src/keys/view.rs index 171c98b..227c8fe 100644 --- a/core/src/keys/view.rs +++ b/core/src/keys/view.rs @@ -64,22 +64,14 @@ impl ViewKey { /// Checks `note_pk = H(R · a) · G + B` pub fn owns(&self, note: &Note) -> bool { - let sa = note.stealth_address(); + let stealth = note.stealth_address(); - let aR = sa.R() * self.a(); + let aR = stealth.R() * self.a(); let hash_aR = hash(&aR); let hash_aR_G = GENERATOR_EXTENDED * hash_aR; let note_pk = hash_aR_G + self.B(); - sa.note_pk().as_ref() == ¬e_pk - } - - /// Checks `k_sync ?= R_sync · a` - pub fn owns_unchecked(&self, note: &Note) -> bool { - let sa = note.sync_address(); - let aR = sa.R() * self.a(); - - sa.k() == &aR + stealth.note_pk().as_ref() == ¬e_pk } } diff --git a/core/src/lib.rs b/core/src/lib.rs index fe02181..bc0eb7b 100644 --- a/core/src/lib.rs +++ b/core/src/lib.rs @@ -10,11 +10,11 @@ #![deny(missing_docs)] #![no_std] -mod addresses; mod encryption; mod error; mod keys; mod note; +mod stealth_address; #[cfg(feature = "alloc")] mod transaction; @@ -22,8 +22,6 @@ mod transaction; /// The number of output notes in a transaction pub const OUTPUT_NOTES: usize = 2; -pub use addresses::stealth::StealthAddress; -pub use addresses::sync::SyncAddress; pub use encryption::{aes, elgamal}; pub use error::Error; pub use keys::hash; @@ -31,6 +29,7 @@ pub use keys::public::PublicKey; pub use keys::secret::SecretKey; pub use keys::view::ViewKey; pub use note::{Note, NoteType, VALUE_ENC_SIZE as NOTE_VAL_ENC_SIZE}; +pub use stealth_address::StealthAddress; #[cfg(feature = "alloc")] /// Transaction Skeleton used by the phoenix transaction model diff --git a/core/src/note.rs b/core/src/note.rs index 1b1f77f..dabe6c0 100644 --- a/core/src/note.rs +++ b/core/src/note.rs @@ -8,7 +8,7 @@ use core::convert::{TryFrom, TryInto}; use crate::{ encryption::elgamal, transparent_value_commitment, value_commitment, Error, - PublicKey, SecretKey, StealthAddress, SyncAddress, ViewKey, + PublicKey, SecretKey, StealthAddress, ViewKey, }; use dusk_bls12_381::BlsScalar; use dusk_bytes::{DeserializableSlice, Error as BytesError, Serializable}; @@ -77,7 +77,6 @@ pub struct Note { pub(crate) note_type: NoteType, pub(crate) value_commitment: JubJubAffine, pub(crate) stealth_address: StealthAddress, - pub(crate) sync_address: SyncAddress, pub(crate) pos: u64, pub(crate) value_enc: [u8; VALUE_ENC_SIZE], // the elgamal encryption of the sender_pk encrypted using the output_npk @@ -105,9 +104,6 @@ impl Note { let r = JubJubScalar::random(&mut *rng); let stealth_address = pk.gen_stealth_address(&r); - let r_sync = JubJubScalar::random(&mut *rng); - let sync_address = pk.gen_sync_address(&r_sync); - let value_commitment = value_commitment(value, value_blinder); // Output notes have undefined position, equals to u64's MAX value @@ -152,7 +148,6 @@ impl Note { note_type, value_commitment, stealth_address, - sync_address, pos, value_enc, sender_enc: [sender_enc_A, sender_enc_B], @@ -182,12 +177,11 @@ impl Note { /// Creates a new transparent note /// - /// This is equivalent to [`transparent`] but taking only a stealth address, - /// sync address, and a value. This is done to be able to generate a note + /// This is equivalent to [`transparent`] but taking only a stealth address + /// and a value. This is done to be able to generate a note /// directly for a stealth address, as opposed to a public key. pub fn transparent_stealth( stealth_address: StealthAddress, - sync_address: SyncAddress, value: u64, sender_enc: [(JubJubAffine, JubJubAffine); 2], ) -> Self { @@ -202,7 +196,6 @@ impl Note { note_type: NoteType::Transparent, value_commitment, stealth_address, - sync_address, pos, value_enc, sender_enc, @@ -238,7 +231,6 @@ impl Note { note_type: NoteType::Transparent, value_commitment: JubJubAffine::default(), stealth_address: StealthAddress::default(), - sync_address: SyncAddress::default(), pos: 0, value_enc: [0; VALUE_ENC_SIZE], sender_enc: [(JubJubAffine::default(), JubJubAffine::default()); 2], @@ -319,11 +311,6 @@ impl Note { &self.stealth_address } - /// Returns the sync address associated with the note. - pub const fn sync_address(&self) -> &SyncAddress { - &self.sync_address - } - /// Set the position of the note on the tree. /// This, naturally, won't reflect immediatelly on the data storage pub fn set_pos(&mut self, pos: u64) { @@ -379,7 +366,6 @@ impl Note { const SIZE: usize = 1 + JubJubAffine::SIZE + StealthAddress::SIZE - + SyncAddress::SIZE + u64::SIZE + VALUE_ENC_SIZE + 4 * JubJubAffine::SIZE; @@ -400,9 +386,6 @@ impl Serializable for Note { buf[start..start + StealthAddress::SIZE] .copy_from_slice(&self.stealth_address.to_bytes()); start += StealthAddress::SIZE; - buf[start..start + SyncAddress::SIZE] - .copy_from_slice(&self.sync_address.to_bytes()); - start += SyncAddress::SIZE; buf[start..start + u64::SIZE].copy_from_slice(&self.pos.to_le_bytes()); start += u64::SIZE; buf[start..start + VALUE_ENC_SIZE].copy_from_slice(&self.value_enc); @@ -431,7 +414,6 @@ impl Serializable for Note { let mut buf = &bytes[1..]; let value_commitment = JubJubAffine::from_reader(&mut buf)?; let stealth_address = StealthAddress::from_reader(&mut buf)?; - let sync_address = SyncAddress::from_reader(&mut buf)?; let pos = u64::from_reader(&mut buf)?; let mut value_enc = [0u8; VALUE_ENC_SIZE]; @@ -448,7 +430,6 @@ impl Serializable for Note { note_type, value_commitment, stealth_address, - sync_address, pos, value_enc, sender_enc: [ diff --git a/core/src/addresses/stealth.rs b/core/src/stealth_address.rs similarity index 93% rename from core/src/addresses/stealth.rs rename to core/src/stealth_address.rs index 53dca21..d6e5479 100644 --- a/core/src/addresses/stealth.rs +++ b/core/src/stealth_address.rs @@ -4,7 +4,6 @@ // // Copyright (c) DUSK NETWORK. All rights reserved. -use crate::SyncAddress; use dusk_jubjub::{JubJubAffine, JubJubExtended}; use jubjub_schnorr::PublicKey as NotePublicKey; @@ -71,15 +70,6 @@ impl PartialEq for StealthAddress { } } -impl From<&SyncAddress> for StealthAddress { - fn from(sa: &SyncAddress) -> Self { - StealthAddress { - note_pk: NotePublicKey::from(sa.k()), - R: *sa.R(), - } - } -} - impl Serializable<64> for StealthAddress { type Error = Error; /// Encode the `StealthAddress` to an array of 64 bytes diff --git a/core/tests/keys.rs b/core/tests/keys.rs index 8c6ef99..593906e 100644 --- a/core/tests/keys.rs +++ b/core/tests/keys.rs @@ -73,9 +73,7 @@ fn keys_consistency() { let note = Note::transparent(&mut rng, &pk, NOTE_VALUE, sender_blinder); assert!(vk.owns(¬e)); - assert!(vk.owns_unchecked(¬e)); assert!(sk.owns(¬e)); - assert!(sk.owns_unchecked(¬e)); let wrong_sk = SecretKey::random(&mut rng); let wrong_vk = ViewKey::from(&wrong_sk); @@ -84,9 +82,7 @@ fn keys_consistency() { assert_ne!(vk, wrong_vk); assert!(!wrong_vk.owns(¬e)); - assert!(!wrong_vk.owns_unchecked(¬e)); assert!(!wrong_sk.owns(¬e)); - assert!(!wrong_sk.owns_unchecked(¬e)); let sa = pk.gen_stealth_address(&r); diff --git a/core/tests/note_test.rs b/core/tests/note_test.rs index e0f05e3..c32dd78 100644 --- a/core/tests/note_test.rs +++ b/core/tests/note_test.rs @@ -44,9 +44,6 @@ fn transparent_stealth_note() -> Result<(), Error> { let r = JubJubScalar::random(&mut rng); let stealth = pk.gen_stealth_address(&r); - let r = JubJubScalar::random(&mut rng); - let sync_address = pk.gen_sync_address(&r); - let value = 25; let sender_blinder = [ @@ -69,12 +66,8 @@ fn transparent_stealth_note() -> Result<(), Error> { let sender_enc_b: (JubJubAffine, JubJubAffine) = (sender_enc_b.0.into(), sender_enc_b.1.into()); - let note = Note::transparent_stealth( - stealth, - sync_address, - value, - [sender_enc_a, sender_enc_b], - ); + let note = + Note::transparent_stealth(stealth, value, [sender_enc_a, sender_enc_b]); assert_eq!(note.note_type(), NoteType::Transparent); assert_eq!(value, note.value(None)?); @@ -224,7 +217,4 @@ fn note_keys_consistency() { assert!(!wrong_vk.owns(¬e)); assert!(vk.owns(¬e)); - - assert!(!wrong_vk.owns_unchecked(¬e)); - assert!(vk.owns_unchecked(¬e)); }