commonware_codec/types/
mod.rs1use crate::{Buf, Error, Read};
4use core::cmp::Ordering;
5
6pub mod btree_map;
7pub mod btree_set;
8pub mod bytes;
9#[cfg(feature = "std")]
10pub mod hash_map;
11#[cfg(feature = "std")]
12pub mod hash_set;
13pub mod lazy;
14#[cfg(feature = "std")]
15pub mod net;
16pub mod primitives;
17pub mod tuple;
18pub mod vec;
19
20pub(crate) fn read_ordered_map<K, V, F>(
22 buf: &mut impl Buf,
23 len: usize,
24 k_cfg: &K::Cfg,
25 v_cfg: &V::Cfg,
26 mut insert: F,
27 map_type: &'static str,
28) -> Result<(), Error>
29where
30 K: Read + Ord,
31 V: Read,
32 F: FnMut(K, V) -> Option<V>,
33{
34 let mut last: Option<(K, V)> = None;
35 for _ in 0..len {
36 let key = K::read_cfg(buf, k_cfg)?;
38
39 if let Some((ref last_key, _)) = last {
41 match key.cmp(last_key) {
42 Ordering::Equal => return Err(Error::Invalid(map_type, "Duplicate key")),
43 Ordering::Less => return Err(Error::Invalid(map_type, "Keys must ascend")),
44 _ => {}
45 }
46 }
47
48 let value = V::read_cfg(buf, v_cfg)?;
50
51 if let Some((last_key, last_value)) = last.take() {
53 insert(last_key, last_value);
54 }
55 last = Some((key, value));
56 }
57
58 if let Some((last_key, last_value)) = last {
60 insert(last_key, last_value);
61 }
62
63 Ok(())
64}
65
66pub(crate) fn read_ordered_set<K, F>(
68 buf: &mut impl Buf,
69 len: usize,
70 cfg: &K::Cfg,
71 mut insert: F,
72 set_type: &'static str,
73) -> Result<(), Error>
74where
75 K: Read + Ord,
76 F: FnMut(K) -> bool,
77{
78 let mut last: Option<K> = None;
79 for _ in 0..len {
80 let item = K::read_cfg(buf, cfg)?;
82
83 if let Some(ref last) = last {
85 match item.cmp(last) {
86 Ordering::Equal => return Err(Error::Invalid(set_type, "Duplicate item")),
87 Ordering::Less => return Err(Error::Invalid(set_type, "Items must ascend")),
88 _ => {}
89 }
90 }
91
92 if let Some(last) = last.take() {
94 insert(last);
95 }
96 last = Some(item);
97 }
98
99 if let Some(last) = last {
101 insert(last);
102 }
103
104 Ok(())
105}
106
107#[cfg(test)]
108pub(crate) mod tests {
109 use crate::{Buf, BufsMut, Error, Read, Write};
110 use bytes::{BufMut, Bytes, BytesMut, TryGetError, buf::UninitSlice};
111
112 #[derive(Debug, PartialEq, Eq)]
117 pub struct Byte(pub u8);
118
119 impl Write for Byte {
120 fn write(&self, buf: &mut impl BufMut) {
121 buf.put_u8(self.0);
122 }
123 }
124
125 impl Read for Byte {
126 type Cfg = ();
127
128 fn read_cfg(buf: &mut impl Buf, _: &()) -> Result<Self, Error> {
129 Ok(Self(<u8 as Read>::read_cfg(buf, &())?))
130 }
131 }
132
133 pub struct TrackingWriteBuf {
139 inner: BytesMut,
140 pub put_slice_calls: usize,
142 pub put_u8_calls: usize,
144 pub pushed: Vec<Bytes>,
146 }
147
148 impl TrackingWriteBuf {
149 pub fn new() -> Self {
150 Self {
151 inner: BytesMut::new(),
152 put_slice_calls: 0,
153 put_u8_calls: 0,
154 pushed: Vec::new(),
155 }
156 }
157
158 pub fn freeze(self) -> Bytes {
159 self.inner.freeze()
160 }
161 }
162
163 unsafe impl BufMut for TrackingWriteBuf {
167 fn remaining_mut(&self) -> usize {
168 self.inner.remaining_mut()
169 }
170
171 fn chunk_mut(&mut self) -> &mut UninitSlice {
172 self.inner.chunk_mut()
173 }
174
175 unsafe fn advance_mut(&mut self, cnt: usize) {
176 unsafe { self.inner.advance_mut(cnt) }
180 }
181
182 fn put_slice(&mut self, src: &[u8]) {
183 self.put_slice_calls += 1;
184 self.inner.put_slice(src);
185 }
186
187 fn put_u8(&mut self, n: u8) {
188 self.put_u8_calls += 1;
189 self.inner.put_u8(n);
190 }
191 }
192
193 impl BufsMut for TrackingWriteBuf {
194 fn push(&mut self, chunk: impl Into<Bytes> + 'static) {
195 let bytes = chunk.into();
196 self.inner.extend_from_slice(&bytes);
197 self.pushed.push(bytes);
198 }
199 }
200
201 pub struct TrackingReadBuf {
207 inner: Bytes,
208 pub bulk_reads: usize,
210 pub byte_reads: usize,
212 }
213
214 impl TrackingReadBuf {
215 pub fn new(bytes: &'static [u8]) -> Self {
216 Self {
217 inner: Bytes::from_static(bytes),
218 bulk_reads: 0,
219 byte_reads: 0,
220 }
221 }
222 }
223
224 impl Buf for TrackingReadBuf {}
225
226 impl bytes::Buf for TrackingReadBuf {
227 fn remaining(&self) -> usize {
228 self.inner.remaining()
229 }
230
231 fn chunk(&self) -> &[u8] {
232 self.inner.chunk()
233 }
234
235 fn advance(&mut self, cnt: usize) {
236 self.bulk_reads += 1;
237 self.inner.advance(cnt)
238 }
239
240 fn get_u8(&mut self) -> u8 {
241 self.byte_reads += 1;
242 self.inner.get_u8()
243 }
244
245 fn try_get_u8(&mut self) -> Result<u8, TryGetError> {
246 self.byte_reads += 1;
247 self.inner.try_get_u8()
248 }
249
250 fn copy_to_bytes(&mut self, len: usize) -> Bytes {
251 self.inner.copy_to_bytes(len)
252 }
253 }
254}