Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
bytecodealliance
GitHub Repository: bytecodealliance/wasmtime
Path: blob/main/crates/wasi-common/src/sync/mod.rs
1693 views
1
//! The `wasi-cap-std-sync` crate provides impl of `WasiFile` and `WasiDir` in
2
//! terms of `cap_std::fs::{File, Dir}`. These types provide sandboxed access
3
//! to the local filesystem on both Unix and Windows.
4
//!
5
//! All syscalls are hidden behind the `cap-std` hierarchy, with the lone
6
//! exception of the `sched` implementation, which is provided for both unix
7
//! and windows in separate modules.
8
//!
9
//! Any `wasi_common::{WasiCtx, WasiCtxBuilder}` is interoperable with the
10
//! implementations provided in `wasi_common::sync`. However, for convenience,
11
//! this module provides its own `WasiCtxBuilder` that hooks up to all of the
12
//! crate's components, i.e. it fills in all of the arguments to
13
//! `WasiCtx::builder(...)`, presents `preopen_dir` in terms of
14
//! `cap_std::fs::Dir`, and provides convenience methods for inheriting the
15
//! parent process's stdio, args, and env.
16
17
pub mod clocks;
18
pub mod dir;
19
pub mod file;
20
pub mod net;
21
pub mod sched;
22
pub mod stdio;
23
24
pub use cap_std::ambient_authority;
25
pub use cap_std::fs::Dir;
26
pub use cap_std::net::TcpListener;
27
pub use clocks::clocks_ctx;
28
pub use sched::sched_ctx;
29
30
use self::net::Socket;
31
use crate::{Error, WasiCtx, WasiFile, file::FileAccessMode, table::Table};
32
use cap_rand::{Rng, RngCore, SeedableRng};
33
use std::mem;
34
use std::path::Path;
35
36
pub struct WasiCtxBuilder {
37
ctx: WasiCtx,
38
built: bool,
39
}
40
41
impl WasiCtxBuilder {
42
pub fn new() -> Self {
43
WasiCtxBuilder {
44
ctx: WasiCtx::new(random_ctx(), clocks_ctx(), sched_ctx(), Table::new()),
45
built: false,
46
}
47
}
48
pub fn env(&mut self, var: &str, value: &str) -> Result<&mut Self, crate::StringArrayError> {
49
self.ctx.push_env(var, value)?;
50
Ok(self)
51
}
52
pub fn envs(&mut self, env: &[(String, String)]) -> Result<&mut Self, crate::StringArrayError> {
53
for (k, v) in env {
54
self.ctx.push_env(k, v)?;
55
}
56
Ok(self)
57
}
58
pub fn inherit_env(&mut self) -> Result<&mut Self, crate::StringArrayError> {
59
for (key, value) in std::env::vars() {
60
self.ctx.push_env(&key, &value)?;
61
}
62
Ok(self)
63
}
64
pub fn arg(&mut self, arg: &str) -> Result<&mut Self, crate::StringArrayError> {
65
self.ctx.push_arg(arg)?;
66
Ok(self)
67
}
68
pub fn args(&mut self, arg: &[String]) -> Result<&mut Self, crate::StringArrayError> {
69
for a in arg {
70
self.ctx.push_arg(&a)?;
71
}
72
Ok(self)
73
}
74
pub fn inherit_args(&mut self) -> Result<&mut Self, crate::StringArrayError> {
75
for arg in std::env::args() {
76
self.ctx.push_arg(&arg)?;
77
}
78
Ok(self)
79
}
80
pub fn stdin(&mut self, f: Box<dyn WasiFile>) -> &mut Self {
81
self.ctx.set_stdin(f);
82
self
83
}
84
pub fn stdout(&mut self, f: Box<dyn WasiFile>) -> &mut Self {
85
self.ctx.set_stdout(f);
86
self
87
}
88
pub fn stderr(&mut self, f: Box<dyn WasiFile>) -> &mut Self {
89
self.ctx.set_stderr(f);
90
self
91
}
92
pub fn inherit_stdin(&mut self) -> &mut Self {
93
self.stdin(Box::new(crate::sync::stdio::stdin()))
94
}
95
pub fn inherit_stdout(&mut self) -> &mut Self {
96
self.stdout(Box::new(crate::sync::stdio::stdout()))
97
}
98
pub fn inherit_stderr(&mut self) -> &mut Self {
99
self.stderr(Box::new(crate::sync::stdio::stderr()))
100
}
101
pub fn inherit_stdio(&mut self) -> &mut Self {
102
self.inherit_stdin().inherit_stdout().inherit_stderr()
103
}
104
pub fn preopened_dir(
105
&mut self,
106
dir: Dir,
107
guest_path: impl AsRef<Path>,
108
) -> Result<&mut Self, Error> {
109
let dir = Box::new(crate::sync::dir::Dir::from_cap_std(dir));
110
self.ctx.push_preopened_dir(dir, guest_path)?;
111
Ok(self)
112
}
113
pub fn preopened_socket(
114
&mut self,
115
fd: u32,
116
socket: impl Into<Socket>,
117
) -> Result<&mut Self, Error> {
118
let socket: Socket = socket.into();
119
let file: Box<dyn WasiFile> = socket.into();
120
self.ctx
121
.insert_file(fd, file, FileAccessMode::READ | FileAccessMode::WRITE);
122
Ok(self)
123
}
124
pub fn build(&mut self) -> WasiCtx {
125
assert!(!self.built);
126
let WasiCtxBuilder { ctx, .. } = mem::replace(self, Self::new());
127
self.built = true;
128
ctx
129
}
130
}
131
132
pub fn random_ctx() -> Box<dyn RngCore + Send + Sync> {
133
let mut rng = cap_rand::thread_rng(cap_rand::ambient_authority());
134
Box::new(cap_rand::rngs::StdRng::from_seed(rng.r#gen()))
135
}
136
137
#[cfg(feature = "wasmtime")]
138
super::define_wasi!(block_on);
139
140