use anyhow::{Context, Result};
use nix::{
sched::{self, CloneFlags},
unistd::Pid,
};
use oci_spec::runtime::LinuxNamespace;
use procfs::process::{ProcState, Process};
use crate::linux::namespace;
pub fn clone_child(
namespace_list: &[LinuxNamespace],
child_fn: impl FnMut() -> isize,
) -> Result<Pid> {
const STACK_SIZE: usize = 4 * 1024 * 1024;
let mut stack: [u8; STACK_SIZE] = [0; STACK_SIZE];
let clone_flags = namespace_list
.iter()
.map(namespace::linux_namespace_to_clone_flags)
.reduce(|flag_1, flag_2| flag_1 | flag_2)
.unwrap_or(CloneFlags::empty());
let pid = sched::clone(Box::new(child_fn), &mut stack, clone_flags, None)
.context("failed to clone the container process")?;
Ok(pid)
}
pub fn inspect_process(pid: i32) -> Result<ProcState> {
let process = Process::new(pid).context(format!("failed to inspect the process {}", pid))?;
let process_stat = process
.stat()
.context(format!("failed to inspect the status of process {}", pid))?;
let state = process_stat
.state()
.context(format!("failed to inspect the state of process {}", pid))?;
Ok(state)
}