diff --git a/programs/contain/src/main.rs b/programs/contain/src/main.rs index 8e22e23..2e60062 100644 --- a/programs/contain/src/main.rs +++ b/programs/contain/src/main.rs @@ -2,31 +2,66 @@ extern crate syscall; use syscall::scheme::Scheme; -use std::{env, fs, thread}; +use std::{env, fs,thread}; +use std::io::{stderr, Write}; use std::os::unix::process::CommandExt; -use std::process::Command; +use std::path::Path; +use std::process::{self, Command}; use self::chroot::ChrootScheme; mod chroot; -pub fn main() { - let mut args = env::args().skip(1); +fn usage() -> ! { + write!(stderr(), "contain [create|enter] root cmd args..\n").unwrap(); + process::exit(1); +} - let root_opt = args.next(); +fn create(root: &Path) { + let root = Path::new(root); - let cmd = args.next().unwrap_or("sh".to_string()); + println!("{}", root.display()); + fs::create_dir(root).unwrap(); - let mut names = vec![ + let mut bin = root.to_path_buf(); + bin.push("bin"); + println!("{}", bin.display()); + fs::create_dir(&bin).unwrap(); + + for entry in fs::read_dir("/bin").unwrap() { + let entry = entry.unwrap(); + let mut dest = bin.clone(); + dest.push(entry.file_name()); + println!("{} -> {}", entry.path().display(), dest.display()); + fs::copy(entry.path(), dest).unwrap(); + } + + let mut etc = root.to_path_buf(); + etc.push("etc"); + println!("{}", etc.display()); + fs::create_dir(&etc).unwrap(); + + let mut net = etc.clone(); + net.push("net"); + println!("{}", net.display()); + fs::create_dir(&net).unwrap(); + + for entry in fs::read_dir("/etc/net").unwrap() { + let entry = entry.unwrap(); + let mut dest = net.clone(); + dest.push(entry.file_name()); + println!("{} -> {}", entry.path().display(), dest.display()); + fs::copy(entry.path(), dest).unwrap(); + } +} + +fn enter(root: &Path, cmd: &str, args: &[String]) { + let names = [ "rand", "tcp", "udp" ]; - if root_opt.is_none() { - names.push("file"); - } - let mut name_ptrs = Vec::new(); for name in names.iter() { name_ptrs.push([name.as_ptr() as usize, name.len()]); @@ -34,27 +69,24 @@ pub fn main() { let new_ns = syscall::mkns(&name_ptrs).unwrap(); - let root_thread = if let Some(root) = root_opt { - Some(thread::spawn(move || { - syscall::setrens(-1isize as usize, new_ns).unwrap(); - let scheme_fd = syscall::open(":file", syscall::O_CREAT | syscall::O_RDWR | syscall::O_CLOEXEC).unwrap(); - syscall::setrens(-1isize as usize, syscall::getns().unwrap()).unwrap(); + let root_canon = fs::canonicalize(root).unwrap(); + let root_thread = thread::spawn(move || { + syscall::setrens(-1isize as usize, new_ns).unwrap(); + let scheme_fd = syscall::open(":file", syscall::O_CREAT | syscall::O_RDWR | syscall::O_CLOEXEC).unwrap(); + syscall::setrens(-1isize as usize, syscall::getns().unwrap()).unwrap(); - let chroot_scheme = ChrootScheme::new(fs::canonicalize(root).unwrap()); - loop { - let mut packet = syscall::Packet::default(); - if syscall::read(scheme_fd, &mut packet).unwrap() == 0 { - break; - } - chroot_scheme.handle(&mut packet); - syscall::write(scheme_fd, &packet).unwrap(); + let chroot_scheme = ChrootScheme::new(root_canon); + loop { + let mut packet = syscall::Packet::default(); + if syscall::read(scheme_fd, &mut packet).unwrap() == 0 { + break; } + chroot_scheme.handle(&mut packet); + syscall::write(scheme_fd, &packet).unwrap(); + } - let _ = syscall::close(scheme_fd); - })) - } else { - None - }; + let _ = syscall::close(scheme_fd); + }); let pid = unsafe { syscall::clone(0).unwrap() }; if pid == 0 { @@ -88,3 +120,27 @@ pub fn main() { println!("Container {}: exit: {:X}", new_ns, status); } } + +pub fn main() { + let mut args = env::args().skip(1); + + if let Some(op) = args.next() { + match op.as_str() { + "create" => if let Some(root) = args.next() { + create(Path::new(&root)); + } else { + usage(); + }, + "enter" => if let Some(root) = args.next() { + let cmd = args.next().unwrap_or("sh".to_string()); + let args: Vec = args.collect(); + enter(Path::new(&root), &cmd, &args); + } else { + usage(); + }, + _ => usage() + } + } else { + usage(); + } +} diff --git a/programs/coreutils b/programs/coreutils index 3308c45..c043ba9 160000 --- a/programs/coreutils +++ b/programs/coreutils @@ -1 +1 @@ -Subproject commit 3308c4507cfe7c3922e41ad472d792dac864e83f +Subproject commit c043ba9089b81e805a0c98e8e9caf4a54a9603f7