diff --git a/crates/wasi-c2/TEST_FAILURES b/crates/wasi-c2/TEST_FAILURES index dbb8a8338f..b5a541d2d8 100644 --- a/crates/wasi-c2/TEST_FAILURES +++ b/crates/wasi-c2/TEST_FAILURES @@ -1,6 +1,4 @@ -wasi_tests::big_random_buf - - no randomness yet wasi_tests::clock_time_get - no clocks yet wasi_tests::dangling_symlink diff --git a/crates/wasi-c2/src/ctx.rs b/crates/wasi-c2/src/ctx.rs index 7b0a366ae1..ce0e05b1e7 100644 --- a/crates/wasi-c2/src/ctx.rs +++ b/crates/wasi-c2/src/ctx.rs @@ -1,5 +1,6 @@ use crate::dir::{DirCaps, DirEntry, WasiDir}; use crate::file::{FileCaps, FileEntry, WasiFile}; +use crate::random::WasiRandom; use crate::string_array::{StringArray, StringArrayError}; use crate::table::Table; use crate::Error; @@ -10,6 +11,7 @@ use std::rc::Rc; pub struct WasiCtx { pub(crate) args: StringArray, pub(crate) env: StringArray, + pub(crate) random: Box, table: Rc>, } @@ -22,6 +24,7 @@ impl WasiCtx { WasiCtx { args: StringArray::new(), env: StringArray::new(), + random: Box::new(crate::random::GetRandom), table: Rc::new(RefCell::new(Table::new())), } } @@ -110,4 +113,9 @@ impl WasiCtxBuilder { )))?; Ok(self) } + + pub fn random(&mut self, random: Box) -> &mut Self { + self.0.random = random; + self + } } diff --git a/crates/wasi-c2/src/lib.rs b/crates/wasi-c2/src/lib.rs index eb581d06dc..8393b1c5c5 100644 --- a/crates/wasi-c2/src/lib.rs +++ b/crates/wasi-c2/src/lib.rs @@ -4,6 +4,7 @@ mod ctx; mod dir; mod error; mod file; +pub mod random; pub mod snapshots; pub mod stdio; mod string_array; diff --git a/crates/wasi-c2/src/random.rs b/crates/wasi-c2/src/random.rs new file mode 100644 index 0000000000..2397469e18 --- /dev/null +++ b/crates/wasi-c2/src/random.rs @@ -0,0 +1,37 @@ +use crate::Error; +use std::cell::RefCell; + +pub trait WasiRandom { + fn get(&self, buf: &mut [u8]) -> Result<(), Error>; +} + +pub struct GetRandom; + +impl WasiRandom for GetRandom { + fn get(&self, buf: &mut [u8]) -> Result<(), Error> { + getrandom::getrandom(buf)?; + Ok(()) + } +} + +pub struct Deterministic { + sequence: RefCell>>, +} + +impl Deterministic { + pub fn new(bytes: Vec) -> Self { + Deterministic { + sequence: RefCell::new(bytes.into_iter().cycle()), + } + } +} + +impl WasiRandom for Deterministic { + fn get(&self, buf: &mut [u8]) -> Result<(), Error> { + let mut s = self.sequence.borrow_mut(); + for b in buf.iter_mut() { + *b = s.next().expect("infinite sequence"); + } + Ok(()) + } +} diff --git a/crates/wasi-c2/src/snapshots/preview_1.rs b/crates/wasi-c2/src/snapshots/preview_1.rs index d8d37b4fc8..f778654e58 100644 --- a/crates/wasi-c2/src/snapshots/preview_1.rs +++ b/crates/wasi-c2/src/snapshots/preview_1.rs @@ -6,7 +6,7 @@ use fs_set_times::SystemTimeSpec; use std::cell::{Ref, RefMut}; use std::convert::{TryFrom, TryInto}; use std::io::{IoSlice, IoSliceMut}; -use std::ops::Deref; +use std::ops::{Deref, DerefMut}; use tracing::debug; use wiggle::GuestPtr; @@ -801,7 +801,9 @@ impl<'a> wasi_snapshot_preview1::WasiSnapshotPreview1 for WasiCtx { } fn random_get(&self, buf: &GuestPtr, buf_len: types::Size) -> Result<(), Error> { - unimplemented!() + let mut buf = buf.as_array(buf_len).as_slice_mut()?; + self.random.get(buf.deref_mut())?; + Ok(()) } fn sock_recv(