leodos_protocols/transport/srspp/machine/receiver/utils/
bump_slab.rs1pub struct BumpSlab<const N: usize> {
3 data: [u8; N],
5 len: usize,
7}
8
9impl<const N: usize> BumpSlab<N> {
10 pub const fn new() -> Self {
12 Self {
13 data: [0u8; N],
14 len: 0,
15 }
16 }
17
18 pub fn alloc(&mut self, payload: &[u8]) -> Option<(usize, usize)> {
20 if self.len + payload.len() > N {
21 return None;
22 }
23 let offset = self.len;
24 self.data[offset..offset + payload.len()].copy_from_slice(payload);
25 self.len += payload.len();
26 Some((offset, payload.len()))
27 }
28
29 pub fn get(&self, offset: usize, len: usize) -> &[u8] {
31 &self.data[offset..offset + len]
32 }
33
34 pub fn clear(&mut self) {
36 self.len = 0;
37 }
38
39 pub fn used(&self) -> usize {
41 self.len
42 }
43}
44
45#[cfg(test)]
46mod tests {
47 use super::*;
48
49 #[test]
50 fn bumpslab_alloc_get_clear() {
51 let mut slab = BumpSlab::<64>::new();
52 let (off1, len1) = slab.alloc(&[10, 20, 30]).unwrap();
53 let (off2, len2) = slab.alloc(&[40, 50]).unwrap();
54 assert_eq!(slab.get(off1, len1), &[10, 20, 30]);
55 assert_eq!(slab.get(off2, len2), &[40, 50]);
56 assert_eq!(slab.used(), 5);
57 slab.clear();
58 assert_eq!(slab.used(), 0);
59 }
60
61 #[test]
62 fn bumpslab_full() {
63 let mut slab = BumpSlab::<4>::new();
64 assert!(slab.alloc(&[1, 2, 3]).is_some());
65 assert!(slab.alloc(&[4, 5]).is_none());
66 }
67}