1#![cfg_attr(not(feature = "std"), no_std)]
2extern crate alloc;
3
4pub mod bigint;
5pub mod pkcs7;
6pub mod sha256;
7pub mod sha512;
8pub mod hmac;
9pub mod hkdf;
10pub mod aes;
11pub mod aes128;
12pub mod aes256;
13pub mod token;
14pub mod x25519;
15pub mod ed25519;
16pub mod identity;
17
18pub trait Rng {
21 fn fill_bytes(&mut self, dest: &mut [u8]);
22}
23
24pub struct FixedRng {
26 bytes: alloc::vec::Vec<u8>,
27 pos: usize,
28}
29
30impl FixedRng {
31 pub fn new(bytes: &[u8]) -> Self {
32 Self {
33 bytes: bytes.to_vec(),
34 pos: 0,
35 }
36 }
37}
38
39impl Rng for FixedRng {
40 fn fill_bytes(&mut self, dest: &mut [u8]) {
41 for b in dest.iter_mut() {
42 *b = self.bytes[self.pos % self.bytes.len()];
43 self.pos += 1;
44 }
45 }
46}
47
48#[cfg(feature = "std")]
50pub struct OsRng;
51
52#[cfg(feature = "std")]
53impl Rng for OsRng {
54 fn fill_bytes(&mut self, dest: &mut [u8]) {
55 #[cfg(target_os = "linux")]
57 {
58 let ret = unsafe {
59 libc_getrandom(dest.as_mut_ptr(), dest.len(), 0)
60 };
61 assert!(ret == dest.len() as isize, "getrandom failed");
62 }
63 #[cfg(not(target_os = "linux"))]
64 {
65 use std::io::Read;
67 let mut f = std::fs::File::open("/dev/urandom").expect("Failed to open /dev/urandom");
68 f.read_exact(dest).expect("Failed to read from /dev/urandom");
69 }
70 }
71}
72
73#[cfg(all(feature = "std", target_os = "linux"))]
74unsafe fn libc_getrandom(buf: *mut u8, buflen: usize, flags: u32) -> isize {
75 #[cfg(target_arch = "x86_64")]
77 {
78 let ret: isize;
79 core::arch::asm!(
80 "syscall",
81 in("rax") 318u64,
82 in("rdi") buf as u64,
83 in("rsi") buflen as u64,
84 in("rdx") flags as u64,
85 lateout("rax") ret,
86 lateout("rcx") _,
87 lateout("r11") _,
88 );
89 ret
90 }
91 #[cfg(target_arch = "aarch64")]
92 {
93 let ret: isize;
94 core::arch::asm!(
95 "svc #0",
96 in("x8") 278u64,
97 in("x0") buf as u64,
98 in("x1") buflen as u64,
99 in("x2") flags as u64,
100 lateout("x0") ret,
101 );
102 ret
103 }
104 #[cfg(not(any(target_arch = "x86_64", target_arch = "aarch64")))]
105 {
106 compile_error!("Unsupported architecture for getrandom syscall");
107 }
108}