apple_security_framework/
random.rs

1//! Randomness support.
2
3use std::io;
4
5use security_framework_sys::random::{kSecRandomDefault, SecRandomCopyBytes, SecRandomRef};
6
7/// A source of random data.
8///
9/// # Examples
10///
11/// ```
12/// let rng = apple_security_framework::random::SecRandom::default();
13///
14/// let mut buf = [0; 32];
15/// rng.copy_bytes(&mut buf).unwrap();
16///
17/// println!("{}", hex::encode(buf));
18/// ```
19pub struct SecRandom(SecRandomRef);
20
21unsafe impl Sync for SecRandom {}
22unsafe impl Send for SecRandom {}
23
24impl Default for SecRandom {
25    #[inline(always)]
26    fn default() -> Self {
27        unsafe { Self(kSecRandomDefault) }
28    }
29}
30
31impl SecRandom {
32    /// Fills the buffer with cryptographically secure random bytes.
33    pub fn copy_bytes(&self, buf: &mut [u8]) -> io::Result<()> {
34        if unsafe { SecRandomCopyBytes(self.0, buf.len(), buf.as_mut_ptr().cast()) } == 0 {
35            Ok(())
36        } else {
37            Err(io::Error::last_os_error())
38        }
39    }
40}
41
42#[cfg(test)]
43mod test {
44    use super::*;
45
46    #[test]
47    fn basic() {
48        let mut buf = [0; 10];
49        SecRandom::default().copy_bytes(&mut buf).unwrap();
50    }
51}