kernel/collections/
ring.rs1use core::mem::MaybeUninit;
2
3pub struct RingBuffer<T, const N: usize> {
5 buffer: [MaybeUninit<T>; N],
6 read_index: usize,
7 write_index: usize,
8}
9
10#[allow(dead_code)]
11impl<T, const N: usize> RingBuffer<T, N> {
12 pub fn try_push(&mut self, value: T) -> bool {
13 let next_index = (self.write_index + 1) % self.buffer.len();
14 if next_index == self.read_index {
15 return false;
16 }
17
18 self.buffer[self.write_index] = MaybeUninit::new(value);
19 self.write_index = next_index;
20
21 true
22 }
23
24 pub fn push(&mut self, value: T) {
25 let next_index = (self.write_index + 1) % self.buffer.len();
26 if next_index == self.read_index {
27 panic!("Ring buffer overflow");
28 }
29
30 self.buffer[self.write_index] = MaybeUninit::new(value);
31 self.write_index = next_index;
32 }
33
34 pub fn push_replace(&mut self, value: T) {
35 let next_index = (self.write_index + 1) % self.buffer.len();
36 if next_index == self.read_index {
38 unsafe { self.buffer[self.read_index].assume_init_drop() };
40 self.buffer[self.read_index] = MaybeUninit::new(value);
41 self.write_index = next_index;
42 self.read_index = (self.read_index + 1) % self.buffer.len();
44 } else {
45 self.buffer[self.write_index] = MaybeUninit::new(value);
46 self.write_index = next_index;
47 }
48 }
49
50 pub fn pop(&mut self) -> Option<T> {
51 if self.read_index == self.write_index {
52 return None;
53 }
54
55 let value = unsafe { self.buffer[self.read_index].assume_init_read() };
56 self.read_index = (self.read_index + 1) % self.buffer.len();
57
58 Some(value)
59 }
60
61 pub fn clear(&mut self) {
62 self.read_index = 0;
63 self.write_index = 0;
64 }
65}
66
67#[allow(dead_code)]
68impl<T: Copy, const N: usize> RingBuffer<T, N> {
69 pub const fn empty() -> Self {
70 Self {
71 buffer: [MaybeUninit::<T>::uninit(); N],
72 read_index: 0,
73 write_index: 0,
74 }
75 }
76}