diff --git a/Cargo.lock b/Cargo.lock index 4ed3298..be9cc17 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -737,6 +737,7 @@ dependencies = [ "group", "k256", "p256", + "p384", "rand", "rand_core", "rand_dev", @@ -1086,6 +1087,16 @@ dependencies = [ "primeorder", ] +[[package]] +name = "p384" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fe42f1670a52a47d448f14b6a5c61dd78fce51856e68edaa38f7ae3a46b8d6b6" +dependencies = [ + "elliptic-curve", + "primeorder", +] + [[package]] name = "papergrid" version = "0.11.0" diff --git a/README.md b/README.md index 6d56dd8..42bf3e4 100644 --- a/README.md +++ b/README.md @@ -73,11 +73,13 @@ Crate provides support for following elliptic curves out of box: |--------------|--------------------|-------------------| | secp256k1 | `curve-secp256k1` | [RustCrypto/k256] | | secp256r1 | `curve-secp256r1` | [RustCrypto/p256] | +| secp384r1 | `curve-secp384r1` | [RustCrypto/p384] | | stark-curve | `curve-stark` | [Dfns/stark] | | Ed25519 | `curve-ed25519` | [curve25519-dalek]| [RustCrypto/k256]: https://github.com/RustCrypto/elliptic-curves/tree/master/k256 [RustCrypto/p256]: https://github.com/RustCrypto/elliptic-curves/tree/master/p256 +[RustCrypto/p384]: https://github.com/RustCrypto/elliptic-curves/tree/master/p384 [Dfns/stark]: https://github.com/LFDT-Lockness/stark-curve/ [curve25519-dalek]: https://docs.rs/curve25519-dalek/ diff --git a/generic-ec-curves/Cargo.toml b/generic-ec-curves/Cargo.toml index b3b1c1a..f6f1160 100644 --- a/generic-ec-curves/Cargo.toml +++ b/generic-ec-curves/Cargo.toml @@ -18,6 +18,7 @@ zeroize = { workspace = true, features = ["zeroize_derive"] } elliptic-curve = { version = "0.13", default-features = false, features = ["sec1", "hash2curve"], optional = true } k256 = { version = "0.13", optional = true, default-features = false, features = ["hash2curve"] } p256 = { version = "0.13", optional = true, default-features = false, features = ["hash2curve"] } +p384 = { version = "0.13", optional = true, default-features = false, features = ["hash2curve"] } sha2 = { workspace = true, optional = true } stark-curve = { version = "0.1", default-features = false, optional = true } @@ -39,6 +40,7 @@ default = [] rust-crypto = ["elliptic-curve"] secp256k1 = ["rust-crypto", "k256", "sha2"] secp256r1 = ["rust-crypto", "p256", "sha2"] +secp384r1 = ["rust-crypto", "p384", "sha2"] stark = ["rust-crypto", "stark-curve", "sha2"] ed25519 = ["dep:curve25519", "dep:group"] diff --git a/generic-ec-curves/benches/curves.rs b/generic-ec-curves/benches/curves.rs index 2deb569..9647d26 100644 --- a/generic-ec-curves/benches/curves.rs +++ b/generic-ec-curves/benches/curves.rs @@ -14,6 +14,9 @@ fn bench_curves(c: &mut criterion::Criterion) { bench_curve::(c, &mut rng, "secp256r1"); bench_bytes_reduction::(c, &mut rng, "secp256r1"); + bench_curve::(c, &mut rng, "secp384r1"); + bench_bytes_reduction::(c, &mut rng, "secp384r1"); + bench_curve::(c, &mut rng, "stark"); bench_bytes_reduction::(c, &mut rng, "stark"); diff --git a/generic-ec-curves/src/lib.rs b/generic-ec-curves/src/lib.rs index e8beb40..9b64a91 100644 --- a/generic-ec-curves/src/lib.rs +++ b/generic-ec-curves/src/lib.rs @@ -6,7 +6,7 @@ //! [`generic-ec` crate]: https://docs.rs/generic-ec #![cfg_attr(not(test), deny(clippy::unwrap_used, clippy::expect_used))] -#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))] +#![cfg_attr(docsrs, feature(doc_cfg))] #![forbid(missing_docs)] #![no_std] @@ -27,6 +27,9 @@ pub use rust_crypto::Secp256k1; #[cfg(feature = "secp256r1")] pub use rust_crypto::Secp256r1; +#[cfg(feature = "secp384r1")] +pub use rust_crypto::Secp384r1; + #[cfg(feature = "stark")] pub use rust_crypto::Stark; diff --git a/generic-ec-curves/src/rust_crypto/curve_name.rs b/generic-ec-curves/src/rust_crypto/curve_name.rs index 83bb2f8..4ce673a 100644 --- a/generic-ec-curves/src/rust_crypto/curve_name.rs +++ b/generic-ec-curves/src/rust_crypto/curve_name.rs @@ -14,6 +14,11 @@ impl CurveName for k256::Secp256k1 { const CURVE_NAME: &'static str = "secp256k1"; } +#[cfg(feature = "secp384r1")] +impl CurveName for p384::NistP384 { + const CURVE_NAME: &'static str = "secp384r1"; +} + #[cfg(feature = "stark")] impl CurveName for stark_curve::StarkCurve { const CURVE_NAME: &'static str = "stark"; diff --git a/generic-ec-curves/src/rust_crypto/mod.rs b/generic-ec-curves/src/rust_crypto/mod.rs index f371d98..1ee5e0b 100644 --- a/generic-ec-curves/src/rust_crypto/mod.rs +++ b/generic-ec-curves/src/rust_crypto/mod.rs @@ -67,6 +67,12 @@ pub type Secp256k1 = RustCryptoCurve>; #[cfg(feature = "secp256r1")] pub type Secp256r1 = RustCryptoCurve>; +/// secp384r1 curve (NIST P-384) +/// +/// Based on [p384] crate +#[cfg(feature = "secp384r1")] +pub type Secp384r1 = RustCryptoCurve>; + /// Stark curve /// /// Based on [stark_curve] crate @@ -175,6 +181,13 @@ unsafe impl NoInvalidPoints for Secp256r1 {} /// Safe because: /// - RustCrypto curves are always on curve: /// generic-ec-curves/src/rust_crypto/point.rs:60 +/// - p384 is prime order and so is always torsion-free: +/// +#[cfg(feature = "secp384r1")] +unsafe impl NoInvalidPoints for Secp384r1 {} +/// Safe because: +/// - RustCrypto curves are always on curve: +/// generic-ec-curves/src/rust_crypto/point.rs:60 /// - stark is prime order and so is always torsion-free: /// #[cfg(feature = "stark")] @@ -187,7 +200,7 @@ mod tests { Curve, }; - use super::{Secp256k1, Secp256r1, Stark}; + use super::{Secp256k1, Secp256r1, Secp384r1, Stark}; /// Asserts that `E` implements `Curve` fn _impls_curve() {} @@ -196,10 +209,12 @@ mod tests { fn _curves_impl_trait() { _impls_curve::(); _impls_curve::(); + _impls_curve::(); _impls_curve::(); _exposes_affine_coords::(); _exposes_affine_coords::(); + _exposes_affine_coords::(); _exposes_affine_coords::(); } } diff --git a/generic-ec-curves/src/rust_crypto/scalar.rs b/generic-ec-curves/src/rust_crypto/scalar.rs index 2d2ffdd..d15bcba 100644 --- a/generic-ec-curves/src/rust_crypto/scalar.rs +++ b/generic-ec-curves/src/rust_crypto/scalar.rs @@ -1,6 +1,6 @@ use core::ops::Mul; -use elliptic_curve::bigint::{ArrayEncoding, ByteArray, U256, U512}; +use elliptic_curve::bigint::{ArrayEncoding, ByteArray, U256, U384, U512}; use elliptic_curve::{Curve, CurveArithmetic, Field, Group, ScalarPrimitive}; use generic_ec_core::{ Additive, CurveGenerator, FromUniformBytes, IntegerEncoding, Invertible, Multiplicative, One, @@ -108,6 +108,17 @@ impl FromUniformBytes for RustCryptoScalar { BytesModOrder::from_be_bytes_mod_order(bytes) } } +#[cfg(feature = "secp384r1")] +impl FromUniformBytes for RustCryptoScalar { + /// 64 bytes + /// + /// `L = ceil((ceil(log2(q)) + k) / 8) = ceil((384 + 128) / 8) = 64` bytes are enough to + /// guarantee the uniform distribution + type Bytes = [u8; 64]; + fn from_uniform_bytes(bytes: &Self::Bytes) -> Self { + BytesModOrder::from_be_bytes_mod_order(bytes) + } +} #[cfg(feature = "stark")] impl FromUniformBytes for RustCryptoScalar { /// 48 bytes @@ -265,6 +276,22 @@ where } } +impl Reduce<48> for RustCryptoScalar +where + E::Scalar: elliptic_curve::ops::Reduce, +{ + fn from_be_array_mod_order(bytes: &[u8; 48]) -> Self { + Self(elliptic_curve::ops::Reduce::::reduce( + U384::from_be_byte_array((*bytes).into()), + )) + } + fn from_le_array_mod_order(bytes: &[u8; 48]) -> Self { + Self(elliptic_curve::ops::Reduce::::reduce( + U384::from_le_byte_array((*bytes).into()), + )) + } +} + /// Choice of algorithm for computing bytes mod curve order. Efficient algorithm /// is different for different curves. pub(super) trait BytesModOrder { @@ -284,22 +311,43 @@ impl BytesModOrder for RustCryptoScalar { #[cfg(feature = "secp256r1")] impl BytesModOrder for RustCryptoScalar { fn from_be_bytes_mod_order(bytes: &[u8]) -> Self { - crate::utils::scalar_from_be_bytes_mod_order_reducing_32(bytes, &Self(p256::Scalar::ONE)) + crate::utils::scalar_from_be_bytes_mod_order_reducing::<_, 32>( + bytes, + &Self(p256::Scalar::ONE), + ) } fn from_le_bytes_mod_order(bytes: &[u8]) -> Self { - crate::utils::scalar_from_le_bytes_mod_order_reducing_32(bytes, &Self(p256::Scalar::ONE)) + crate::utils::scalar_from_le_bytes_mod_order_reducing::<_, 32>( + bytes, + &Self(p256::Scalar::ONE), + ) + } +} +#[cfg(feature = "secp384r1")] +impl BytesModOrder for RustCryptoScalar { + fn from_be_bytes_mod_order(bytes: &[u8]) -> Self { + crate::utils::scalar_from_be_bytes_mod_order_reducing::<_, 48>( + bytes, + &Self(p384::Scalar::ONE), + ) + } + fn from_le_bytes_mod_order(bytes: &[u8]) -> Self { + crate::utils::scalar_from_le_bytes_mod_order_reducing::<_, 48>( + bytes, + &Self(p384::Scalar::ONE), + ) } } #[cfg(feature = "stark")] impl BytesModOrder for RustCryptoScalar { fn from_be_bytes_mod_order(bytes: &[u8]) -> Self { - crate::utils::scalar_from_be_bytes_mod_order_reducing_32( + crate::utils::scalar_from_be_bytes_mod_order_reducing::<_, 32>( bytes, &Self(stark_curve::Scalar::ONE), ) } fn from_le_bytes_mod_order(bytes: &[u8]) -> Self { - crate::utils::scalar_from_le_bytes_mod_order_reducing_32( + crate::utils::scalar_from_le_bytes_mod_order_reducing::<_, 32>( bytes, &Self(stark_curve::Scalar::ONE), ) diff --git a/generic-ec-curves/src/utils.rs b/generic-ec-curves/src/utils.rs index b621f90..15d56b1 100644 --- a/generic-ec-curves/src/utils.rs +++ b/generic-ec-curves/src/utils.rs @@ -133,108 +133,100 @@ where /// Interprets `bytes` as little-endian encoding of an integer, takes it modulo curve (prime) /// order and returns scalar `S` /// -/// Works with scalars for which only [`Reduce<32>`][Reduce] is defined. +/// Works with scalars for which [`Reduce`][Reduce] is defined. /// /// Takes: /// * Little-endian `bytes` representation of the integer /// * Scalar `one = 1` -pub fn scalar_from_le_bytes_mod_order_reducing_32(bytes: &[u8], one: &S) -> S +pub fn scalar_from_le_bytes_mod_order_reducing(bytes: &[u8], one: &S) -> S where S: Default + Copy, - S: Reduce<32>, + S: Reduce, S: generic_ec_core::Additive + generic_ec_core::Multiplicative, { let len = bytes.len(); - match len { - ..=31 => { - let mut padded = [0u8; 32]; - padded[..len].copy_from_slice(bytes); - S::from_le_array_mod_order(&padded) - } - 32 => { - #[allow(clippy::expect_used)] - let bytes: &[u8; 32] = bytes.try_into().expect("we checked that bytes len == 32"); - S::from_le_array_mod_order(bytes) - } - 33.. => { - let two_to_256 = S::add(&S::from_le_array_mod_order(&[0xff; 32]), one); + if len < N { + let mut padded = [0u8; N]; + padded[..len].copy_from_slice(bytes); + S::from_le_array_mod_order(&padded) + } else if len == N { + #[allow(clippy::expect_used)] + let bytes: &[u8; N] = bytes.try_into().expect("we checked that bytes len == N"); + S::from_le_array_mod_order(bytes) + } else { + let two_to_8n = S::add(&S::from_le_array_mod_order(&[0xff; N]), one); - let chunks = bytes.chunks_exact(32); - let remainder = if !chunks.remainder().is_empty() { - Some(scalar_from_le_bytes_mod_order_reducing_32::( - chunks.remainder(), - one, - )) - } else { - None - }; + let chunks = bytes.chunks_exact(N); + let remainder = if !chunks.remainder().is_empty() { + Some(scalar_from_le_bytes_mod_order_reducing::( + chunks.remainder(), + one, + )) + } else { + None + }; - let chunks = chunks.rev().map(|chunk| { - #[allow(clippy::expect_used)] - let chunk: &[u8; 32] = chunk.try_into().expect("wrong chunk size"); - S::from_le_array_mod_order(chunk) - }); + let chunks = chunks.rev().map(|chunk| { + #[allow(clippy::expect_used)] + let chunk: &[u8; N] = chunk.try_into().expect("wrong chunk size"); + S::from_le_array_mod_order(chunk) + }); - remainder - .into_iter() - .chain(chunks) - .reduce(|acc, int| S::add(&S::mul(&acc, &two_to_256), &int)) - .unwrap_or_default() - } + remainder + .into_iter() + .chain(chunks) + .reduce(|acc, int| S::add(&S::mul(&acc, &two_to_8n), &int)) + .unwrap_or_default() } } /// Interprets `bytes` as big-endian encoding of an integer, takes it modulo curve (prime) /// order and returns scalar `S` /// -/// Works with scalars for which only [`Reduce<32>`][Reduce] is defined. +/// Works with scalars for which [`Reduce`][Reduce] is defined. /// /// Takes: /// * Big-endian `bytes` representation of the integer /// * Scalar `one = 1` -pub fn scalar_from_be_bytes_mod_order_reducing_32(bytes: &[u8], one: &S) -> S +pub fn scalar_from_be_bytes_mod_order_reducing(bytes: &[u8], one: &S) -> S where S: Default + Copy, - S: Reduce<32>, + S: Reduce, S: generic_ec_core::Additive + generic_ec_core::Multiplicative, { let len = bytes.len(); - match len { - ..=31 => { - let mut padded = [0u8; 32]; - padded[32 - len..].copy_from_slice(bytes); - S::from_be_array_mod_order(&padded) - } - 32 => { - #[allow(clippy::expect_used)] - let bytes: &[u8; 32] = bytes.try_into().expect("we checked that bytes len == 32"); - S::from_be_array_mod_order(bytes) - } - 33.. => { - let two_to_256 = S::add(&S::from_be_array_mod_order(&[0xff; 32]), one); + if len < N { + let mut padded = [0u8; N]; + padded[N - len..].copy_from_slice(bytes); + S::from_be_array_mod_order(&padded) + } else if len == N { + #[allow(clippy::expect_used)] + let bytes: &[u8; N] = bytes.try_into().expect("we checked that bytes len == N"); + S::from_be_array_mod_order(bytes) + } else { + let two_to_8n = S::add(&S::from_be_array_mod_order(&[0xff; N]), one); - let chunks = bytes.rchunks_exact(32); - let remainder = if !chunks.remainder().is_empty() { - Some(scalar_from_be_bytes_mod_order_reducing_32::( - chunks.remainder(), - one, - )) - } else { - None - }; + let chunks = bytes.rchunks_exact(N); + let remainder = if !chunks.remainder().is_empty() { + Some(scalar_from_be_bytes_mod_order_reducing::( + chunks.remainder(), + one, + )) + } else { + None + }; - let chunks = chunks.rev().map(|chunk| { - #[allow(clippy::expect_used)] - let chunk: &[u8; 32] = chunk.try_into().expect("wrong chunk size"); - S::from_be_array_mod_order(chunk) - }); + let chunks = chunks.rev().map(|chunk| { + #[allow(clippy::expect_used)] + let chunk: &[u8; N] = chunk.try_into().expect("wrong chunk size"); + S::from_be_array_mod_order(chunk) + }); - remainder - .into_iter() - .chain(chunks) - .reduce(|acc, int| S::add(&S::mul(&acc, &two_to_256), &int)) - .unwrap_or_default() - } + remainder + .into_iter() + .chain(chunks) + .reduce(|acc, int| S::add(&S::mul(&acc, &two_to_8n), &int)) + .unwrap_or_default() } } @@ -255,7 +247,7 @@ mod tests { ); assert_eq!( expected, - super::scalar_from_be_bytes_mod_order_reducing_32(&x.to_be_bytes(), one).0 + super::scalar_from_be_bytes_mod_order_reducing::<_, 32>(&x.to_be_bytes(), one).0 ); assert_eq!( @@ -264,7 +256,7 @@ mod tests { ); assert_eq!( expected, - super::scalar_from_le_bytes_mod_order_reducing_32(&x.to_le_bytes(), one).0 + super::scalar_from_le_bytes_mod_order_reducing::<_, 32>(&x.to_le_bytes(), one).0 ); } } diff --git a/generic-ec/Cargo.toml b/generic-ec/Cargo.toml index 4f06ee9..c54f9f2 100644 --- a/generic-ec/Cargo.toml +++ b/generic-ec/Cargo.toml @@ -53,9 +53,10 @@ udigest = ["dep:udigest"] curves = ["generic-ec-curves"] curve-secp256k1 = ["curves", "generic-ec-curves/secp256k1"] curve-secp256r1 = ["curves", "generic-ec-curves/secp256r1"] +curve-secp384r1 = ["curves", "generic-ec-curves/secp384r1"] curve-stark = ["curves", "generic-ec-curves/stark"] curve-ed25519 = ["curves", "generic-ec-curves/ed25519", "curve25519"] -all-curves = ["curve-secp256k1", "curve-secp256r1", "curve-stark", "curve-ed25519"] +all-curves = ["curve-secp256k1", "curve-secp256r1", "curve-secp384r1", "curve-stark", "curve-ed25519"] hash-to-scalar = ["dep:rand_hash", "dep:digest", "udigest"] diff --git a/generic-ec/src/lib.rs b/generic-ec/src/lib.rs index 4a9b7e4..82fd7e3 100644 --- a/generic-ec/src/lib.rs +++ b/generic-ec/src/lib.rs @@ -71,11 +71,13 @@ //! |--------------|--------------------|-------------------| //! | secp256k1 | `curve-secp256k1` | [RustCrypto/k256] | //! | secp256r1 | `curve-secp256r1` | [RustCrypto/p256] | +//! | secp384r1 | `curve-secp384r1` | [RustCrypto/p384] | //! | stark-curve | `curve-stark` | [Dfns/stark] | //! | Ed25519 | `curve-ed25519` | [curve25519-dalek]| //! //! [RustCrypto/k256]: https://github.com/RustCrypto/elliptic-curves/tree/master/k256 //! [RustCrypto/p256]: https://github.com/RustCrypto/elliptic-curves/tree/master/p256 +//! [RustCrypto/p384]: https://github.com/RustCrypto/elliptic-curves/tree/master/p384 //! [Dfns/stark]: https://github.com/LFDT-Lockness/stark-curve/ //! [curve25519-dalek]: https://docs.rs/curve25519-dalek/ //! @@ -184,7 +186,7 @@ #![cfg_attr(not(test), forbid(unused_crate_dependencies))] #![cfg_attr(not(test), deny(clippy::unwrap_used, clippy::expect_used))] #![no_std] -#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))] +#![cfg_attr(docsrs, feature(doc_cfg))] #[cfg(feature = "std")] extern crate std; @@ -277,6 +279,9 @@ pub mod curves { #[cfg(feature = "curve-secp256r1")] #[cfg_attr(docsrs, doc(cfg(feature = "curve-secp256r1")))] pub use generic_ec_curves::Secp256r1; + #[cfg(feature = "curve-secp384r1")] + #[cfg_attr(docsrs, doc(cfg(feature = "curve-secp384r1")))] + pub use generic_ec_curves::Secp384r1; #[cfg(feature = "curve-stark")] #[cfg_attr(docsrs, doc(cfg(feature = "curve-stark")))] pub use generic_ec_curves::Stark; @@ -351,6 +356,8 @@ pub mod curves { secp256k1: Secp256k1, #[cfg(feature = "curve-secp256r1")] secp256r1: Secp256r1, + #[cfg(feature = "curve-secp384r1")] + secp384r1: Secp384r1, #[cfg(feature = "curve-stark")] stark: Stark, #[cfg(feature = "curve-ed25519")] diff --git a/generic-ec/src/multiscalar/straus.rs b/generic-ec/src/multiscalar/straus.rs index 569322f..dfdf1e0 100644 --- a/generic-ec/src/multiscalar/straus.rs +++ b/generic-ec/src/multiscalar/straus.rs @@ -186,7 +186,7 @@ impl NafMatrix { fn add_scalar(&mut self, scalar: &Scalar) { let scalar_bytes = scalar.to_le_bytes(); let mut x_u64 = vec![0u64; scalar_bytes.len() / 8 + 1]; - read_le_u64_into(&scalar_bytes, &mut x_u64[0..4]); + read_le_u64_into(&scalar_bytes, &mut x_u64[0..scalar_bytes.len() / 8]); let offset = self.matrix.len(); debug_assert!( @@ -320,6 +320,8 @@ mod tests { mod secp256k1 {} #[instantiate_tests()] mod secp256r1 {} + #[instantiate_tests()] + mod secp384r1 {} #[instantiate_tests()] mod stark {} #[instantiate_tests()] diff --git a/tests/benches/multiscalar.rs b/tests/benches/multiscalar.rs index 478f069..eb34be0 100644 --- a/tests/benches/multiscalar.rs +++ b/tests/benches/multiscalar.rs @@ -15,6 +15,7 @@ fn multiscalar(c: &mut criterion::Criterion) { multiscalar_for_curve::(c, &mut rng, "secp256k1"); multiscalar_for_curve::(c, &mut rng, "secp256r1"); + multiscalar_for_curve::(c, &mut rng, "secp384r1"); multiscalar_for_curve::(c, &mut rng, "stark"); multiscalar_for_curve::(c, &mut rng, "ed25519"); diff --git a/tests/benches/random.rs b/tests/benches/random.rs index 5d24e53..1f2b416 100644 --- a/tests/benches/random.rs +++ b/tests/benches/random.rs @@ -8,6 +8,7 @@ fn random(c: &mut criterion::Criterion) { random_for_curve::(c, &mut rng, "secp256k1"); random_for_curve::(c, &mut rng, "secp256r1"); + random_for_curve::(c, &mut rng, "secp384r1"); random_for_curve::(c, &mut rng, "stark"); random_for_curve::(c, &mut rng, "ed25519"); } diff --git a/tests/tests/curves.rs b/tests/tests/curves.rs index 4af1888..21ce32b 100644 --- a/tests/tests/curves.rs +++ b/tests/tests/curves.rs @@ -248,6 +248,9 @@ mod tests { #[instantiate_tests()] mod secp256r1 {} + #[instantiate_tests()] + mod secp384r1 {} + #[instantiate_tests()] mod stark {} @@ -287,6 +290,9 @@ mod scalar_reduce { #[instantiate_tests()] mod secp256r1_32 {} + #[instantiate_tests()] + mod secp384r1_48 {} + #[instantiate_tests()] mod stark_32 {} @@ -299,7 +305,7 @@ mod scalar_reduce { #[generic_tests::define] mod coordinates { use generic_ec::coords::{HasAffineX, HasAffineXAndParity, HasAffineXY, HasAffineY}; - use generic_ec::curves::{Secp256k1, Secp256r1, Stark}; + use generic_ec::curves::{Secp256k1, Secp256r1, Secp384r1, Stark}; use generic_ec::{Curve, Point, Scalar}; use rand_dev::DevRng; @@ -353,6 +359,9 @@ mod coordinates { #[instantiate_tests()] mod secp256r1 {} + #[instantiate_tests()] + mod secp384r1 {} + #[instantiate_tests()] mod stark {} } diff --git a/tests/tests/dlog_eq.rs b/tests/tests/dlog_eq.rs index 304abe4..911df4e 100644 --- a/tests/tests/dlog_eq.rs +++ b/tests/tests/dlog_eq.rs @@ -40,6 +40,8 @@ mod interactive { mod secp256k1 {} #[instantiate_tests()] mod secp256r1 {} + #[instantiate_tests()] + mod secp384r1 {} #[instantiate_tests()] mod stark {} #[instantiate_tests()] @@ -84,6 +86,8 @@ mod non_interactive { mod secp256k1_sha256 {} #[instantiate_tests()] mod secp256r1_sha256 {} + #[instantiate_tests()] + mod secp384r1_sha256 {} #[instantiate_tests()] mod stark_sha256 {} #[instantiate_tests()] diff --git a/tests/tests/multiscalar.rs b/tests/tests/multiscalar.rs index 88af298..0fe55a4 100644 --- a/tests/tests/multiscalar.rs +++ b/tests/tests/multiscalar.rs @@ -3,7 +3,7 @@ mod tests { use core::iter; use generic_ec::{ - curves::{Ed25519, Secp256k1, Secp256r1, Stark}, + curves::{Ed25519, Secp256k1, Secp256r1, Secp384r1, Stark}, multiscalar::{Dalek, MultiscalarMul, Naive, Straus}, Curve, Point, Scalar, }; @@ -35,6 +35,8 @@ mod tests { mod secp256k1_straus {} #[instantiate_tests()] mod secp256r1_straus {} + #[instantiate_tests()] + mod secp384r1_straus {} #[instantiate_tests()] mod stark_straus {} #[instantiate_tests()] diff --git a/tests/tests/serde.rs b/tests/tests/serde.rs index e5b9070..055251d 100644 --- a/tests/tests/serde.rs +++ b/tests/tests/serde.rs @@ -418,6 +418,9 @@ mod tests { #[instantiate_tests()] mod secp256r1 {} + #[instantiate_tests()] + mod secp384r1 {} + #[instantiate_tests()] mod stark {} }