pub trait CommandExt: Sealed {
// Required methods
fn uid(&mut self, id: u32) -> &mut Command;
fn gid(&mut self, id: u32) -> &mut Command;
fn groups(&mut self, groups: &[u32]) -> &mut Command;
unsafe fn pre_exec<F>(&mut self, f: F) -> &mut Command
where F: FnMut() -> Result<()> + Send + Sync + 'static;
fn exec(&mut self) -> Error;
fn arg0<S>(&mut self, arg: S) -> &mut Command
where S: AsRef<OsStr>;
fn process_group(&mut self, pgroup: i32) -> &mut Command;
// Provided method
fn before_exec<F>(&mut self, f: F) -> &mut Command
where F: FnMut() -> Result<()> + Send + Sync + 'static { ... }
}
Expand description
特定于 Unix 的 process::Command
构建器扩展。
这个 trait 是封闭的:它不能在标准库之外实现。 这是为了将来的附加方法不会破坏更改。
Required Methods§
sourcefn uid(&mut self, id: u32) -> &mut Command
fn uid(&mut self, id: u32) -> &mut Command
设置子进程的用户 ID。
这将转换为子进程中的 setuid
调用。
setuid
调用失败将导致 spawn 失败。
sourcefn groups(&mut self, groups: &[u32]) -> &mut Command
fn groups(&mut self, groups: &[u32]) -> &mut Command
setgroups
#90747)设置调用进程的补充组 ID。
在子进程中转换为 setgroups
调用。
1.34.0 · sourceunsafe fn pre_exec<F>(&mut self, f: F) -> &mut Commandwhere
F: FnMut() -> Result<()> + Send + Sync + 'static,
unsafe fn pre_exec<F>(&mut self, f: F) -> &mut Commandwhere F: FnMut() -> Result<()> + Send + Sync + 'static,
计划在 exec
函数被调用之前运行一个闭包。
允许闭包返回 I/O 错误,该错误的 OS 错误代码将被传达回父级,并从请求 spawn 开始作为错误返回。
可以注册多个闭包,并且将按照注册顺序对其进行调用。如果闭包返回 Err
,则不会再调用任何闭包,并且 spawn 操作将立即失败返回。
注意和安全
fork
之后,此闭包将在子进程的上下文中运行。这主要意味着,代表此闭包对内存所做的任何修改对于父进程都是不可见的。
这通常是一个非常受限制的环境,无法保证正常操作 (如 malloc
,通过 std::env
访问环境变量或获取互斥锁) (由于运行 fork
时可能仍在运行其他线程)。
有关更多详细信息,请参见 POSIX fork() 规范 和任何目标平台的等效文档,尤其是有关 async-signal-safety 的要求。
这也意味着所有资源 (例如文件描述符和内存映射的区域) 都被复制了。您有责任确保闭包不会因为无效使用这些副本而违反库不变量。
只有当 panic 消息的所有格式参数都可以安全格式化时,闭包中的 panic 才是安全的; 这是因为尽管 Command
在调用 pre_exec 钩子之前调用了 std::panic::always_abort
,但 panic 仍会尝试格式化 panic 消息。
运行此闭包时,标准输入输出文件描述符和工作目录等方面已成功更改,因此这些位置的输出可能不会出现在预期的位置。
1.9.0 · sourcefn exec(&mut self) -> Error
fn exec(&mut self) -> Error
通过此 Command
执行所有必需的设置,然后调用 execvp
syscall。
成功后,该函数将不会返回,否则它将返回错误,指示 exec (或 Command
的另一部分安装) 失败的原因。
exec
不返回与调用 process::exit
具有相同的含义 – 当前栈或任何其他线程栈上的析构函数都不会运行。因此,建议仅在不运行任何析构函数的时候调用 exec
。
请注意,execvp
系统调用独立保证释放所有内存,并关闭所有带有 CLOEXEC
选项的文件描述符 (默认情况下在标准库打开的所有文件描述符上设置)。
与 spawn
不同,此函数不会使用 fork
来创建一个新的子进程。但是,与 spawn 一样,标准输入输出描述符的默认行为将继承自当前进程。
Notes
如果此函数返回错误,则该进程可能在 “broken state” 中。例如,工作目录,环境变量,信号处理设置,各种 user/group 信息或标准输入输出文件描述符的各个方面可能已更改。
如果需要 “事务性生成” 来妥善处理错误,建议改用跨平台 spawn
。
1.45.0 · sourcefn arg0<S>(&mut self, arg: S) -> &mut Commandwhere
S: AsRef<OsStr>,
fn arg0<S>(&mut self, arg: S) -> &mut Commandwhere S: AsRef<OsStr>,
设置可执行参数
将第一个进程参数 argv[0]
设置为默认可执行路径以外的其他值。
1.64.0 · sourcefn process_group(&mut self, pgroup: i32) -> &mut Command
fn process_group(&mut self, pgroup: i32) -> &mut Command
设置子进程的进程组 ID (PGID)。
相当于子进程中的一个 setpgid
调用,但可能效率更高。
进程组确定哪些进程接收信号。
Examples
在终端中按 Ctrl-C 将向当前前台进程组中的所有进程发送 SIGINT。
通过在新进程组中生成 sleep
子进程,它将不会从终端接收 SIGINT。
父进程可以安装信号处理程序并按照自己的条件管理子进程。
进程组 ID 为 0 将使用进程 ID 作为 PGID。
use std::process::Command;
use std::os::unix::process::CommandExt;
Command::new("sleep")
.arg("10")
.process_group(0)
.spawn()?
.wait()?;
Run