1use crate::{
4 error::{Error, Result},
5 header::Header,
6 io::{Read, Reference},
7 marker::Marker,
8 value::Value,
9};
10
11mod bool;
12mod bytes;
13mod float;
14mod int;
15mod map;
16mod null;
17mod seq;
18mod string;
19mod unit;
20
21#[derive(Debug)]
23pub struct Decoder<R> {
24 reader: R,
25 pos: usize,
26}
27
28impl<R> Decoder<R> {
29 pub fn from_reader(reader: R) -> Self {
31 Decoder { reader, pos: 0 }
32 }
33
34 pub fn into_reader(self) -> R {
36 self.reader
37 }
38
39 pub fn pos(&self) -> usize {
41 self.pos
42 }
43}
44
45impl<'de, R> Decoder<R>
46where
47 R: Read<'de>,
48{
49 pub fn decode_value(&mut self) -> Result<Value> {
53 let header = self.decode_header()?;
54 self.decode_value_of(header)
55 }
56
57 pub fn peek_marker(&mut self) -> Result<Marker> {
61 self.peek_byte().map(Marker::detect)
62 }
63
64 pub fn decode_header(&mut self) -> Result<Header> {
68 match self.peek_marker()? {
69 Marker::Int => self.decode_int_header().map(From::from),
70 Marker::String => self.decode_string_header().map(From::from),
71 Marker::Seq => self.decode_seq_header().map(From::from),
72 Marker::Map => self.decode_map_header().map(From::from),
73 Marker::Float => self.decode_float_header().map(From::from),
74 Marker::Bytes => self.decode_bytes_header().map(From::from),
75 Marker::Bool => self.decode_bool_header().map(From::from),
76 Marker::Unit => self.decode_unit_header().map(From::from),
77 Marker::Null => self.decode_null_header().map(From::from),
78 }
79 }
80
81 #[cfg_attr(feature = "tracing", tracing::instrument(skip_all))]
85 pub fn skip_value(&mut self) -> Result<()> {
86 let header = self.decode_header()?;
87 self.skip_value_of(header)
88 }
89
90 #[cfg_attr(feature = "tracing", tracing::instrument(skip_all))]
92 pub fn skip_value_of(&mut self, header: Header) -> Result<()> {
93 match header {
94 Header::Int(header) => self.skip_int_value_of(header),
95 Header::String(header) => self.skip_string_value_of(header),
96 Header::Seq(header) => self.skip_seq_value_of(header),
97 Header::Map(header) => self.skip_map_value_of(header),
98 Header::Float(header) => self.skip_float_value_of(header),
99 Header::Bytes(header) => self.skip_bytes_value_of(header),
100 Header::Bool(header) => self.skip_bool_value_of(header),
101 Header::Unit(header) => self.skip_unit_value_of(header),
102 Header::Null(header) => self.skip_null_value_of(header),
103 }
104 }
105
106 pub fn decode_value_of(&mut self, header: Header) -> Result<Value> {
110 match header {
111 Header::Int(header) => self.decode_int_value_of(header).map(From::from),
112 Header::String(header) => self.decode_string_value_of(header).map(From::from),
113 Header::Seq(header) => self.decode_seq_value_of(header).map(From::from),
114 Header::Map(header) => self.decode_map_value_of(header).map(From::from),
115 Header::Float(header) => self.decode_float_value_of(header).map(From::from),
116 Header::Bytes(header) => self.decode_bytes_value_of(header).map(From::from),
117 Header::Bool(header) => self.decode_bool_value_of(header).map(From::from),
118 Header::Unit(header) => self.decode_unit_value_of(header).map(From::from),
119 Header::Null(header) => self.decode_null_value_of(header).map(From::from),
120 }
121 }
122}
123
124impl<'de, R> Decoder<R>
127where
128 R: Read<'de>,
129{
130 #[inline]
131 fn peek_byte(&mut self) -> Result<u8> {
132 self.reader.peek_one()
133 }
134
135 #[inline]
136 fn pull_byte_expecting(&mut self, marker: Marker) -> Result<u8> {
137 let pos = self.pos;
138
139 let byte = self.pull_byte()?;
140
141 marker.validate(byte).map_err(|exp| {
142 Error::invalid_type(
143 exp.unexpected.to_string(),
144 exp.expected.to_string(),
145 Some(pos),
146 )
147 })?;
148
149 Ok(byte)
150 }
151
152 #[inline]
153 fn pull_byte(&mut self) -> Result<u8> {
154 let byte = self.reader.read_one()?;
155
156 self.pos += 1;
157
158 Ok(byte)
159 }
160
161 #[inline]
162 fn pull_bytes_into<'s>(&'s mut self, buf: &'s mut [u8]) -> Result<()> {
163 let len = buf.len();
164
165 if len == 0 {
166 return Ok(());
167 }
168
169 self.reader.read_into(buf)?;
170
171 self.pos += len;
172
173 Ok(())
174 }
175
176 #[inline]
177 fn pull_bytes<'s>(
178 &'s mut self,
179 len: usize,
180 scratch: &'s mut Vec<u8>,
181 ) -> Result<Reference<'de, 's, [u8]>> {
182 let bytes = self.reader.read(len, scratch)?;
183
184 debug_assert_eq!(bytes.len(), len);
185
186 self.pos += len;
187
188 Ok(bytes)
189 }
190
191 #[inline]
192 fn pull_len_bytes(&mut self, width: u8) -> Result<usize> {
193 let pos = self.pos;
194
195 const MAX_WIDTH: usize = 8;
196 let mut padded_be_bytes: [u8; MAX_WIDTH] = [0b0; MAX_WIDTH];
197 self.pull_bytes_into(&mut padded_be_bytes[(MAX_WIDTH - (width as usize))..])?;
198
199 u64::from_be_bytes(padded_be_bytes)
200 .try_into()
201 .map_err(|_| Error::number_out_of_range(Some(pos)))
202 }
203}
204
205#[cfg(test)]
208mod test {
209 use crate::{error::ErrorCode, io::SliceReader};
210
211 use super::*;
212
213 #[test]
214 fn new() {
215 let bytes = SliceReader::new(&[1, 2, 3]);
216 let decoder = Decoder::from_reader(&bytes);
217 assert_eq!(decoder.pos, 0);
218 }
219
220 #[test]
221 fn pull_byte() {
222 let bytes = SliceReader::new(&[1, 2, 3]);
223 let mut decoder = Decoder::from_reader(bytes);
224 assert_eq!(decoder.pos, 0);
225
226 let byte = decoder.pull_byte().unwrap();
227 assert_eq!(byte, 1);
228 assert_eq!(decoder.pos, 1);
229
230 let byte = decoder.pull_byte().unwrap();
231 assert_eq!(byte, 2);
232 assert_eq!(decoder.pos, 2);
233
234 let byte = decoder.pull_byte().unwrap();
235 assert_eq!(byte, 3);
236 assert_eq!(decoder.pos, 3);
237
238 let error_code = decoder.pull_byte().unwrap_err().code();
239 assert_eq!(error_code, ErrorCode::UnexpectedEndOfFile);
240 }
241
242 #[test]
243 fn pull_bytes_into() {
244 let bytes = SliceReader::new(&[1, 2, 3]);
245 let mut decoder = Decoder::from_reader(bytes);
246 assert_eq!(decoder.pos, 0);
247
248 let mut buf = vec![];
249 decoder.pull_bytes_into(&mut buf).unwrap();
250 assert_eq!(buf, &[]);
251 assert_eq!(decoder.pos, 0);
252
253 let mut buf = vec![0];
254 decoder.pull_bytes_into(&mut buf).unwrap();
255 assert_eq!(buf, &[1]);
256 assert_eq!(decoder.pos, 1);
257
258 let mut buf = vec![0, 0];
259 decoder.pull_bytes_into(&mut buf).unwrap();
260 assert_eq!(buf, &[2, 3]);
261 assert_eq!(decoder.pos, 3);
262
263 let mut buf = vec![0, 0, 0];
264 let error_code = decoder.pull_bytes_into(&mut buf).unwrap_err().code();
265 assert_eq!(error_code, ErrorCode::UnexpectedEndOfFile);
266 assert_eq!(decoder.pos, 3);
267 }
268
269 #[test]
270 fn pull_bytes() {
271 let bytes = SliceReader::new(&[1, 2, 3]);
272 let mut decoder = Decoder::from_reader(bytes);
273 let mut scratch = vec![];
274 assert_eq!(decoder.pos, 0);
275
276 let reference = decoder.pull_bytes(0, &mut scratch).unwrap();
277 assert_eq!(reference.as_ref(), &[]);
278 assert_eq!(decoder.pos, 0);
279
280 scratch.clear();
281
282 let reference = decoder.pull_bytes(1, &mut scratch).unwrap();
283 assert_eq!(reference.as_ref(), &[1]);
284 assert_eq!(decoder.pos, 1);
285
286 scratch.clear();
287
288 let reference = decoder.pull_bytes(2, &mut scratch).unwrap();
289 assert_eq!(reference.as_ref(), &[2, 3]);
290 assert_eq!(decoder.pos, 3);
291
292 scratch.clear();
293
294 let error_code = decoder.pull_bytes(1, &mut scratch).unwrap_err().code();
295 assert_eq!(error_code, ErrorCode::UnexpectedEndOfFile);
296 assert_eq!(decoder.pos, 3);
297 }
298}