1use crate::error::{FastCryptoError, FastCryptoResult};
5use crate::traits::AllowedRng;
6use core::ops::{Add, Div, Mul, Neg, Sub};
7use serde::de::DeserializeOwned;
8use serde::Serialize;
9use std::fmt::Debug;
10use std::ops::{AddAssign, SubAssign};
11
12pub mod ristretto255;
13pub trait GroupElement:
19 Copy
20 + Clone
21 + Debug
22 + Eq
23 + Add<Output = Self>
24 + AddAssign
25 + for<'a> Add<&'a Self, Output = Self>
26 + Sub<Output = Self>
27 + SubAssign
28 + for<'a> Sub<&'a Self, Output = Self>
29 + Neg<Output = Self>
30 + Mul<Self::ScalarType, Output = Self>
31 + Div<Self::ScalarType, Output = Result<Self, FastCryptoError>>
32 + for<'a> Mul<&'a Self::ScalarType, Output = Self>
33 + Sized
34{
35 type ScalarType: Scalar;
37
38 fn zero() -> Self;
40
41 fn generator() -> Self;
43}
44
45pub trait Scalar:
49 GroupElement<ScalarType = Self> + Copy + From<u128> + Sized + Debug + Serialize + DeserializeOwned
50{
51 fn rand<R: AllowedRng>(rng: &mut R) -> Self;
52 fn inverse(&self) -> FastCryptoResult<Self>;
53}
54
55pub trait Doubling: Clone {
57 fn double(self) -> Self;
59
60 fn repeated_doubling(self, repetitions: u64) -> Self {
62 (0..repetitions).fold(self, |acc, _| acc.double())
63 }
64}
65
66pub trait Pairing: GroupElement {
67 type Other: GroupElement<ScalarType = Self::ScalarType>;
68 type Output;
69
70 fn pairing(&self, other: &Self::Other) -> <Self as Pairing>::Output;
71
72 fn multi_pairing(
74 points_g1: &[Self],
75 points_g2: &[Self::Other],
76 ) -> FastCryptoResult<<Self as Pairing>::Output>
77 where
78 <Self as Pairing>::Output: GroupElement,
79 {
80 if points_g1.len() != points_g2.len() {
81 return Err(FastCryptoError::InvalidInput);
82 }
83 if points_g1.is_empty() {
84 return Ok(<Self as Pairing>::Output::zero());
85 }
86 Ok(points_g1
87 .iter()
88 .skip(1)
89 .zip(points_g2.iter().skip(1))
90 .map(|(g1, g2)| g1.pairing(g2))
91 .fold(
92 points_g1[0].pairing(&points_g2[0]),
93 <Self as Pairing>::Output::add,
94 ))
95 }
96}
97
98pub trait FiatShamirChallenge {
102 fn fiat_shamir_reduction_to_group_element(uniform_buffer: &[u8]) -> Self;
103}
104
105pub trait HashToGroupElement {
108 fn hash_to_group_element(msg: &[u8]) -> Self;
110}
111
112pub trait MultiScalarMul: GroupElement {
114 fn multi_scalar_mul(scalars: &[Self::ScalarType], points: &[Self]) -> FastCryptoResult<Self>;
115}
116
117pub trait FromTrustedByteArray<const LENGTH: usize>: Sized {
119 fn from_trusted_byte_array(bytes: &[u8; LENGTH]) -> FastCryptoResult<Self>;
120}