Add method SecretKey::from_hashed_data

Analogous to the method on `Message`; add a constructor method on
`SecretKey` that hashes the input data.

While we are at it improve the rustdocs on `Message::from_hashed_data`
so docs on both methods are uniform.
This commit is contained in:
Tobin C. Harding 2022-10-27 14:14:57 +11:00
parent 15a8c20427
commit 5417fad7cb
2 changed files with 46 additions and 7 deletions

View File

@ -25,6 +25,9 @@ use crate::Error::{self, InvalidPublicKey, InvalidPublicKeySum, InvalidSecretKey
use crate::ffi::{self, CPtr, impl_array_newtype};
use crate::ffi::types::c_uint;
#[cfg(feature = "bitcoin_hashes")]
use crate::{hashes, ThirtyTwoByteHash};
#[cfg(feature = "serde")]
use serde::ser::SerializeTuple;
@ -228,6 +231,31 @@ impl SecretKey {
SecretKey(sk)
}
/// Constructs a [`SecretKey`] by hashing `data` with hash algorithm `H`.
///
/// Requires the feature `bitcoin_hashes` to be enabled.
///
/// # Examples
///
/// ```
/// # #[cfg(feature="bitcoin_hashes")] {
/// use secp256k1::hashes::{sha256, Hash};
/// use secp256k1::SecretKey;
///
/// let sk1 = SecretKey::from_hashed_data::<sha256::Hash>("Hello world!".as_bytes());
/// // is equivalent to
/// let sk2 = SecretKey::from(sha256::Hash::hash("Hello world!".as_bytes()));
///
/// assert_eq!(sk1, sk2);
/// # }
/// ```
#[cfg(feature = "bitcoin_hashes")]
#[cfg_attr(docsrs, doc(cfg(feature = "bitcoin_hashes")))]
#[inline]
pub fn from_hashed_data<H: ThirtyTwoByteHash + hashes::Hash>(data: &[u8]) -> Self {
<H as hashes::Hash>::hash(data).into()
}
/// Returns the secret key as a byte value.
#[inline]
pub fn secret_bytes(&self) -> [u8; constants::SECRET_KEY_SIZE] {
@ -352,6 +380,14 @@ impl SecretKey {
}
}
#[cfg(feature = "bitcoin_hashes")]
impl<T: ThirtyTwoByteHash> From<T> for SecretKey {
/// Converts a 32-byte hash directly to a secret key without error paths.
fn from(t: T) -> SecretKey {
SecretKey::from_slice(&t.into_32()).expect("failed to create secret key")
}
}
#[cfg(feature = "serde")]
#[cfg_attr(docsrs, doc(cfg(feature = "serde")))]
impl serde::Serialize for SecretKey {

View File

@ -281,20 +281,23 @@ impl Message {
}
}
/// Constructs a `Message` by hashing `data` with hash algorithm `H`. This requires the feature
/// `bitcoin_hashes` to be enabled.
/// ```rust
/// extern crate bitcoin_hashes;
/// # extern crate secp256k1;
/// Constructs a [`Message`] by hashing `data` with hash algorithm `H`.
///
/// Requires the feature `bitcoin_hashes` to be enabled.
///
/// # Examples
///
/// ```
/// # #[cfg(feature="bitcoin_hashes")] {
/// use secp256k1::hashes::{sha256, Hash};
/// use secp256k1::Message;
/// use bitcoin_hashes::sha256;
/// use bitcoin_hashes::Hash;
///
/// let m1 = Message::from_hashed_data::<sha256::Hash>("Hello world!".as_bytes());
/// // is equivalent to
/// let m2 = Message::from(sha256::Hash::hash("Hello world!".as_bytes()));
///
/// assert_eq!(m1, m2);
/// # }
/// ```
#[cfg(feature = "bitcoin_hashes")]
#[cfg_attr(docsrs, doc(cfg(feature = "bitcoin_hashes")))]