diff options
Diffstat (limited to 'vendor/ed25519-compact/src/common.rs')
-rw-r--r-- | vendor/ed25519-compact/src/common.rs | 90 |
1 files changed, 90 insertions, 0 deletions
diff --git a/vendor/ed25519-compact/src/common.rs b/vendor/ed25519-compact/src/common.rs new file mode 100644 index 000000000..12f28c519 --- /dev/null +++ b/vendor/ed25519-compact/src/common.rs @@ -0,0 +1,90 @@ +use core::ops::{Deref, DerefMut}; +use core::ptr; +use core::sync::atomic; + +use super::error::Error; + +/// A seed, which a key pair can be derived from. +#[derive(Copy, Clone, Debug, Eq, PartialEq, Hash)] +pub struct Seed([u8; Seed::BYTES]); + +impl From<[u8; 32]> for Seed { + fn from(seed: [u8; 32]) -> Self { + Seed(seed) + } +} + +impl Seed { + /// Number of raw bytes in a seed. + pub const BYTES: usize = 32; + + /// Creates a seed from raw bytes. + pub fn new(seed: [u8; Seed::BYTES]) -> Self { + Seed(seed) + } + + /// Creates a seed from a slice. + pub fn from_slice(seed: &[u8]) -> Result<Self, Error> { + let mut seed_ = [0u8; Seed::BYTES]; + if seed.len() != seed_.len() { + return Err(Error::InvalidSeed); + } + seed_.copy_from_slice(seed); + Ok(Seed::new(seed_)) + } + + /// Tentatively overwrite the content of the seed with zeros. + pub fn wipe(self) { + Mem::wipe(self.0) + } +} + +#[cfg(feature = "random")] +impl Default for Seed { + /// Generates a random seed. + fn default() -> Self { + let mut seed = [0u8; Seed::BYTES]; + getrandom::getrandom(&mut seed).expect("RNG failure"); + Seed(seed) + } +} + +#[cfg(feature = "random")] +impl Seed { + /// Generates a random seed. + pub fn generate() -> Self { + Seed::default() + } +} + +impl Deref for Seed { + type Target = [u8; Seed::BYTES]; + + /// Returns a seed as raw bytes. + fn deref(&self) -> &Self::Target { + &self.0 + } +} + +impl DerefMut for Seed { + /// Returns a seed as mutable raw bytes. + fn deref_mut(&mut self) -> &mut Self::Target { + &mut self.0 + } +} + +pub(crate) struct Mem; + +impl Mem { + #[inline] + pub fn wipe<T: Default>(mut x: impl AsMut<[T]>) { + let x = x.as_mut(); + for i in 0..x.len() { + unsafe { + ptr::write_volatile(x.as_mut_ptr().add(i), T::default()); + } + } + atomic::compiler_fence(atomic::Ordering::SeqCst); + atomic::fence(atomic::Ordering::SeqCst); + } +} |