about summary refs log tree commit diff
path: root/library/std/src/os/unix/process.rs
diff options
context:
space:
mode:
authorJosh Triplett <josh@joshtriplett.org>2025-02-27 22:00:15 +0000
committerJosh Triplett <josh@joshtriplett.org>2025-05-20 18:25:05 +0200
commita3cf6f640828647e34afe96a626b3b4f6bbb22b1 (patch)
treed358007b1f6aa3b6d79eaac3abe480c2f0958b1a /library/std/src/os/unix/process.rs
parentf8e9e7636aabcbc29345d9614432d15b3c0c4ec7 (diff)
downloadrust-a3cf6f640828647e34afe96a626b3b4f6bbb22b1.tar.gz
rust-a3cf6f640828647e34afe96a626b3b4f6bbb22b1.zip
Add `std::os::unix::process::CommandExt::chroot` to safely chroot a child process
This adds a `chroot` method to the `CommandExt` extension trait for the
`Command` builder, to set a directory to chroot into. This will chroot
the child process into that directory right before calling chdir for the
`Command`'s working directory.

To avoid allowing a process to have a working directory outside of the
chroot, if the `Command` does not yet have a working directory set,
`chroot` will set its working directory to "/".
Diffstat (limited to 'library/std/src/os/unix/process.rs')
-rw-r--r--library/std/src/os/unix/process.rs16
1 files changed, 16 insertions, 0 deletions
diff --git a/library/std/src/os/unix/process.rs b/library/std/src/os/unix/process.rs
index 7c3fa7d6507..27866badfbe 100644
--- a/library/std/src/os/unix/process.rs
+++ b/library/std/src/os/unix/process.rs
@@ -8,6 +8,7 @@ use cfg_if::cfg_if;
 
 use crate::ffi::OsStr;
 use crate::os::unix::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, OwnedFd, RawFd};
+use crate::path::Path;
 use crate::sealed::Sealed;
 use crate::sys_common::{AsInner, AsInnerMut, FromInner, IntoInner};
 use crate::{io, process, sys};
@@ -197,6 +198,16 @@ pub trait CommandExt: Sealed {
     /// ```
     #[stable(feature = "process_set_process_group", since = "1.64.0")]
     fn process_group(&mut self, pgroup: i32) -> &mut process::Command;
+
+    /// Set the root of the child process. This calls `chroot` in the child process before executing
+    /// the command.
+    ///
+    /// This happens before changing to the directory specified with `Command::current_dir`, and
+    /// that directory will be relative to the new root. If no directory has been specified with
+    /// `Command::current_dir`, this will set the directory to `/`, to avoid leaving the current
+    /// directory outside the chroot.
+    #[unstable(feature = "process_chroot", issue = "none")]
+    fn chroot<P: AsRef<Path>>(&mut self, dir: P) -> &mut process::Command;
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
@@ -242,6 +253,11 @@ impl CommandExt for process::Command {
         self.as_inner_mut().pgroup(pgroup);
         self
     }
+
+    fn chroot<P: AsRef<Path>>(&mut self, dir: P) -> &mut process::Command {
+        self.as_inner_mut().chroot(dir.as_ref());
+        self
+    }
 }
 
 /// Unix-specific extensions to [`process::ExitStatus`] and