use nix::{
mount::{mount, MsFlags},
unistd,
};
use proc_mounts::MountIter;
use slog::info;
use std::{fs::create_dir_all, path::Path};
use crate::error::OxidebpfError;
use crate::LOGGER;
pub fn mount_point() -> Option<String> {
let mount_iter = match MountIter::new() {
Ok(mount_iter) => mount_iter,
Err(e) => {
info!(LOGGER.0, "failed to create MountIter: {}", e.to_string());
return None;
}
};
mount_iter
.flatten()
.find(|m| m.fstype == "debugfs")
.map(|m| m.dest.into_os_string().into_string().unwrap_or_default())
}
pub fn mount_if_missing(mount_location: &str) -> Result<(), OxidebpfError> {
if mount_point().is_some() {
return Ok(());
}
let path = Path::new(mount_location);
if !path.exists() {
if let Err(e) = create_dir_all(path)
.map_err(|_e| OxidebpfError::FileIOError)
.and_then(|_| {
unistd::chown(path, Some(unistd::getuid()), Some(unistd::getgid())).map_err(|_| {
OxidebpfError::LinuxError(
"chown".to_string(),
nix::errno::from_i32(nix::errno::errno()),
)
})
})
{
info!(
LOGGER.0,
"failure to create mount point directory: {}",
e.to_string()
);
}
}
mount(
Some("debugfs"),
mount_location,
Some("debugfs"),
MsFlags::MS_NOSUID | MsFlags::MS_NODEV | MsFlags::MS_NOEXEC | MsFlags::MS_RELATIME,
None::<&str>,
)
.map_err(|_e| {
OxidebpfError::LinuxError(
"mount(debugfs)".to_string(),
nix::errno::from_i32(nix::errno::errno()),
)
})?;
Ok(())
}