ca281c9395
To allow improving the implementation and interface in this repo and move it back into redox-scheme later.
72 lines
1.7 KiB
Rust
72 lines
1.7 KiB
Rust
use std::collections::{BTreeMap, btree_map};
|
|
use std::num::Wrapping;
|
|
|
|
use syscall::{EBADF, Error, Result};
|
|
|
|
mod readiness_based;
|
|
|
|
pub use readiness_based::ReadinessBased;
|
|
|
|
pub struct HandleMap<T> {
|
|
handles: BTreeMap<usize, T>,
|
|
next_id: Wrapping<usize>,
|
|
}
|
|
|
|
impl<T> HandleMap<T> {
|
|
pub const fn new() -> Self {
|
|
HandleMap {
|
|
handles: BTreeMap::new(),
|
|
next_id: Wrapping(1),
|
|
}
|
|
}
|
|
|
|
pub fn insert(&mut self, handle: T) -> usize {
|
|
let id = self.next_id;
|
|
|
|
// If we've looped round there's a small chance that the file descriptor still exists, so loop till we get one that doesn't
|
|
self.next_id += Wrapping(1);
|
|
loop {
|
|
if !self.handles.contains_key(&self.next_id.0) {
|
|
break;
|
|
} else {
|
|
self.next_id += Wrapping(1);
|
|
}
|
|
}
|
|
|
|
self.handles.insert(id.0, handle);
|
|
id.0
|
|
}
|
|
|
|
pub fn remove(&mut self, id: usize) -> Option<T> {
|
|
self.handles.remove(&id)
|
|
}
|
|
|
|
pub fn get(&self, id: usize) -> Result<&T> {
|
|
self.handles.get(&id).ok_or(Error::new(EBADF))
|
|
}
|
|
|
|
pub fn get_mut(&mut self, id: usize) -> Result<&mut T> {
|
|
self.handles.get_mut(&id).ok_or(Error::new(EBADF))
|
|
}
|
|
|
|
pub fn iter(&self) -> btree_map::Iter<'_, usize, T> {
|
|
self.handles.iter()
|
|
}
|
|
|
|
pub fn iter_mut(&mut self) -> btree_map::IterMut<'_, usize, T> {
|
|
self.handles.iter_mut()
|
|
}
|
|
|
|
pub fn keys(&self) -> btree_map::Keys<'_, usize, T> {
|
|
self.handles.keys()
|
|
}
|
|
|
|
pub fn values(&self) -> btree_map::Values<'_, usize, T> {
|
|
self.handles.values()
|
|
}
|
|
|
|
pub fn values_mut(&mut self) -> btree_map::ValuesMut<'_, usize, T> {
|
|
self.handles.values_mut()
|
|
}
|
|
}
|