fix: storage tables grow (handles, open files, encrypted opens, grants: Slots/Vec, no 8/16 caps; release follows all narrowed grants); storage says FULL, init spawn STORAGE_BUSY (was NOT_FOUND), pm BUSY; cap slots per process 64 -> 255
This commit is contained in:
55
crates/servers/storage-server/src/slots.rs
Normal file
55
crates/servers/storage-server/src/slots.rs
Normal file
@@ -0,0 +1,55 @@
|
||||
//! A table that grows as it fills, bounded by storage's memory rather than
|
||||
//! a count: an entry keeps its index for life (a handle names it), and a
|
||||
//! freed index is reused first. At most what a `FileHandle` can name.
|
||||
|
||||
use alloc::vec::Vec;
|
||||
|
||||
pub const MAX: usize = u16::MAX as usize + 1;
|
||||
|
||||
pub struct Slots<T>(Vec<Option<T>>);
|
||||
|
||||
impl<T> Slots<T> {
|
||||
pub const fn new() -> Self {
|
||||
Self(Vec::new())
|
||||
}
|
||||
|
||||
/// The index the next entry would get, if there is room for one.
|
||||
pub fn free(&self) -> Option<usize> {
|
||||
let i = self.0.iter().position(Option::is_none).unwrap_or(self.0.len());
|
||||
(i < MAX).then_some(i)
|
||||
}
|
||||
|
||||
/// Puts `value` at `index`, growing to it.
|
||||
pub fn put(&mut self, index: usize, value: T) {
|
||||
if index >= MAX {
|
||||
return;
|
||||
}
|
||||
if self.0.len() <= index {
|
||||
self.0.resize_with(index + 1, || None);
|
||||
}
|
||||
self.0[index] = Some(value);
|
||||
}
|
||||
|
||||
pub fn get(&self, index: usize) -> Option<&T> {
|
||||
self.0.get(index)?.as_ref()
|
||||
}
|
||||
|
||||
pub fn get_mut(&mut self, index: usize) -> Option<&mut T> {
|
||||
self.0.get_mut(index)?.as_mut()
|
||||
}
|
||||
|
||||
pub fn take(&mut self, index: usize) -> Option<T> {
|
||||
self.0.get_mut(index)?.take()
|
||||
}
|
||||
|
||||
/// Every entry, with its index.
|
||||
pub fn iter(&self) -> impl Iterator<Item = (usize, &T)> {
|
||||
self.0.iter().enumerate().filter_map(|(i, v)| v.as_ref().map(|v| (i, v)))
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> Default for Slots<T> {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user