diff --git a/.github/workflows/rust.yml b/.github/workflows/rust.yml index 2fd296a..d1094a6 100644 --- a/.github/workflows/rust.yml +++ b/.github/workflows/rust.yml @@ -30,7 +30,7 @@ jobs: - run: cargo test --target ${{ matrix.target }} --no-default-features --features alloc --lib - run: cargo test --target ${{ matrix.target }} - run: cargo test --target ${{ matrix.target }} --features batch - - run: cargo test --target ${{ matrix.target }} --features rand_core + - run: cargo test --target ${{ matrix.target }} --features "digest rand_core" - run: cargo test --target ${{ matrix.target }} --features serde - run: cargo test --target ${{ matrix.target }} --features pem diff --git a/Cargo.toml b/Cargo.toml index 5bfa0ed..e41609d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -57,6 +57,7 @@ std = ["alloc", "ed25519/std", "serde?/std", "sha2/std"] asm = ["sha2/asm"] batch = ["alloc", "merlin", "rand_core"] +digest = [] # This features turns off stricter checking for scalar malleability in signatures legacy_compatibility = [] pkcs8 = ["ed25519/pkcs8"] diff --git a/src/errors.rs b/src/errors.rs index aa4e5aa..7cba06d 100644 --- a/src/errors.rs +++ b/src/errors.rs @@ -48,6 +48,7 @@ pub(crate) enum InternalError { length_c: usize, }, /// An ed25519ph signature can only take up to 255 octets of context. + #[cfg(feature = "digest")] PrehashedContextLength, /// A mismatched (public, secret) key pair. MismatchedKeypair, @@ -76,6 +77,7 @@ impl Display for InternalError { {} has length {}, {} has length {}.", na, la, nb, lb, nc, lc ), + #[cfg(feature = "digest")] InternalError::PrehashedContextLength => write!( f, "An ed25519ph signature can only take up to 255 octets of context" diff --git a/src/lib.rs b/src/lib.rs index 817e954..84cb275 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -262,6 +262,7 @@ mod signature; mod signing; mod verifying; +#[cfg(feature = "digest")] pub use curve25519_dalek::digest::Digest; #[cfg(feature = "batch")] diff --git a/src/signing.rs b/src/signing.rs index df828a6..a2adffa 100644 --- a/src/signing.rs +++ b/src/signing.rs @@ -24,6 +24,7 @@ use serde_bytes::{ByteBuf as SerdeByteBuf, Bytes as SerdeBytes}; use sha2::Sha512; +#[cfg(feature = "digest")] use curve25519_dalek::digest::generic_array::typenum::U64; use curve25519_dalek::digest::Digest; use curve25519_dalek::edwards::CompressedEdwardsY; @@ -208,12 +209,15 @@ impl SigningKey { /// /// # Examples /// - #[cfg_attr(feature = "rand_core", doc = "```")] - #[cfg_attr(not(feature = "rand_core"), doc = "```ignore")] + #[cfg_attr(all(feature = "rand_core", feature = "digest"), doc = "```")] + #[cfg_attr( + any(not(feature = "rand_core"), not(feature = "digest")), + doc = "```ignore" + )] /// use ed25519_dalek::Digest; /// use ed25519_dalek::SigningKey; - /// use ed25519_dalek::Sha512; /// use ed25519_dalek::Signature; + /// use sha2::Sha512; /// use rand::rngs::OsRng; /// /// # #[cfg(feature = "std")] @@ -253,13 +257,16 @@ impl SigningKey { /// Let's add a context for good measure (remember, you'll want to choose /// your own!): /// - #[cfg_attr(feature = "rand_core", doc = "```")] - #[cfg_attr(not(feature = "rand_core"), doc = "```ignore")] + #[cfg_attr(all(feature = "rand_core", feature = "digest"), doc = "```")] + #[cfg_attr( + any(not(feature = "rand_core"), not(feature = "digest")), + doc = "```ignore" + )] /// # use ed25519_dalek::Digest; /// # use ed25519_dalek::SigningKey; /// # use ed25519_dalek::Signature; /// # use ed25519_dalek::SignatureError; - /// # use ed25519_dalek::Sha512; + /// # use sha2::Sha512; /// # use rand::rngs::OsRng; /// # /// # fn do_test() -> Result { @@ -286,6 +293,7 @@ impl SigningKey { /// /// [rfc8032]: https://tools.ietf.org/html/rfc8032#section-5.1 /// [terrible_idea]: https://github.com/isislovecruft/scripts/blob/master/gpgkey2bc.py + #[cfg(feature = "digest")] pub fn sign_prehashed( &self, prehashed_message: D, @@ -327,13 +335,16 @@ impl SigningKey { /// /// # Examples /// - #[cfg_attr(feature = "rand_core", doc = "```")] - #[cfg_attr(not(feature = "rand_core"), doc = "```ignore")] + #[cfg_attr(all(feature = "rand_core", feature = "digest"), doc = "```")] + #[cfg_attr( + any(not(feature = "rand_core"), not(feature = "digest")), + doc = "```ignore" + )] /// use ed25519_dalek::Digest; /// use ed25519_dalek::SigningKey; /// use ed25519_dalek::Signature; /// use ed25519_dalek::SignatureError; - /// use ed25519_dalek::Sha512; + /// use sha2::Sha512; /// use rand::rngs::OsRng; /// /// # fn do_test() -> Result<(), SignatureError> { @@ -369,6 +380,7 @@ impl SigningKey { /// ``` /// /// [rfc8032]: https://tools.ietf.org/html/rfc8032#section-5.1 + #[cfg(feature = "digest")] pub fn verify_prehashed( &self, prehashed_message: D, @@ -724,6 +736,7 @@ impl ExpandedSecretKey { /// a `SignatureError`. /// /// [rfc8032]: https://tools.ietf.org/html/rfc8032#section-5.1 + #[cfg(feature = "digest")] #[allow(non_snake_case)] pub(crate) fn sign_prehashed<'a, D>( &self, diff --git a/src/verifying.rs b/src/verifying.rs index 89e1b65..7879e20 100644 --- a/src/verifying.rs +++ b/src/verifying.rs @@ -13,6 +13,7 @@ use core::convert::TryFrom; use core::fmt::Debug; use core::hash::{Hash, Hasher}; +#[cfg(feature = "digest")] use curve25519_dalek::digest::generic_array::typenum::U64; use curve25519_dalek::digest::Digest; use curve25519_dalek::edwards::CompressedEdwardsY; @@ -21,7 +22,7 @@ use curve25519_dalek::scalar::Scalar; use ed25519::signature::Verifier; -pub use sha2::Sha512; +use sha2::Sha512; #[cfg(feature = "pkcs8")] use ed25519::pkcs8::{self, DecodePublicKey}; @@ -206,6 +207,7 @@ impl VerifyingKey { /// /// Returns `true` if the `signature` was a valid signature created by this /// `Keypair` on the `prehashed_message`. + #[cfg(feature = "digest")] #[allow(non_snake_case)] pub fn verify_prehashed( &self, @@ -350,6 +352,7 @@ impl VerifyingKey { /// /// Returns `true` if the `signature` was a valid signature created by this /// `Keypair` on the `prehashed_message`. + #[cfg(feature = "digest")] #[allow(non_snake_case)] pub fn verify_prehashed_strict( &self, diff --git a/tests/ed25519.rs b/tests/ed25519.rs index 25c3520..6775573 100644 --- a/tests/ed25519.rs +++ b/tests/ed25519.rs @@ -14,6 +14,7 @@ use curve25519_dalek; use ed25519_dalek::*; use hex::FromHex; +#[cfg(feature = "digest")] use hex_literal::hex; #[cfg(test)] @@ -96,8 +97,9 @@ mod vectors { } // From https://tools.ietf.org/html/rfc8032#section-7.3 + #[cfg(feature = "digest")] #[test] - fn ed25519ph_rf8032_test_vector() { + fn ed25519ph_rf8032_test_vector_prehash() { let sec_bytes = hex!("833fe62409237b9d62ec77587520911e9a759cec1d19755b7da901b96dca3d42"); let pub_bytes = hex!("ec172b93ad5e563bf4932c70e1245034c35467ef2efd4d64ebf819683467e2bf"); let msg_bytes = hex!("616263"); @@ -234,6 +236,7 @@ mod vectors { // Identical to repudiation() above, but testing verify_prehashed against // verify_prehashed_strict. See comments above for a description of what's happening. + #[cfg(feature = "digest")] #[test] fn repudiation_prehash() { let message1 = Sha512::new().chain_update(b"Send 100 USD to Alice"); @@ -282,6 +285,7 @@ mod vectors { mod integrations { use super::*; use rand::rngs::OsRng; + #[cfg(feature = "digest")] use sha2::Sha512; use std::collections::HashMap; @@ -328,6 +332,7 @@ mod integrations { ); } + #[cfg(feature = "digest")] #[test] fn ed25519ph_sign_verify() { let signing_key: SigningKey;