Skip to content

Instantly share code, notes, and snippets.

@JamesTheAwesomeDude
Last active April 24, 2024 20:51
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save JamesTheAwesomeDude/fb3126929c322f26fcf2a6259345a0fa to your computer and use it in GitHub Desktop.
Save JamesTheAwesomeDude/fb3126929c322f26fcf2a6259345a0fa to your computer and use it in GitHub Desktop.
rust randombytes function that returns an array
/* Written on Rust 1.77.2 (Stable), should run on even older builds.
Usage Example:
let my_buffer: [u8; 42] = randombytes().unwrap();
*/
extern crate getrandom; // https://github.com/rust-random/getrandom
use core::mem::MaybeUninit;
pub fn randombytes<const N: usize>() -> Result<[u8; N], getrandom::Error> {
// https://github.com/rust-random/rand/issues/1080
// https://github.com/rust-random/rand/blob/0.8.5/rand_core/src/os.rs#L67
// https://github.com/rust-random/getrandom/blob/v0.2.14/src/lib.rs#L376
let mut buf = [MaybeUninit::<u8>::uninit(); N];
getrandom::getrandom_uninit(&mut buf)?;
Ok(unsafe {
// TODO pending https://github.com/rust-lang/rust/issues/96097
// https://github.com/rust-random/getrandom/blob/v0.2.14/src/util.rs#L4
// https://github.com/rust-lang/rust/blob/1.77.2/library/core/src/mem/maybe_uninit.rs#L947
// https://github.com/Lokathor/bytemuck/blob/v1.15.0/src/lib.rs#L113
// SAFETY: `MaybeUninit<T>` is guaranteed to be layout-compatible with `T`,
// therefore `[MaybeUninit<T>; N]` is layout-compatible with `[T; N]`.
// SAFETY: getrandom_uninit returned Ok,
// therefore buf is guaranteed to be entirely initialized.
core::mem::transmute_copy(&core::mem::ManuallyDrop::new(buf))
})
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment