Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

part of PR 340 - adding syscalls #356

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 40 additions & 9 deletions src/syscall/linux.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
//! Implements Command trait for Linux systems
use std::ffi::{CStr, OsStr};
use std::os::unix::ffi::OsStrExt;
use std::os::unix::fs::symlink;
use std::sync::Arc;
use std::{any::Any, mem, path::Path, ptr};

Expand All @@ -9,18 +10,13 @@ use caps::{errors::CapsError, CapSet, Capability, CapsHashSet};
use libc::{c_char, uid_t};
use nix::{
errno::Errno,
unistd::{fchdir, pivot_root, sethostname},
};
use nix::{fcntl::open, sched::CloneFlags};
use nix::{
fcntl::OFlag,
unistd::{Gid, Uid},
};
use nix::{
fcntl::{open, OFlag},
mount::{mount, umount2, MntFlags, MsFlags},
sched::{unshare, CloneFlags},
sys::stat::{mknod, Mode, SFlag},
unistd,
unistd::{chown, fchdir, pivot_root, sethostname, Gid, Uid},
};
use nix::{sched::unshare, sys::stat::Mode};

use oci_spec::runtime::LinuxRlimit;

Expand Down Expand Up @@ -211,4 +207,39 @@ impl Syscall for LinuxSyscall {

Ok(())
}

fn mount(
&self,
source: Option<&Path>,
target: &Path,
fstype: Option<&str>,
flags: MsFlags,
data: Option<&str>,
) -> Result<()> {
match mount(source, target, fstype, flags, data) {
Ok(_) => Ok(()),
Err(e) => bail!("Failed to mount {:?}", e),
}
}

fn symlink(&self, original: &Path, link: &Path) -> Result<()> {
match symlink(original, link) {
Ok(_) => Ok(()),
Err(e) => bail!("Failed to symlink {:?}", e),
}
}

fn mknod(&self, path: &Path, kind: SFlag, perm: Mode, dev: u64) -> Result<()> {
match mknod(path, kind, perm, dev) {
Ok(_) => Ok(()),
Err(e) => bail!("Failed to mknod {:?}", e),
}
}

fn chown(&self, path: &Path, owner: Option<Uid>, group: Option<Gid>) -> Result<()> {
match chown(path, owner, group) {
Ok(_) => Ok(()),
Err(e) => bail!("Failed to chown {:?}", e),
}
}
}
13 changes: 13 additions & 0 deletions src/syscall/syscall.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@ use std::{any::Any, ffi::OsStr, path::Path, sync::Arc};
use anyhow::Result;
use caps::{errors::CapsError, CapSet, CapsHashSet};
use nix::{
mount::MsFlags,
sched::CloneFlags,
sys::stat::{Mode, SFlag},
unistd::{Gid, Uid},
};

Expand All @@ -27,6 +29,17 @@ pub trait Syscall {
fn set_hostname(&self, hostname: &str) -> Result<()>;
fn set_rlimit(&self, rlimit: &LinuxRlimit) -> Result<()>;
fn get_pwuid(&self, uid: u32) -> Option<Arc<OsStr>>;
fn mount(
&self,
source: Option<&Path>,
target: &Path,
fstype: Option<&str>,
flags: MsFlags,
data: Option<&str>,
) -> Result<()>;
fn symlink(&self, original: &Path, link: &Path) -> Result<()>;
fn mknod(&self, path: &Path, kind: SFlag, perm: Mode, dev: u64) -> Result<()>;
fn chown(&self, path: &Path, owner: Option<Uid>, group: Option<Gid>) -> Result<()>;
}

pub fn create_syscall() -> Box<dyn Syscall> {
Expand Down
113 changes: 108 additions & 5 deletions src/syscall/test.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,56 @@
use std::{any::Any, cell::RefCell, ffi::OsStr, sync::Arc};
use std::{
any::Any,
cell::RefCell,
ffi::OsStr,
path::{Path, PathBuf},
sync::Arc,
};

use caps::{errors::CapsError, CapSet, CapsHashSet};
use nix::sched::CloneFlags;
use nix::{
mount::MsFlags,
sched::CloneFlags,
sys::stat::{Mode, SFlag},
unistd::{Gid, Uid},
};

use oci_spec::runtime::LinuxRlimit;

use super::Syscall;

#[derive(Clone, PartialEq, Eq, Debug)]
pub struct MountArgs {
pub source: Option<PathBuf>,
pub target: PathBuf,
pub fstype: Option<String>,
pub flags: MsFlags,
pub data: Option<String>,
}

#[derive(Clone, PartialEq, Eq, Debug)]
pub struct MknodArgs {
pub path: PathBuf,
pub kind: SFlag,
pub perm: Mode,
pub dev: u64,
}

#[derive(Clone, PartialEq, Eq, Debug)]
pub struct ChownArgs {
pub path: PathBuf,
pub owner: Option<Uid>,
pub group: Option<Gid>,
}

#[derive(Clone)]
pub struct TestHelperSyscall {
set_ns_args: RefCell<Vec<(i32, CloneFlags)>>,
unshare_args: RefCell<Vec<CloneFlags>>,
set_capability_args: RefCell<Vec<(CapSet, CapsHashSet)>>,
mount_args: RefCell<Vec<MountArgs>>,
symlink_args: RefCell<Vec<(PathBuf, PathBuf)>>,
mknod_args: RefCell<Vec<MknodArgs>>,
chown_args: RefCell<Vec<ChownArgs>>,
}

impl Default for TestHelperSyscall {
Expand All @@ -19,6 +59,10 @@ impl Default for TestHelperSyscall {
set_ns_args: RefCell::new(vec![]),
unshare_args: RefCell::new(vec![]),
set_capability_args: RefCell::new(vec![]),
mount_args: RefCell::new(vec![]),
symlink_args: RefCell::new(vec![]),
mknod_args: RefCell::new(vec![]),
chown_args: RefCell::new(vec![]),
}
}
}
Expand All @@ -28,7 +72,7 @@ impl Syscall for TestHelperSyscall {
self
}

fn pivot_rootfs(&self, _path: &std::path::Path) -> anyhow::Result<()> {
fn pivot_rootfs(&self, _path: &Path) -> anyhow::Result<()> {
unimplemented!()
}

Expand All @@ -38,7 +82,7 @@ impl Syscall for TestHelperSyscall {
Ok(())
}

fn set_id(&self, _uid: nix::unistd::Uid, _gid: nix::unistd::Gid) -> anyhow::Result<()> {
fn set_id(&self, _uid: Uid, _gid: Gid) -> anyhow::Result<()> {
unimplemented!()
}

Expand All @@ -65,9 +109,52 @@ impl Syscall for TestHelperSyscall {
todo!()
}

fn chroot(&self, _: &std::path::Path) -> anyhow::Result<()> {
fn chroot(&self, _: &Path) -> anyhow::Result<()> {
todo!()
}

fn mount(
&self,
source: Option<&Path>,
target: &Path,
fstype: Option<&str>,
flags: MsFlags,
data: Option<&str>,
) -> anyhow::Result<()> {
self.mount_args.borrow_mut().push(MountArgs {
source: source.map(|x| x.to_owned()),
target: target.to_owned(),
fstype: fstype.map(|x| x.to_owned()),
flags,
data: data.map(|x| x.to_owned()),
});
Ok(())
}

fn symlink(&self, original: &Path, link: &Path) -> anyhow::Result<()> {
self.symlink_args
.borrow_mut()
.push((original.to_path_buf(), link.to_path_buf()));
Ok(())
}

fn mknod(&self, path: &Path, kind: SFlag, perm: Mode, dev: u64) -> anyhow::Result<()> {
self.mknod_args.borrow_mut().push(MknodArgs {
path: path.to_path_buf(),
kind,
perm,
dev,
});
Ok(())
}
fn chown(&self, path: &Path, owner: Option<Uid>, group: Option<Gid>) -> anyhow::Result<()> {
self.chown_args.borrow_mut().push(ChownArgs {
path: path.to_path_buf(),
owner,
group,
});
Ok(())
}
}

impl TestHelperSyscall {
Expand All @@ -82,4 +169,20 @@ impl TestHelperSyscall {
pub fn get_set_capability_args(&self) -> Vec<(CapSet, CapsHashSet)> {
self.set_capability_args.borrow_mut().clone()
}

pub fn get_mount_args(&self) -> Vec<MountArgs> {
self.mount_args.borrow_mut().clone()
}

pub fn get_symlink_args(&self) -> Vec<(PathBuf, PathBuf)> {
self.symlink_args.borrow_mut().clone()
}

pub fn get_mknod_args(&self) -> Vec<MknodArgs> {
self.mknod_args.borrow_mut().clone()
}

pub fn get_chown_args(&self) -> Vec<ChownArgs> {
self.chown_args.borrow_mut().clone()
}
}