Skip to content

Commit

Permalink
adding some of Martins suggestions
Browse files Browse the repository at this point in the history
  • Loading branch information
Daniel Masny committed Oct 9, 2023
1 parent fe3f130 commit 159cd2c
Show file tree
Hide file tree
Showing 4 changed files with 217 additions and 233 deletions.
159 changes: 72 additions & 87 deletions src/ff/curve_points.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,16 @@
use curve25519_dalek::{
constants,
ristretto::{CompressedRistretto, RistrettoPoint},
Scalar,
};
use generic_array::GenericArray;
use curve25519_dalek::{ristretto::{CompressedRistretto, RistrettoPoint},constants, Scalar};
use typenum::U32;
use sha2::Sha256;
use hkdf::Hkdf;


use sha2::Sha256;
use typenum::U32;

use crate::{
error::Error,
ff::{Serializable,ec_prime_field::Fp25519,Field},
ff::{ec_prime_field::Fp25519, Field, Serializable},
secret_sharing::{Block, SharedValue},
};

Expand All @@ -31,7 +33,7 @@ impl Serializable for RP25519 {
type Size = <<RP25519 as SharedValue>::Storage as Block>::Size;

fn serialize(&self, buf: &mut GenericArray<u8, Self::Size>) {
let raw = &self.0.as_bytes()[..buf.len()] ;
let raw = &self.0.as_bytes()[..buf.len()];
buf.copy_from_slice(raw);
}

Expand All @@ -40,7 +42,6 @@ impl Serializable for RP25519 {
}
}


impl rand::distributions::Distribution<RP25519> for rand::distributions::Standard {
fn sample<R: crate::rand::Rng + ?Sized>(&self, rng: &mut R) -> RP25519 {
//Fp25519(Scalar::random(rng: &mut R))
Expand All @@ -50,62 +51,59 @@ impl rand::distributions::Distribution<RP25519> for rand::distributions::Standar
}
}


impl std::ops::Add for RP25519 {
type Output = Self;
type Output = Self;

fn add(self, rhs: Self) -> Self::Output {
Self((self.0.decompress().unwrap()+rhs.0.decompress().unwrap()).compress())
}
fn add(self, rhs: Self) -> Self::Output {
Self((self.0.decompress().unwrap() + rhs.0.decompress().unwrap()).compress())
}
}

impl std::ops::AddAssign for RP25519 {
#[allow(clippy::assign_op_pattern)]
fn add_assign(&mut self, rhs: Self) {
*self = *self + rhs;
}
#[allow(clippy::assign_op_pattern)]
fn add_assign(&mut self, rhs: Self) {
*self = *self + rhs;
}
}

impl std::ops::Neg for RP25519 {
type Output = Self;
type Output = Self;

fn neg(self) -> Self::Output {
Self(self.0.decompress().unwrap().neg().compress())
}
fn neg(self) -> Self::Output {
Self(self.0.decompress().unwrap().neg().compress())
}
}

impl std::ops::Sub for RP25519 {
type Output = Self;
type Output = Self;

fn sub(self, rhs: Self) -> Self::Output {
Self((self.0.decompress().unwrap()-rhs.0.decompress().unwrap()).compress())
}
fn sub(self, rhs: Self) -> Self::Output {
Self((self.0.decompress().unwrap() - rhs.0.decompress().unwrap()).compress())
}
}

impl std::ops::SubAssign for RP25519 {
#[allow(clippy::assign_op_pattern)]
fn sub_assign(&mut self, rhs: Self) {
*self = *self - rhs;
}
#[allow(clippy::assign_op_pattern)]
fn sub_assign(&mut self, rhs: Self) {
*self = *self - rhs;
}
}


///Scalar Multiplication
///<'a, 'b> `std::ops::Mul<&'b"` Fp25519 for &'a
impl RP25519 {
pub const ONE: Self = Self(constants::RISTRETTO_BASEPOINT_COMPRESSED);

/// # Errors
/// Propagates errors from decompressing invalid curve point
pub fn s_mul(self, rhs: Fp25519) -> Result<RP25519,Error> {
self.0.decompress().map_or(
Err(Error::DecompressingInvalidCurvePoint),
|x| Ok((x * Scalar::from(rhs)).compress().into())
)
}
pub fn s_mul(self, rhs: Fp25519) -> Result<RP25519, Error> {
self.0
.decompress()
.map_or(Err(Error::DecompressingInvalidCurvePoint), |x| {
Ok((x * Scalar::from(rhs)).compress().into())
})
}
}


///do not use
impl std::ops::Mul for RP25519 {
type Output = Self;
Expand All @@ -117,8 +115,7 @@ impl std::ops::Mul for RP25519 {

///do not use
impl std::ops::MulAssign for RP25519 {

fn mul_assign(& mut self, _rhs: RP25519) {
fn mul_assign(&mut self, _rhs: RP25519) {
panic!("Two curve points cannot be multiplied! Do not use *, *= for RP25519 or secret shares of RP25519");
}
}
Expand Down Expand Up @@ -159,7 +156,7 @@ macro_rules! cp_hash_impl {
}
}

impl From<$u_type> for RP25519 {
impl From<$u_type> for RP25519 {
fn from(s: $u_type) -> Self {
let hk = Hkdf::<Sha256>::new(None, &s.to_le_bytes());
let mut okm = [0u8; 32];
Expand All @@ -168,23 +165,17 @@ macro_rules! cp_hash_impl {
RP25519::deserialize(&okm.into())
}
}
}
};
}

cp_hash_impl!(
u64,
8
);
cp_hash_impl!(u64, 8);

cp_hash_impl!(
u32,
4
);
cp_hash_impl!(u32, 4);

/// Daniel had to implement this since Reveal wants it, prefer not to, I dont understand why it is
/// actually needed there, maybe to upgrade it to malicious? but it still shouldn't be needed
impl Field for RP25519 {
const ONE: RP25519= RP25519::ONE;
const ONE: RP25519 = Self(constants::RISTRETTO_BASEPOINT_COMPRESSED);

///both following methods are based on hashing and do not allow to actually convert elements in Fp25519
/// from or into u128. However it is sufficient to generate random elements in Fp25519
Expand All @@ -204,7 +195,6 @@ impl Field for RP25519 {
hk.expand(&[], &mut okm).unwrap();
RP25519::deserialize(&okm.into())
}

}

impl TryFrom<u128> for RP25519 {
Expand All @@ -213,75 +203,70 @@ impl TryFrom<u128> for RP25519 {
fn try_from(v: u128) -> Result<Self, Self::Error> {
let mut bits = [0u8; 32];
bits[..].copy_from_slice(&v.to_le_bytes());
let f: RP25519=RP25519::ONE;
let f: RP25519 = RP25519::ONE;
f.serialize((&mut bits).into());
Ok(f)
}
}




#[cfg(all(test, unit_test))]
mod test {
use generic_array::GenericArray;
use crate::ff::curve_points::RP25519;
use crate::ff::Serializable;
use typenum::U32;
use curve25519_dalek::scalar::Scalar;
use generic_array::GenericArray;
use rand::{thread_rng, Rng};
use crate::ff::ec_prime_field::Fp25519;
use crate::secret_sharing::SharedValue;
use typenum::U32;

use crate::{
ff::{curve_points::RP25519, ec_prime_field::Fp25519, Serializable, field::Field},
};

#[test]
fn serde_25519() {
let input:[u8;32] = [
0x01, 0xff,0x00, 0xff,0x00, 0xff,0x00, 0xff,
0x00, 0xff,0x00, 0xff,0x00, 0xff,0x00, 0xff,
0x00, 0xff,0x00, 0xff,0x00, 0xff,0x00, 0xff,
0x00, 0xff,0x00, 0xff,0x00, 0x00,0x00, 0x00
let input: [u8; 32] = [
0x01, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff,
0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff, 0x00, 0xff,
0x00, 0x00, 0x00, 0x00,
];
let mut output: GenericArray<u8,U32> = [0u8;32].into();
let mut output: GenericArray<u8, U32> = [0u8; 32].into();
let a = RP25519::deserialize(&input.into());
assert_eq!(a.0.as_bytes()[..32],input);
assert_eq!(a.0.as_bytes()[..32], input);
a.serialize(&mut output);
assert_eq!(a.0.as_bytes()[..32],output.as_slice()[..32]);
assert_eq!(input,output.as_slice()[..32]);
assert_eq!(a.0.as_bytes()[..32], output.as_slice()[..32]);
assert_eq!(input, output.as_slice()[..32]);
}

#[test]
fn scalar_to_point() {
let a = Scalar::ONE;
let b : RP25519 = a.into();
let d : Fp25519 = a.into();
let c : RP25519 = RP25519::from(d);
assert_eq!(b,RP25519::ZERO);
assert_eq!(c,RP25519::ZERO);
let b: RP25519 = a.into();
let d: Fp25519 = a.into();
let c: RP25519 = RP25519::from(d);
assert_eq!(b, RP25519::ONE);
assert_eq!(c, RP25519::ONE);
}

#[test]
fn curve_arithmetics() {
let mut rng = thread_rng();
let fp_a = rng.gen::<Fp25519>();
let fp_b = rng.gen::<Fp25519>();
let fp_c = fp_a+fp_b;
let fp_d = RP25519::from(fp_a)+RP25519::from(fp_b);
let fp_c = fp_a + fp_b;
let fp_d = RP25519::from(fp_a) + RP25519::from(fp_b);
assert_eq!(fp_d, RP25519::from(fp_c));
assert_ne!(fp_d, RP25519::ZERO);
assert_ne!(fp_d, RP25519::ONE);
let fp_e = rng.gen::<Fp25519>();
let fp_f=rng.gen::<Fp25519>();
let fp_g =fp_e*fp_f;
let fp_f = rng.gen::<Fp25519>();
let fp_g = fp_e * fp_f;
let fp_h = RP25519::from(fp_e).s_mul(fp_f).unwrap();
assert_eq!(fp_h,RP25519::from(fp_g));
assert_ne!(fp_h, RP25519::ZERO);
assert_eq!(fp_h, RP25519::from(fp_g));
assert_ne!(fp_h, RP25519::ONE);
}

#[test]
fn curve_point_to_hash() {
let mut rng = thread_rng();
let fp_a = rng.gen::<RP25519>();
assert_ne!(0u64,u64::from(fp_a));
assert_ne!(0u32,u32::from(fp_a));
assert_ne!(0u64, u64::from(fp_a));
assert_ne!(0u32, u32::from(fp_a));
}

}
}
Loading

0 comments on commit 159cd2c

Please sign in to comment.