TLA Line data Source code
1 : //! A heapless buffer for events of sorts.
2 :
3 : use std::ops;
4 :
5 : use heapless::HistoryBuffer;
6 :
7 CBC 9620 : #[derive(Debug, Clone)]
8 : pub struct HistoryBufferWithDropCounter<T, const L: usize> {
9 : buffer: HistoryBuffer<T, L>,
10 : drop_count: u64,
11 : }
12 :
13 : impl<T, const L: usize> HistoryBufferWithDropCounter<T, L> {
14 43653714 : pub fn write(&mut self, data: T) {
15 43653714 : let len_before = self.buffer.len();
16 43653714 : self.buffer.write(data);
17 43653714 : let len_after = self.buffer.len();
18 43653714 : self.drop_count += u64::from(len_before == len_after);
19 43653714 : }
20 12 : pub fn drop_count(&self) -> u64 {
21 12 : self.drop_count
22 12 : }
23 1778 : pub fn map<U, F: Fn(&T) -> U>(&self, f: F) -> HistoryBufferWithDropCounter<U, L> {
24 1778 : let mut buffer = HistoryBuffer::new();
25 1778 : buffer.extend(self.buffer.oldest_ordered().map(f));
26 1778 : HistoryBufferWithDropCounter::<U, L> {
27 1778 : buffer,
28 1778 : drop_count: self.drop_count,
29 1778 : }
30 1778 : }
31 : }
32 :
33 : impl<T, const L: usize> Default for HistoryBufferWithDropCounter<T, L> {
34 108808 : fn default() -> Self {
35 108808 : Self {
36 108808 : buffer: HistoryBuffer::default(),
37 108808 : drop_count: 0,
38 108808 : }
39 108808 : }
40 : }
41 :
42 : impl<T, const L: usize> ops::Deref for HistoryBufferWithDropCounter<T, L> {
43 : type Target = HistoryBuffer<T, L>;
44 :
45 1704 : fn deref(&self) -> &Self::Target {
46 1704 : &self.buffer
47 1704 : }
48 : }
49 :
50 3550 : #[derive(serde::Serialize)]
51 : struct SerdeRepr<T> {
52 : buffer: Vec<T>,
53 : drop_count: u64,
54 : }
55 :
56 : impl<'a, T, const L: usize> From<&'a HistoryBufferWithDropCounter<T, L>> for SerdeRepr<T>
57 : where
58 : T: Clone + serde::Serialize,
59 : {
60 3550 : fn from(value: &'a HistoryBufferWithDropCounter<T, L>) -> Self {
61 3550 : let HistoryBufferWithDropCounter { buffer, drop_count } = value;
62 3550 : SerdeRepr {
63 3550 : buffer: buffer.iter().cloned().collect(),
64 3550 : drop_count: *drop_count,
65 3550 : }
66 3550 : }
67 : }
68 :
69 : impl<T, const L: usize> serde::Serialize for HistoryBufferWithDropCounter<T, L>
70 : where
71 : T: Clone + serde::Serialize,
72 : {
73 3550 : fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
74 3550 : where
75 3550 : S: serde::Serializer,
76 3550 : {
77 3550 : SerdeRepr::from(self).serialize(serializer)
78 3550 : }
79 : }
80 :
81 : #[cfg(test)]
82 : mod test {
83 : use super::HistoryBufferWithDropCounter;
84 :
85 1 : #[test]
86 1 : fn test_basics() {
87 1 : let mut b = HistoryBufferWithDropCounter::<_, 2>::default();
88 1 : b.write(1);
89 1 : b.write(2);
90 1 : b.write(3);
91 2 : assert!(b.iter().any(|e| *e == 2));
92 1 : assert!(b.iter().any(|e| *e == 3));
93 2 : assert!(!b.iter().any(|e| *e == 1));
94 1 : }
95 :
96 1 : #[test]
97 1 : fn test_drop_count_works() {
98 1 : let mut b = HistoryBufferWithDropCounter::<_, 2>::default();
99 1 : b.write(1);
100 1 : assert_eq!(b.drop_count(), 0);
101 1 : b.write(2);
102 1 : assert_eq!(b.drop_count(), 0);
103 1 : b.write(3);
104 1 : assert_eq!(b.drop_count(), 1);
105 1 : b.write(4);
106 1 : assert_eq!(b.drop_count(), 2);
107 1 : }
108 :
109 1 : #[test]
110 1 : fn test_clone_works() {
111 1 : let mut b = HistoryBufferWithDropCounter::<_, 2>::default();
112 1 : b.write(1);
113 1 : b.write(2);
114 1 : b.write(3);
115 1 : assert_eq!(b.drop_count(), 1);
116 1 : let mut c = b.clone();
117 1 : assert_eq!(c.drop_count(), 1);
118 2 : assert!(c.iter().any(|e| *e == 2));
119 1 : assert!(c.iter().any(|e| *e == 3));
120 2 : assert!(!c.iter().any(|e| *e == 1));
121 :
122 1 : c.write(4);
123 2 : assert!(c.iter().any(|e| *e == 4));
124 2 : assert!(!b.iter().any(|e| *e == 4));
125 1 : }
126 :
127 1 : #[test]
128 1 : fn test_map() {
129 1 : let mut b = HistoryBufferWithDropCounter::<_, 2>::default();
130 1 :
131 1 : b.write(1);
132 1 : assert_eq!(b.drop_count(), 0);
133 : {
134 1 : let c = b.map(|i| i + 10);
135 1 : assert_eq!(c.oldest_ordered().cloned().collect::<Vec<_>>(), vec![11]);
136 1 : assert_eq!(c.drop_count(), 0);
137 : }
138 :
139 1 : b.write(2);
140 1 : assert_eq!(b.drop_count(), 0);
141 : {
142 2 : let c = b.map(|i| i + 10);
143 1 : assert_eq!(
144 1 : c.oldest_ordered().cloned().collect::<Vec<_>>(),
145 1 : vec![11, 12]
146 1 : );
147 1 : assert_eq!(c.drop_count(), 0);
148 : }
149 :
150 1 : b.write(3);
151 1 : assert_eq!(b.drop_count(), 1);
152 : {
153 2 : let c = b.map(|i| i + 10);
154 1 : assert_eq!(
155 1 : c.oldest_ordered().cloned().collect::<Vec<_>>(),
156 1 : vec![12, 13]
157 1 : );
158 1 : assert_eq!(c.drop_count(), 1);
159 : }
160 1 : }
161 : }
|