Skip to content

Commit

Permalink
Rename MntNamespace to Namespace
Browse files Browse the repository at this point in the history
This prepares adding support for user namespace.
  • Loading branch information
nbdd0121 committed Oct 3, 2024
1 parent 0af2316 commit 75e472d
Show file tree
Hide file tree
Showing 4 changed files with 22 additions and 16 deletions.
3 changes: 3 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -30,3 +30,6 @@ walkdir = "2"

[workspace]
exclude = ["cgroup_device_filter"]

[profile.release]
debug = "line-tables-only"
3 changes: 3 additions & 0 deletions shell.nix
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,8 @@ pkgs.mkShell {

# For llvm-objdump
llvmPackages.bintools

# To aid testing
runc
];
}
11 changes: 6 additions & 5 deletions src/runc/container.rs
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ impl Container {
}

pub async fn mknod(&self, node: &Path, (major, minor): (u32, u32)) -> Result<()> {
crate::util::namespace::MntNamespace::of_pid(self.pid)?.enter(|| {
crate::util::namespace::Namespace::of_pid(self.pid)?.enter(|| {
if let Some(parent) = node.parent() {
let _ = std::fs::create_dir_all(parent);
}
Expand All @@ -129,24 +129,25 @@ impl Container {
rustix::fs::chown(node, Some(self.uid), Some(self.gid))?;
}
Ok(())
})?
})
}

pub async fn symlink(&self, source: &Path, link: &Path) -> Result<()> {
crate::util::namespace::MntNamespace::of_pid(self.pid)?.enter(|| {
crate::util::namespace::Namespace::of_pid(self.pid)?.enter(|| {
if let Some(parent) = link.parent() {
let _ = std::fs::create_dir_all(parent);
}
let _ = std::fs::remove_file(link);
std::os::unix::fs::symlink(source, link)?;
// No need to chown symlink. Permission is determined by the target.
Ok(())
})?
})
}

pub async fn rm(&self, node: &Path) -> Result<()> {
crate::util::namespace::MntNamespace::of_pid(self.pid)?.enter(|| {
crate::util::namespace::Namespace::of_pid(self.pid)?.enter(|| {
let _ = std::fs::remove_file(node);
Ok(())
})
}

Expand Down
21 changes: 10 additions & 11 deletions src/util/namespace.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,35 +5,34 @@ use anyhow::Result;
use rustix::process::Pid;
use rustix::thread::{LinkNameSpaceType, UnshareFlags};

pub struct MntNamespace {
fd: File,
pub struct Namespace {
mnt_fd: File,
}

impl MntNamespace {
impl Namespace {
/// Open the mount namespace of a process.
pub fn of_pid(pid: Pid) -> Result<MntNamespace> {
let path = format!("/proc/{}/ns/mnt", pid.as_raw_nonzero());
let fd = File::open(path)?;
Ok(MntNamespace { fd })
pub fn of_pid(pid: Pid) -> Result<Namespace> {
let mnt_fd = File::open(format!("/proc/{}/ns/mnt", pid.as_raw_nonzero()))?;
Ok(Namespace { mnt_fd })
}

/// Enter the mount namespace.
pub fn enter<T: Send, F: FnOnce() -> T + Send>(&self, f: F) -> Result<T> {
pub fn enter<F: FnOnce() -> Result<()> + Send>(&self, f: F) -> Result<()> {
// To avoid messing with rest of the process, we do everything in a new thread.
// Use scoped thread to avoid 'static bound (we need to access fd).
std::thread::scope(|scope| {
scope
.spawn(|| -> Result<T> {
.spawn(|| -> Result<()> {
// Unshare FS for this specific thread so we can switch to another namespace.
// Not doing this will cause EINVAL when switching to namespaces.
rustix::thread::unshare(UnshareFlags::FS)?;

// Switch this particular thread to the container's mount namespace.
rustix::thread::move_into_link_name_space(
self.fd.as_fd(),
self.mnt_fd.as_fd(),
Some(LinkNameSpaceType::Mount),
)?;
Ok(f())
Ok(f()?)
})
.join()
.map_err(|_| anyhow::anyhow!("work thread panicked"))?
Expand Down

0 comments on commit 75e472d

Please sign in to comment.