Implemented multithreading and fixed a number of bugs with WASIX

This commit is contained in:
Johnathan Sharratt
2022-05-14 23:58:04 +02:00
committed by Manos Pitsidianakis
parent 7bf6d30459
commit b0709e4153
30 changed files with 2220 additions and 1932 deletions

View File

@@ -2,8 +2,6 @@
//!
//! This API will be superseded by a standard WASI API when/if such a standard is created.
mod capture_files;
pub use super::unstable::wasi::wasi_get_unordered_imports;
use super::{
externals::{wasm_extern_vec_t, wasm_func_t},
@@ -12,15 +10,14 @@ use super::{
store::wasm_store_t,
};
use crate::error::update_last_error;
use std::cmp::min;
use std::convert::TryFrom;
use std::ffi::CStr;
use std::os::raw::c_char;
use std::slice;
use wasmer_api::{Exportable, Extern};
use wasmer_wasi::{
generate_import_object_from_thread, get_wasi_version, WasiEnv, WasiFile, WasiState,
WasiStateBuilder, WasiVersion,
generate_import_object_from_env, get_wasi_version, WasiEnv, WasiFile, WasiState,
WasiStateBuilder, WasiVersion, Pipe,
};
#[derive(Debug)]
@@ -177,13 +174,13 @@ pub extern "C" fn wasi_env_new(mut config: Box<wasi_config_t>) -> Option<Box<was
if !config.inherit_stdout {
config
.state_builder
.stdout(Box::new(capture_files::OutputCapturer::new()));
.stdout(Box::new(Pipe::new()));
}
if !config.inherit_stderr {
config
.state_builder
.stderr(Box::new(capture_files::OutputCapturer::new()));
.stderr(Box::new(Pipe::new()));
}
// TODO: impl capturer for stdin
@@ -206,19 +203,19 @@ pub unsafe extern "C" fn wasi_env_read_stdout(
buffer_len: usize,
) -> isize {
let inner_buffer = slice::from_raw_parts_mut(buffer as *mut _, buffer_len as usize);
let mut state = env.inner.state();
let state = env.inner.state();
let stdout = if let Ok(stdout) = state.fs.stdout_mut() {
if let Ok(mut stdout) = state.stdout() {
if let Some(stdout) = stdout.as_mut() {
stdout
read_inner(stdout, inner_buffer)
} else {
update_last_error("could not find a file handle for `stdout`");
return -1;
}
} else {
update_last_error("could not find a file handle for `stdout`");
return -1;
};
read_inner(stdout, inner_buffer)
}
}
#[no_mangle]
@@ -228,11 +225,10 @@ pub unsafe extern "C" fn wasi_env_read_stderr(
buffer_len: usize,
) -> isize {
let inner_buffer = slice::from_raw_parts_mut(buffer as *mut _, buffer_len as usize);
let mut state = env.inner.state();
let inodes = state.inodes.write().unwrap();
let stderr = if let Ok(stderr) = inodes.stderr_mut(&state.fs.fd_map) {
let state = env.inner.state();
if let Ok(mut stderr) = state.stderr() {
if let Some(stderr) = stderr.as_mut() {
stderr
read_inner(stderr, inner_buffer)
} else {
update_last_error("could not find a file handle for `stderr`");
return -1;
@@ -240,24 +236,16 @@ pub unsafe extern "C" fn wasi_env_read_stderr(
} else {
update_last_error("could not find a file handle for `stderr`");
return -1;
};
read_inner(stderr, inner_buffer)
}
}
fn read_inner(wasi_file: &mut Box<dyn WasiFile>, inner_buffer: &mut [u8]) -> isize {
if let Some(oc) = wasi_file.downcast_mut::<capture_files::OutputCapturer>() {
let total_to_read = min(inner_buffer.len(), oc.buffer.len());
for (address, value) in inner_buffer
.iter_mut()
.zip(oc.buffer.drain(..total_to_read))
{
*address = value;
fn read_inner(wasi_file: &mut Box<dyn WasiFile + Send + Sync + 'static>, inner_buffer: &mut [u8]) -> isize {
match wasi_file.read(inner_buffer) {
Ok(a) => a as isize,
Err(err) => {
update_last_error(format!("failed to read wasi_file: {}", err));
-1
}
total_to_read as isize
} else {
-1
}
}
@@ -356,8 +344,7 @@ fn wasi_get_imports_inner(
let version = c_try!(get_wasi_version(&module.inner, false)
.ok_or("could not detect a WASI version on the given module"));
let mut thread = wasi_env.inner.new_thread();
let import_object = generate_import_object_from_thread(store, thread, version);
let import_object = generate_import_object_from_env(store, wasi_env.inner.clone(), version);
imports.set_buffer(c_try!(module
.inner