resol_vbus/
blob_buffer.rs1use std::{
2 io,
3 ops::{Deref, Index},
4 slice::SliceIndex,
5};
6
7#[derive(Clone, Debug, Default)]
11pub struct BlobBuffer {
12 buf: Vec<u8>,
13 start: usize,
14 offset: usize,
15}
16
17impl BlobBuffer {
18 pub fn new() -> BlobBuffer {
20 BlobBuffer::default()
21 }
22
23 pub fn extend_from_slice(&mut self, data: &[u8]) {
25 if self.start > 0 {
26 drop(self.buf.drain(0..self.start));
27 self.start = 0;
28 }
29
30 self.buf.extend_from_slice(data);
31 }
32
33 pub fn consume(&mut self, length: usize) {
35 self.start += length;
36 self.offset += length;
37 }
38
39 pub fn len(&self) -> usize {
41 self.buf.len() - self.start
42 }
43
44 pub fn is_empty(&self) -> bool {
46 self.buf.len() == self.start
47 }
48
49 pub fn offset(&self) -> usize {
51 self.offset
52 }
53}
54
55impl Deref for BlobBuffer {
56 type Target = [u8];
57
58 fn deref(&self) -> &[u8] {
59 &self.buf[self.start..]
60 }
61}
62
63impl<I> Index<I> for BlobBuffer
64where
65 I: SliceIndex<[u8]>,
66{
67 type Output = I::Output;
68
69 fn index(&self, index: I) -> &Self::Output {
70 &self.deref()[index]
71 }
72}
73
74impl io::Read for BlobBuffer {
75 fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
76 let src_len = self.len();
77 let dst_len = buf.len();
78 let len = if src_len < dst_len { src_len } else { dst_len };
79 buf[0..len].copy_from_slice(&self[0..len]);
80 self.consume(len);
81 Ok(len)
82 }
83}
84
85impl io::Write for BlobBuffer {
86 fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
87 self.extend_from_slice(buf);
88 Ok(buf.len())
89 }
90
91 fn flush(&mut self) -> io::Result<()> {
92 Ok(())
94 }
95}
96
97#[cfg(test)]
98mod tests {
99 use super::*;
100
101 #[test]
102 fn test() {
103 let mut bb = BlobBuffer::new();
104
105 assert_eq!(0, bb.buf.len());
106 assert_eq!(0, bb.start);
107 assert_eq!(0, bb.offset);
108 assert_eq!(0, bb.len());
109 assert_eq!(true, bb.is_empty());
110
111 bb.extend_from_slice(&[0x00, 0x01, 0x02, 0x03]);
112
113 assert_eq!(4, bb.buf.len());
114 assert_eq!(0, bb.start);
115 assert_eq!(0, bb.offset);
116 assert_eq!(4, bb.len());
117 assert_eq!(false, bb.is_empty());
118 assert_eq!(&[0x00, 0x01, 0x02, 0x03], &*bb);
119
120 bb.consume(2);
121
122 assert_eq!(4, bb.buf.len());
123 assert_eq!(2, bb.start);
124 assert_eq!(2, bb.offset);
125 assert_eq!(2, bb.len());
126 assert_eq!(false, bb.is_empty());
127 assert_eq!(&[0x02, 0x03], &*bb);
128
129 bb.consume(1);
130
131 assert_eq!(4, bb.buf.len());
132 assert_eq!(3, bb.start);
133 assert_eq!(3, bb.offset);
134 assert_eq!(1, bb.len());
135 assert_eq!(false, bb.is_empty());
136 assert_eq!(&[0x03], &*bb);
137
138 bb.extend_from_slice(&[0x04, 0x05, 0x06, 0x07]);
139
140 assert_eq!(5, bb.buf.len());
141 assert_eq!(0, bb.start);
142 assert_eq!(3, bb.offset);
143 assert_eq!(5, bb.len());
144 assert_eq!(false, bb.is_empty());
145 assert_eq!(&[0x03, 0x04, 0x05, 0x06, 0x07], &*bb);
146
147 assert_eq!(&[0x03, 0x04, 0x05, 0x06, 0x07], &(*bb));
149
150 assert_eq!(0x05, bb[2]);
152 assert_eq!(&[0x05, 0x06], &bb[2..4]);
153 }
154}