pub struct Command { /* private fields */ }Expand description
A builder for spawning a process.
Implementations§
Source§impl Command
impl Command
Sourcepub fn new<S: AsRef<OsStr>>(program: S) -> Self
pub fn new<S: AsRef<OsStr>>(program: S) -> Self
Constructs a new Command for launching the program at path program,
with the following default configuration:
- No arguments to the program
- Inherit the current process’s environment
- Inherit the current process’s working directory
- Inherit stdin/stdout/stderr for
spawnorstatus, but create pipes foroutput
Builder methods are provided to change these defaults and otherwise configure the process.
If program is not an absolute path, the PATH will be searched in an
OS-defined way.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("sh");Sourcepub fn program<S: AsRef<OsStr>>(&mut self, program: S) -> &mut Self
pub fn program<S: AsRef<OsStr>>(&mut self, program: S) -> &mut Self
Sets the path to the program. This can be used to override what was
already set in Command::new.
NOTE: This also changes argument 0 to match program.
Sourcepub fn arg0<S: AsRef<OsStr>>(&mut self, arg0: S) -> &mut Self
pub fn arg0<S: AsRef<OsStr>>(&mut self, arg0: S) -> &mut Self
Explicitly sets the first argument. By default, this is the same as the program path and is what you want in most cases.
Sourcepub fn get_arg0(&self) -> &OsStr
pub fn get_arg0(&self) -> &OsStr
Gets the first argument. Unless Command::arg0 was used, this returns
the same string as Command::get_program.
Sourcepub fn arg<S: AsRef<OsStr>>(&mut self, arg: S) -> &mut Self
pub fn arg<S: AsRef<OsStr>>(&mut self, arg: S) -> &mut Self
Adds an argument to pass to the program.
Only one argument can be passed per use. So instead of:
reverie_process::Command::new("sh").arg("-C /path/to/repo");usage would be:
reverie_process::Command::new("sh")
.arg("-C")
.arg("/path/to/repo");To pass multiple arguments see args.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("ls").arg("-l").arg("-a");Sourcepub fn get_args(&self) -> impl Iterator<Item = &OsStr>
pub fn get_args(&self) -> impl Iterator<Item = &OsStr>
Returns an iterator of the arguments that will be passed to the program.
This does not include the program name itself. It only includes the
arguments specified with Command::arg and Command::args.
Sourcepub fn prepend_args<I, S>(&mut self, args: I) -> &mut Self
pub fn prepend_args<I, S>(&mut self, args: I) -> &mut Self
Prepends arguments to the beginning of the command. Note that arguments are prepended after arg0, but before the rest of the arguments.
Sourcepub fn env<K, V>(&mut self, key: K, val: V) -> &mut Self
pub fn env<K, V>(&mut self, key: K, val: V) -> &mut Self
Inserts or updates an environment variable mapping.
Note that environment variable names are case-insensitive (but case-preserving) on Windows, and case-sensitive on all other platforms.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("ls").env("PATH", "/bin");Sourcepub fn envs<I, K, V>(&mut self, vars: I) -> &mut Self
pub fn envs<I, K, V>(&mut self, vars: I) -> &mut Self
Adds or updates multiple environment variable mappings.
§Examples
Basic usage:
use std::collections::HashMap;
use std::env;
use reverie_process::Command;
use reverie_process::Stdio;
let filtered_env: HashMap<String, String> = env::vars()
.filter(|&(ref k, _)| k == "TERM" || k == "TZ" || k == "LANG" || k == "PATH")
.collect();
let command = Command::new("printenv")
.stdin(Stdio::null())
.stdout(Stdio::inherit())
.env_clear()
.envs(&filtered_env);Sourcepub fn env_remove<K: AsRef<OsStr>>(&mut self, key: K) -> &mut Self
pub fn env_remove<K: AsRef<OsStr>>(&mut self, key: K) -> &mut Self
Removes an environment variable mapping.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("ls").env_remove("PATH");Sourcepub fn env_clear(&mut self) -> &mut Self
pub fn env_clear(&mut self) -> &mut Self
Clears the entire environment map for the child process.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("ls").env_clear();Sourcepub fn current_dir<P: AsRef<Path>>(&mut self, dir: P) -> &mut Self
pub fn current_dir<P: AsRef<Path>>(&mut self, dir: P) -> &mut Self
Sets the working directory for the child process.
§Interaction with chroot
The working directory is set after the chroot is performed (if a chroot directory is specified). Thus, the path given is relative to the chroot directory. Otherwise, if no chroot directory is specified, the working directory is relative to the current working directory of the parent process at the time the child process is spawned.
§Platform-specific behavior
If the program path is relative (e.g., "./script.sh"), it’s ambiguous
whether it should be interpreted relative to the parent’s working
directory or relative to current_dir. The behavior in this case is
platform specific and unstable, and it’s recommended to use
canonicalize to get an absolute program path instead.
§Examples
Basic usage:
use reverie_process::Command;
let command = Command::new("ls").current_dir("/bin");Sourcepub fn stdin<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
pub fn stdin<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
Sets configuration for the child process’s standard input (stdin) handle.
Defaults to Stdio::inherit when used with spawn or status, and
defaults to Stdio::piped when used with output.
§Examples
Basic usage:
use reverie_process::Command;
use reverie_process::Stdio;
let command = Command::new("ls").stdin(Stdio::null());Sourcepub fn stdout<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
pub fn stdout<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
Sets configuration for the child process’s standard output (stdout) handle.
Defaults to Stdio::inherit when used with spawn or status, and
defaults to Stdio::piped when used with output.
§Examples
Basic usage:
use reverie_process::Command;
use reverie_process::Stdio;
let command = Command::new("ls").stdout(Stdio::null());Sourcepub fn stderr<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
pub fn stderr<T: Into<Stdio>>(&mut self, cfg: T) -> &mut Self
Sets configuration for the child process’s standard error (stderr) handle.
Defaults to Stdio::inherit when used with spawn or status, and
defaults to Stdio::piped when used with output.
§Examples
Basic usage:
use reverie_process::Command;
use reverie_process::Stdio;
let command = Command::new("ls").stderr(Stdio::null());Sourcepub fn chroot<P: AsRef<Path>>(&mut self, chroot: P) -> &mut Self
pub fn chroot<P: AsRef<Path>>(&mut self, chroot: P) -> &mut Self
Changes the root directory of the calling process to the specified path. This directory will be inherited by all child processes of the calling process.
Note that changing the root directory may cause the program to not be found. As such, the program path should be relative to this directory.
Unshares parts of the process execution context that are normally shared with the parent process. This is useful for executing the child process in a new namespace.
Sourcepub unsafe fn pre_exec<F>(&mut self, f: F) -> &mut Self
pub unsafe fn pre_exec<F>(&mut self, f: F) -> &mut Self
Schedules a closure to be run just before the exec function is invoked.
The closure is allowed to return an I/O error whose OS error code will be communicated back to the parent and returned as an error from when the spawn was requested.
Multiple closures can be registered and they will be called in order of
their registration. If a closure returns Err then no further closures
will be called and the spawn operation will immediately return with a
failure.
§Safety
This closure will be run in the context of the child process after a
fork. This primarily means that any modifications made to memory on
behalf of this closure will not be visible to the parent process.
This is often a very constrained environment where normal operations like
malloc or acquiring a mutex are not guaranteed to work (due to other
threads perhaps still running when the fork was run).
This also means that all resources such as file descriptors and memory-mapped regions got duplicated. It is your responsibility to make sure that the closure does not violate library invariants by making invalid use of these duplicates.
When this closure is run, aspects such as the stdio file descriptors and working directory have successfully been changed, so output to these locations may not appear where intended.
Sourcepub fn get_program(&self) -> &OsStr
pub fn get_program(&self) -> &OsStr
Returns the path to the program that was given to Command::new.
§Examples
use reverie_process::Command;
let cmd = Command::new("echo");
assert_eq!(cmd.get_program(), "echo");Sourcepub fn get_current_dir(&self) -> Option<&Path>
pub fn get_current_dir(&self) -> Option<&Path>
Returns the working directory for the child process.
This returns None if the working directory will not be changed.
Sourcepub fn get_envs(&self) -> impl Iterator<Item = (&OsStr, Option<&OsStr>)>
pub fn get_envs(&self) -> impl Iterator<Item = (&OsStr, Option<&OsStr>)>
Returns an iterator of the environment variables that will be set when the process is spawned. Note that this does not include any environment variables inherited from the parent process.
Sourcepub fn get_captured_envs(&self) -> BTreeMap<OsString, OsString>
pub fn get_captured_envs(&self) -> BTreeMap<OsString, OsString>
Returns a mapping of all environment variables that the new child process will inherit.
Sourcepub fn get_env<K: AsRef<OsStr>>(&self, env: K) -> Option<Cow<'_, OsStr>>
pub fn get_env<K: AsRef<OsStr>>(&self, env: K) -> Option<Cow<'_, OsStr>>
Gets an environment variable. If the child process is to inherit this environment variable from the current process, then this returns the current process’s environment variable unless it is to be overridden.
Sourcepub fn map_uid(&mut self, inside_uid: uid_t, outside_uid: uid_t) -> &mut Self
pub fn map_uid(&mut self, inside_uid: uid_t, outside_uid: uid_t) -> &mut Self
Maps one user ID to another.
Implies Namespace::USER.
§Example
This is can be used to gain CAP_SYS_ADMIN privileges in the user
namespace by mapping the root user inside the container to the current
user outside of the container.
use reverie_process::Command;
let command = Command::new("ls").map_uid(1, unsafe { libc::getuid() });§Implementation
This modifies /proc/{pid}/uid_map where {pid} is the PID of the child
process. See user_namespaces(7) for more details.
Sourcepub fn map_uid_range(
&mut self,
starting_inside_uid: uid_t,
starting_outside_uid: uid_t,
count: u32,
) -> &mut Self
pub fn map_uid_range( &mut self, starting_inside_uid: uid_t, starting_outside_uid: uid_t, count: u32, ) -> &mut Self
Maps potentially many user IDs inside the new user namespace to user IDs outside of the user namespace.
Implies Namespace::USER.
§Implementation
This modifies /proc/{pid}/uid_map where {pid} is the PID of the child
process. See user_namespaces(7) for more details.
Sourcepub fn map_root(&mut self) -> &mut Self
pub fn map_root(&mut self) -> &mut Self
Convience function for mapping root (inside the container) to the current user ID (outside the container). This is useful for gaining new capabilities inside the container, such as being able to mount file systems.
Implies Namespace::USER.
This is the same as:
use reverie_process::Command;
let command = Command::new("ls")
.map_uid(0, unsafe { libc::geteuid() })
.map_gid(0, unsafe { libc::getegid() });Sourcepub fn map_gid(&mut self, inside_gid: gid_t, outside_gid: gid_t) -> &mut Self
pub fn map_gid(&mut self, inside_gid: gid_t, outside_gid: gid_t) -> &mut Self
Maps one group ID to another.
Implies Namespace::USER.
§Implementation
This modifies /proc/{pid}/gid_map where {pid} is the PID of the child
process. See user_namespaces(7) for more details.
Sourcepub fn map_gid_range(
&mut self,
starting_inside_gid: gid_t,
starting_outside_gid: gid_t,
count: u32,
) -> &mut Self
pub fn map_gid_range( &mut self, starting_inside_gid: gid_t, starting_outside_gid: gid_t, count: u32, ) -> &mut Self
Maps potentially many group IDs inside the new user namespace to group IDs outside of the user namespace.
Implies Namespace::USER.
§Implementation
This modifies /proc/{pid}/gid_map where {pid} is the PID of the child
process. See user_namespaces(7) for more details.
Sourcepub fn hostname<S: Into<OsString>>(&mut self, hostname: S) -> &mut Self
pub fn hostname<S: Into<OsString>>(&mut self, hostname: S) -> &mut Self
Sets the hostname of the container.
Implies Namespace::UTS, which requires CAP_SYS_ADMIN.
use reverie_process::Command;
let command = Command::new("cat")
.arg("/proc/sys/kernel/hostname")
.map_root()
.hostname("foobar.local");Sourcepub fn domainname<S: Into<OsString>>(&mut self, domainname: S) -> &mut Self
pub fn domainname<S: Into<OsString>>(&mut self, domainname: S) -> &mut Self
Sets the domain name of the container.
Implies Namespace::UTS, which requires CAP_SYS_ADMIN.
§Example
use reverie_process::Command;
let command = Command::new("cat")
.arg("/proc/sys/kernel/domainname")
.map_root()
.domainname("foobar");Sourcepub fn get_hostname(&self) -> Option<&OsStr>
pub fn get_hostname(&self) -> Option<&OsStr>
Gets the hostname of the container.
Sourcepub fn get_domainname(&self) -> Option<&OsStr>
pub fn get_domainname(&self) -> Option<&OsStr>
Gets the domainname of the container.
Sourcepub fn mount(&mut self, mount: Mount) -> &mut Self
pub fn mount(&mut self, mount: Mount) -> &mut Self
Adds a file system to be mounted. Note that these are mounted in the same order as given.
Implies Namespace::MOUNT. Note that Namespace::USER should also have
been set and map_uid should have been called in order to gain the
privileges required to mount.
Sourcepub fn mounts<I>(&mut self, mounts: I) -> &mut Selfwhere
I: IntoIterator<Item = Mount>,
pub fn mounts<I>(&mut self, mounts: I) -> &mut Selfwhere
I: IntoIterator<Item = Mount>,
Adds multiple mounts.
Sourcepub fn local_networking_only(&mut self) -> &mut Self
pub fn local_networking_only(&mut self) -> &mut Self
Sets up the container to have local networking only. This will prevent any network communication to the outside world.
Implies Namespace::NETWORK and Namespace::MOUNT.
This also causes a fresh /sys to be mounted to avoid seeing the host
network interfaces in /sys/class/net.
Sourcepub fn seccomp(&mut self, filter: Filter) -> &mut Self
pub fn seccomp(&mut self, filter: Filter) -> &mut Self
Sets the seccomp filter. The filter is loaded immediately before execve
and after all pre_exec callbacks have been executed. Thus, you will
still be able to call filtered syscalls from pre_exec callbacks.
Sourcepub fn seccomp_notify(&mut self) -> &mut Self
pub fn seccomp_notify(&mut self) -> &mut Self
Indicates that we want to listen for seccomp events using seccomp_unotify(2).
If this is set, the seccomp listener file descriptor will be accessible
via the Child.
Sourcepub fn pty(&mut self, child: PtyChild) -> &mut Self
pub fn pty(&mut self, child: PtyChild) -> &mut Self
Sets the controlling pseudoterminal for the child process).
In the child process, this has the effect of:
- Creating a new session (with
setsid()). - Using an
ioctlto set the controlling terminal. - Setting this file descriptor as the stdio streams.
NOTE: Since this modifies the stdio streams, calling this will reset
Self::stdin, Self::stdout, and Self::stderr back to
Stdio::inherit().
Sourcepub fn find_program(&self) -> Result<PathBuf>
pub fn find_program(&self) -> Result<PathBuf>
Finds the path to the program.
Source§impl Command
impl Command
Sourcepub fn spawn(&mut self) -> Result<Child, Error>
pub fn spawn(&mut self) -> Result<Child, Error>
Executes the command as a child process, returning a handle to it.
By default, stdin, stdout and stderr are inherited from the parent.
Sourcepub fn spawn_with<F>(&mut self, onfail: F) -> Result<Child, Error>
pub fn spawn_with<F>(&mut self, onfail: F) -> Result<Child, Error>
Spawn the child with helper functions. The onfail callback runs in the
child process if an error occurs during execution of the process. The
wait function can be used to wait for the child to fully start up and
to transform it into another type.
Source§impl Command
impl Command
Sourcepub fn from_std_lossy(cmd: &Command) -> Command
pub fn from_std_lossy(cmd: &Command) -> Command
Converts std::process::Command into Command. Note that this is a
very basic and lossy conversion.
This only preserves the
- program path,
- arguments,
- environment variables,
- and working directory.
§Caveats
Since std::process::Command is rather opaque and doesn’t provide
access to all fields, this will not preserve:
- stdio handles,
env_clear,- any
pre_execcallbacks, arg0(if not the same asprogram),uid,gid, orgroups.
Sourcepub fn try_into_std(self) -> Result<Command>
pub fn try_into_std(self) -> Result<Command>
Converts this command to std::process::Command.
This fails if the command contains container configuration that cannot
be represented by std::process::Command, rather than silently
discarding that configuration. This includes namespaces, mounts,
seccomp filters, pseudoterminals, and CPU affinity.
Sourcepub fn into_std_lossy(self) -> Command
pub fn into_std_lossy(self) -> Command
Converts this command to std::process::Command, refusing to discard
any container configuration.
This compatibility shim preserves the former return type for callers
whose commands are representable. It panics instead of silently losing
unsupported configuration. New callers should use Self::try_into_std
to handle that refusal explicitly.