sys: use a BTreeMap for MountInfo internally
Since the only reasonable access is by mount "id" and they don't need to be consecutive (but they are numeric), use a BTreeMap for MountInfo. Signed-off-by: Wolfgang Bumiller <w.bumiller@proxmox.com>
This commit is contained in:
parent
4e27ec9eb1
commit
bd4a6c5b8b
@ -1,6 +1,8 @@
|
|||||||
//! `/proc/PID/mountinfo` handling.
|
//! `/proc/PID/mountinfo` handling.
|
||||||
|
|
||||||
|
use std::collections::BTreeMap;
|
||||||
use std::ffi::{OsStr, OsString};
|
use std::ffi::{OsStr, OsString};
|
||||||
|
use std::iter::FromIterator;
|
||||||
use std::os::unix::ffi::OsStrExt;
|
use std::os::unix::ffi::OsStrExt;
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
use std::str::FromStr;
|
use std::str::FromStr;
|
||||||
@ -10,7 +12,7 @@ use nix::sys::stat;
|
|||||||
use nix::unistd::Pid;
|
use nix::unistd::Pid;
|
||||||
|
|
||||||
/// A mount ID as found within `/proc/PID/mountinfo`.
|
/// A mount ID as found within `/proc/PID/mountinfo`.
|
||||||
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
|
#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
|
||||||
#[repr(transparent)]
|
#[repr(transparent)]
|
||||||
pub struct MountId(usize);
|
pub struct MountId(usize);
|
||||||
|
|
||||||
@ -162,14 +164,14 @@ impl Entry {
|
|||||||
// TODO: Add some structure to this? Eg. sort by parent/child relation? Make a tree?
|
// TODO: Add some structure to this? Eg. sort by parent/child relation? Make a tree?
|
||||||
/// Mount info found in `/proc/PID/mountinfo`.
|
/// Mount info found in `/proc/PID/mountinfo`.
|
||||||
pub struct MountInfo {
|
pub struct MountInfo {
|
||||||
entries: Vec<Entry>,
|
entries: BTreeMap<MountId, Entry>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// An iterator over entries in a `MountInfo`.
|
/// An iterator over entries in a `MountInfo`.
|
||||||
pub type Iter<'a> = std::slice::Iter<'a, Entry>;
|
pub type Iter<'a> = std::collections::btree_map::Iter<'a, MountId, Entry>;
|
||||||
|
|
||||||
/// An iterator over mutable entries in a `MountInfo`.
|
/// An iterator over mutable entries in a `MountInfo`.
|
||||||
pub type IterMut<'a> = std::slice::IterMut<'a, Entry>;
|
pub type IterMut<'a> = std::collections::btree_map::IterMut<'a, MountId, Entry>;
|
||||||
|
|
||||||
impl MountInfo {
|
impl MountInfo {
|
||||||
/// Read the current mount point information.
|
/// Read the current mount point information.
|
||||||
@ -192,6 +194,8 @@ impl MountInfo {
|
|||||||
},
|
},
|
||||||
)?;
|
)?;
|
||||||
|
|
||||||
|
let entries = BTreeMap::from_iter(entries.into_iter().map(|entry| (entry.id, entry)));
|
||||||
|
|
||||||
Ok(Self { entries })
|
Ok(Self { entries })
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -209,7 +213,7 @@ impl MountInfo {
|
|||||||
where
|
where
|
||||||
PathBuf: PartialEq<P>,
|
PathBuf: PartialEq<P>,
|
||||||
{
|
{
|
||||||
self.iter().any(|entry| entry.mount_point == *path)
|
self.iter().any(|(_id, entry)| entry.mount_point == *path)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Check whether there exists a mount point for a specified source.
|
/// Check whether there exists a mount point for a specified source.
|
||||||
@ -218,14 +222,14 @@ impl MountInfo {
|
|||||||
OsString: PartialEq<T>,
|
OsString: PartialEq<T>,
|
||||||
{
|
{
|
||||||
self.iter()
|
self.iter()
|
||||||
.filter_map(|entry| entry.mount_source.as_ref())
|
.filter_map(|(_id, entry)| entry.mount_source.as_ref())
|
||||||
.any(|s| *s == *source)
|
.any(|s| *s == *source)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl IntoIterator for MountInfo {
|
impl IntoIterator for MountInfo {
|
||||||
type Item = Entry;
|
type Item = (MountId, Entry);
|
||||||
type IntoIter = std::vec::IntoIter<Entry>;
|
type IntoIter = std::collections::btree_map::IntoIter<MountId, Entry>;
|
||||||
|
|
||||||
fn into_iter(self) -> Self::IntoIter {
|
fn into_iter(self) -> Self::IntoIter {
|
||||||
self.entries.into_iter()
|
self.entries.into_iter()
|
||||||
@ -233,7 +237,7 @@ impl IntoIterator for MountInfo {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> IntoIterator for &'a MountInfo {
|
impl<'a> IntoIterator for &'a MountInfo {
|
||||||
type Item = &'a Entry;
|
type Item = (&'a MountId, &'a Entry);
|
||||||
type IntoIter = Iter<'a>;
|
type IntoIter = Iter<'a>;
|
||||||
|
|
||||||
fn into_iter(self) -> Self::IntoIter {
|
fn into_iter(self) -> Self::IntoIter {
|
||||||
@ -242,7 +246,7 @@ impl<'a> IntoIterator for &'a MountInfo {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> IntoIterator for &'a mut MountInfo {
|
impl<'a> IntoIterator for &'a mut MountInfo {
|
||||||
type Item = &'a mut Entry;
|
type Item = (&'a MountId, &'a mut Entry);
|
||||||
type IntoIter = IterMut<'a>;
|
type IntoIter = IterMut<'a>;
|
||||||
|
|
||||||
fn into_iter(self) -> Self::IntoIter {
|
fn into_iter(self) -> Self::IntoIter {
|
||||||
@ -250,6 +254,20 @@ impl<'a> IntoIterator for &'a mut MountInfo {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl std::ops::Deref for MountInfo {
|
||||||
|
type Target = BTreeMap<MountId, Entry>;
|
||||||
|
|
||||||
|
fn deref(&self) -> &Self::Target {
|
||||||
|
&self.entries
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl std::ops::DerefMut for MountInfo {
|
||||||
|
fn deref_mut(&mut self) -> &mut Self::Target {
|
||||||
|
&mut self.entries
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_entry() {
|
fn test_entry() {
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user