Skip to content

Commit f8cd7a1

Browse files
committed
Rework scalar de-serialization
1 parent 142714c commit f8cd7a1

File tree

8 files changed

+27
-41
lines changed

8 files changed

+27
-41
lines changed

src/error.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,8 @@ pub enum Error {
3434
ProofVerificationError,
3535
/// Encountered insufficient bytes when attempting to deserialize
3636
SizeError,
37-
/// Encountered a zero scalar
38-
ZeroScalarError,
37+
/// Encountered an invalid scalar
38+
ScalarError,
3939
}
4040

4141
#[cfg(feature = "std")]

src/group/mod.rs

Lines changed: 2 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -78,23 +78,9 @@ pub trait Group {
7878
where
7979
<D as Add<U1>>::Output: ArrayLength<u8>;
8080

81-
/// Return a scalar from its fixed-length bytes representation, without
82-
/// checking if the scalar is zero.
83-
fn from_scalar_slice_unchecked(
84-
scalar_bits: &GenericArray<u8, Self::ScalarLen>,
85-
) -> Result<Self::Scalar>;
86-
8781
/// Return a scalar from its fixed-length bytes representation. If the
88-
/// scalar is zero, then return an error.
89-
fn from_scalar_slice<'a>(
90-
scalar_bits: impl Into<&'a GenericArray<u8, Self::ScalarLen>>,
91-
) -> Result<Self::Scalar> {
92-
let scalar = Self::from_scalar_slice_unchecked(scalar_bits.into())?;
93-
if scalar.ct_eq(&Self::scalar_zero()).into() {
94-
return Err(Error::ZeroScalarError);
95-
}
96-
Ok(scalar)
97-
}
82+
/// scalar is zero or invalid, then return an error.
83+
fn deserialize_scalar(scalar_bits: &GenericArray<u8, Self::ScalarLen>) -> Result<Self::Scalar>;
9884

9985
/// picks a scalar at random
10086
fn random_nonzero_scalar<R: RngCore + CryptoRng>(rng: &mut R) -> Self::Scalar;

src/group/p256.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ use p256_::elliptic_curve::group::GroupEncoding;
2929
use p256_::elliptic_curve::ops::Reduce;
3030
use p256_::elliptic_curve::sec1::{FromEncodedPoint, ToEncodedPoint};
3131
use p256_::elliptic_curve::Field;
32-
use p256_::{AffinePoint, EncodedPoint, NistP256, ProjectivePoint, Scalar};
32+
use p256_::{AffinePoint, EncodedPoint, NistP256, ProjectivePoint, Scalar, SecretKey};
3333
use rand_core::{CryptoRng, RngCore};
3434
use subtle::{Choice, ConditionallySelectable};
3535

@@ -144,10 +144,10 @@ impl Group for NistP256 {
144144
Ok(Scalar::from_be_bytes_reduced(result))
145145
}
146146

147-
fn from_scalar_slice_unchecked(
148-
scalar_bits: &GenericArray<u8, Self::ScalarLen>,
149-
) -> Result<Self::Scalar> {
150-
Ok(Scalar::from_be_bytes_reduced(*scalar_bits))
147+
fn deserialize_scalar(scalar_bits: &GenericArray<u8, Self::ScalarLen>) -> Result<Self::Scalar> {
148+
SecretKey::from_be_bytes(scalar_bits)
149+
.map(|secret_key| *secret_key.to_nonzero_scalar())
150+
.map_err(|_| Error::ScalarError)
151151
}
152152

153153
fn random_nonzero_scalar<R: RngCore + CryptoRng>(rng: &mut R) -> Self::Scalar {

src/group/ristretto.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -78,10 +78,10 @@ impl Group for Ristretto255 {
7878
))
7979
}
8080

81-
fn from_scalar_slice_unchecked(
82-
scalar_bits: &GenericArray<u8, Self::ScalarLen>,
83-
) -> Result<Self::Scalar> {
84-
Ok(Scalar::from_bytes_mod_order(*scalar_bits.as_ref()))
81+
fn deserialize_scalar(scalar_bits: &GenericArray<u8, Self::ScalarLen>) -> Result<Self::Scalar> {
82+
Scalar::from_canonical_bytes((*scalar_bits).into())
83+
.filter(|scalar| scalar != &Scalar::zero())
84+
.ok_or(Error::ScalarError)
8585
}
8686

8787
fn random_nonzero_scalar<R: RngCore + CryptoRng>(rng: &mut R) -> Self::Scalar {

src/group/tests.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,8 +45,8 @@ fn test_identity_element_error<G: Group>() -> Result<()> {
4545
// Checks that the zero scalar cannot be deserialized
4646
fn test_zero_scalar_error<G: Group>() -> Result<()> {
4747
let zero_scalar = G::scalar_zero();
48-
let result = G::from_scalar_slice(&G::scalar_as_bytes(zero_scalar));
49-
assert!(matches!(result, Err(Error::ZeroScalarError)));
48+
let result = G::deserialize_scalar(&G::scalar_as_bytes(zero_scalar));
49+
assert!(matches!(result, Err(Error::ScalarError)));
5050

5151
Ok(())
5252
}

src/serialization.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> NonVerifiableClient
3737
pub fn deserialize(input: &[u8]) -> Result<Self> {
3838
let mut input = input.iter().copied();
3939

40-
let blind = G::from_scalar_slice(&deserialize(&mut input)?)?;
40+
let blind = G::deserialize_scalar(&deserialize(&mut input)?)?;
4141

4242
Ok(Self {
4343
blind,
@@ -60,7 +60,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> VerifiableClient<G,
6060
pub fn deserialize(input: &[u8]) -> Result<Self> {
6161
let mut input = input.iter().copied();
6262

63-
let blind = G::from_scalar_slice(&deserialize(&mut input)?)?;
63+
let blind = G::deserialize_scalar(&deserialize(&mut input)?)?;
6464
let blinded_element = G::from_element_slice(&deserialize(&mut input)?)?;
6565

6666
Ok(Self {
@@ -81,7 +81,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> NonVerifiableServer
8181
pub fn deserialize(input: &[u8]) -> Result<Self> {
8282
let mut input = input.iter().copied();
8383

84-
let sk = G::from_scalar_slice(&deserialize(&mut input)?)?;
84+
let sk = G::deserialize_scalar(&deserialize(&mut input)?)?;
8585

8686
Ok(Self {
8787
sk,
@@ -104,7 +104,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> VerifiableServer<G,
104104
pub fn deserialize(input: &[u8]) -> Result<Self> {
105105
let mut input = input.iter().copied();
106106

107-
let sk = G::from_scalar_slice(&deserialize(&mut input)?)?;
107+
let sk = G::deserialize_scalar(&deserialize(&mut input)?)?;
108108
let pk = G::from_element_slice(&deserialize(&mut input)?)?;
109109

110110
Ok(Self {
@@ -129,8 +129,8 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> Proof<G, H> {
129129
pub fn deserialize(input: &[u8]) -> Result<Self> {
130130
let mut input = input.iter().copied();
131131

132-
let c_scalar = G::from_scalar_slice(&deserialize(&mut input)?)?;
133-
let s_scalar = G::from_scalar_slice(&deserialize(&mut input)?)?;
132+
let c_scalar = G::deserialize_scalar(&deserialize(&mut input)?)?;
133+
let s_scalar = G::deserialize_scalar(&deserialize(&mut input)?)?;
134134

135135
Ok(Proof {
136136
c_scalar,

src/tests/voprf_test_vectors.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -184,7 +184,7 @@ fn test_base_blind<G: Group, H: BlockSizeUser + Digest + FixedOutputReset>(
184184
for parameters in tvs {
185185
for i in 0..parameters.input.len() {
186186
let blind =
187-
G::from_scalar_slice(&GenericArray::clone_from_slice(&parameters.blind[i]))?;
187+
G::deserialize_scalar(&GenericArray::clone_from_slice(&parameters.blind[i]))?;
188188
let client_result = NonVerifiableClient::<G, H>::deterministic_blind_unchecked(
189189
&parameters.input[i],
190190
blind,
@@ -210,7 +210,7 @@ fn test_verifiable_blind<G: Group, H: BlockSizeUser + Digest + FixedOutputReset>
210210
for parameters in tvs {
211211
for i in 0..parameters.input.len() {
212212
let blind =
213-
G::from_scalar_slice(&GenericArray::clone_from_slice(&parameters.blind[i]))?;
213+
G::deserialize_scalar(&GenericArray::clone_from_slice(&parameters.blind[i]))?;
214214
let client_blind_result = VerifiableClient::<G, H>::deterministic_blind_unchecked(
215215
&parameters.input[i],
216216
blind,
@@ -299,7 +299,7 @@ fn test_base_finalize<G: Group, H: BlockSizeUser + Digest + FixedOutputReset>(
299299
) -> Result<()> {
300300
for parameters in tvs {
301301
for i in 0..parameters.input.len() {
302-
let client = NonVerifiableClient::<G, H>::from_blind(G::from_scalar_slice(
302+
let client = NonVerifiableClient::<G, H>::from_blind(G::deserialize_scalar(
303303
&GenericArray::clone_from_slice(&parameters.blind[i]),
304304
)?);
305305

@@ -322,7 +322,7 @@ fn test_verifiable_finalize<G: Group, H: BlockSizeUser + Digest + FixedOutputRes
322322
let mut clients = vec![];
323323
for i in 0..parameters.input.len() {
324324
let client = VerifiableClient::<G, H>::from_blind_and_element(
325-
G::from_scalar_slice(&GenericArray::clone_from_slice(&parameters.blind[i]))?,
325+
G::deserialize_scalar(&GenericArray::clone_from_slice(&parameters.blind[i]))?,
326326
G::from_element_slice(&GenericArray::clone_from_slice(
327327
&parameters.blinded_element[i],
328328
))?,

src/voprf.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -414,7 +414,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> NonVerifiableServer
414414
/// Produces a new instance of a [NonVerifiableServer] using a supplied set
415415
/// of bytes to represent the server's private key
416416
pub fn new_with_key(private_key_bytes: &[u8]) -> Result<Self> {
417-
let sk = G::from_scalar_slice(private_key_bytes)?;
417+
let sk = G::deserialize_scalar(private_key_bytes.into())?;
418418
Ok(Self {
419419
sk,
420420
hash: PhantomData,
@@ -480,7 +480,7 @@ impl<G: Group, H: BlockSizeUser + Digest + FixedOutputReset> VerifiableServer<G,
480480
/// Produces a new instance of a [VerifiableServer] using a supplied set of
481481
/// bytes to represent the server's private key
482482
pub fn new_with_key(key: &[u8]) -> Result<Self> {
483-
let sk = G::from_scalar_slice(key)?;
483+
let sk = G::deserialize_scalar(key.into())?;
484484
let pk = G::base_point() * &sk;
485485
Ok(Self {
486486
sk,

0 commit comments

Comments
 (0)