tl_types/deserialize.rs
1use std::fmt;
2
3#[derive(Clone, Debug, PartialEq)]
4pub enum Error {
5 /// The end of the buffer was reached earlier than anticipated, which
6 /// implies there is not enough data to complete the deserialization.
7 UnexpectedEof,
8
9 /// The error type indicating an unexpected constructor was found,
10 /// for example, when reading data that doesn't represent the
11 /// correct type (e.g. reading a `bool` when we expect a `Vec`).
12 /// In particular, it can occur in the following situations:
13 ///
14 /// * When reading a boolean.
15 /// * When reading a boxed vector.
16 /// * When reading an arbitrary boxed type.
17 ///
18 /// It is important to note that unboxed or bare [`types`] lack the
19 /// constructor information, and as such they cannot be validated.
20 ///
21 /// [`types`]: types/index.html
22 UnexpectedConstructor {
23 /// The unexpected constructor identifier.
24 id: u32,
25 },
26}
27
28impl std::error::Error for Error {}
29
30impl fmt::Display for Error {
31 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
32 match *self {
33 Self::UnexpectedEof => write!(f, "unexpected eof"),
34 Self::UnexpectedConstructor { id } => write!(f, "unexpected constructor: {:08x}", id),
35 }
36 }
37}
38
39/// Re-implement `Cursor` to only work over in-memory buffers and greatly
40/// narrow the possible error cases.
41pub struct Cursor<'a> {
42 buf: &'a [u8],
43 pos: usize,
44}
45
46impl<'a> Cursor<'a> {
47 pub fn from_slice(buf: &'a [u8]) -> Self {
48 Self { buf, pos: 0 }
49 }
50
51 // TODO not a fan we need to expose this (and a way to create `Cursor`),
52 // but crypto needs it because it needs to know where deserialization
53 // of some inner data ends.
54 pub fn pos(&self) -> usize {
55 self.pos
56 }
57
58 pub fn read_byte(&mut self) -> Result<u8> {
59 if self.pos < self.buf.len() {
60 let byte = self.buf[self.pos];
61 self.pos += 1;
62 Ok(byte)
63 } else {
64 Err(Error::UnexpectedEof)
65 }
66 }
67
68 pub fn read_exact(&mut self, buf: &mut [u8]) -> Result<()> {
69 if self.pos + buf.len() > self.buf.len() {
70 Err(Error::UnexpectedEof)
71 } else {
72 buf.copy_from_slice(&self.buf[self.pos..self.pos + buf.len()]);
73 self.pos += buf.len();
74 Ok(())
75 }
76 }
77
78 pub fn read_to_end(&mut self, buf: &mut Vec<u8>) -> Result<usize> {
79 buf.extend(&self.buf[self.pos..]);
80 let old = self.pos;
81 self.pos = self.buf.len();
82 Ok(self.pos - old)
83 }
84}
85
86/// The problem with being generic over `std::io::Read` is that it's
87/// fallible, but in practice, we're always going to serialize in-memory,
88/// so instead we just use a `[u8]` as our buffer.
89// TODO this is only public for session
90pub type Buffer<'a, 'b> = &'a mut Cursor<'b>;
91pub type Result<T> = std::result::Result<T, Error>;
92
93/// This trait allows for data serialized according to the
94/// [Binary Data Serialization] to be deserialized into concrete instances.
95///
96/// [Binary Data Serialization]: https://core.telegram.org/mtproto/serialize
97pub trait Deserializable {
98 /// Deserializes an instance of the type from a given buffer.
99 fn deserialize(buf: Buffer) -> Result<Self>
100 where
101 Self: std::marker::Sized;
102
103 /// Convenience function to deserialize an instance from a given buffer.
104 ///
105 /// # Examples
106 ///
107 /// ```
108 /// use gramme_types::Deserializable as _;
109 ///
110 /// assert_eq!(bool::from_bytes(&[0x37, 0x97, 0x79, 0xbc]).unwrap(), false);
111 /// ```
112 fn from_bytes(buf: &[u8]) -> Result<Self>
113 where
114 Self: std::marker::Sized,
115 {
116 Self::deserialize(&mut Cursor::from_slice(buf))
117 }
118}
119
120impl Deserializable for bool {
121 /// Deserializes a boolean according to the following definitions:
122 ///
123 /// * `boolFalse#bc799737 = Bool;` deserializes into `false`.
124 /// * `boolTrue#997275b5 = Bool;` deserializes into `true`.
125 ///
126 /// # Examples
127 ///
128 /// ```
129 /// use gramme_types::Deserializable;
130 ///
131 /// assert_eq!(bool::from_bytes(&[0xb5, 0x75, 0x72, 0x99]).unwrap(), true);
132 /// assert_eq!(bool::from_bytes(&[0x37, 0x97, 0x79, 0xbc]).unwrap(), false);
133 /// ```
134 #[allow(clippy::unreadable_literal)]
135 fn deserialize(buf: Buffer) -> Result<Self> {
136 let id = u32::deserialize(buf)?;
137 match id {
138 0x997275b5u32 => Ok(true),
139 0xbc799737u32 => Ok(false),
140 _ => Err(Error::UnexpectedConstructor { id }),
141 }
142 }
143}
144
145impl Deserializable for i32 {
146 /// Deserializes a 32-bit signed integer according to the following
147 /// definition:
148 ///
149 /// * `int ? = Int;`.
150 ///
151 /// # Examples
152 ///
153 /// ```
154 /// use gramme_types::Deserializable;
155 ///
156 /// assert_eq!(i32::from_bytes(&[0x00, 0x00, 0x00, 0x00]).unwrap(), 0i32);
157 /// assert_eq!(i32::from_bytes(&[0x01, 0x00, 0x00, 0x00]).unwrap(), 1i32);
158 /// assert_eq!(i32::from_bytes(&[0xff, 0xff, 0xff, 0xff]).unwrap(), -1i32);
159 /// assert_eq!(i32::from_bytes(&[0xff, 0xff, 0xff, 0x7f]).unwrap(), i32::max_value());
160 /// assert_eq!(i32::from_bytes(&[0x00, 0x00, 0x00, 0x80]).unwrap(), i32::min_value());
161 /// ```
162 fn deserialize(buf: Buffer) -> Result<Self> {
163 let mut buffer = [0u8; 4];
164 buf.read_exact(&mut buffer)?;
165 Ok(Self::from_le_bytes(buffer))
166 }
167}
168
169impl Deserializable for u32 {
170 /// Deserializes a 32-bit unsigned integer according to the following
171 /// definition:
172 ///
173 /// * `int ? = Int;`.
174 ///
175 /// # Examples
176 ///
177 /// ```
178 /// use gramme_types::Deserializable;
179 ///
180 /// assert_eq!(u32::from_bytes(&[0x00, 0x00, 0x00, 0x00]).unwrap(), 0u32);
181 /// assert_eq!(u32::from_bytes(&[0x01, 0x00, 0x00, 0x00]).unwrap(), 1u32);
182 /// assert_eq!(u32::from_bytes(&[0xff, 0xff, 0xff, 0xff]).unwrap(), u32::max_value());
183 /// assert_eq!(u32::from_bytes(&[0x00, 0x00, 0x00, 0x00]).unwrap(), u32::min_value());
184 /// ```
185 fn deserialize(buf: Buffer) -> Result<Self> {
186 let mut buffer = [0u8; 4];
187 buf.read_exact(&mut buffer)?;
188 Ok(Self::from_le_bytes(buffer))
189 }
190}
191
192impl Deserializable for i64 {
193 /// Deserializes a 64-bit signed integer according to the following
194 /// definition:
195 ///
196 /// * `long ? = Long;`.
197 ///
198 /// # Examples
199 ///
200 /// ```
201 /// use gramme_types::Deserializable;
202 ///
203 /// assert_eq!(i64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0]).unwrap(), 0i64);
204 /// assert_eq!(i64::from_bytes(&[0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0]).unwrap(), 1i64);
205 /// assert_eq!(i64::from_bytes(&[0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]).unwrap(), (-1i64));
206 /// assert_eq!(i64::from_bytes(&[0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f]).unwrap(), i64::max_value());
207 /// assert_eq!(i64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x80]).unwrap(), i64::min_value());
208 /// ```
209 fn deserialize(buf: Buffer) -> Result<Self> {
210 let mut buffer = [0u8; 8];
211 buf.read_exact(&mut buffer)?;
212 Ok(Self::from_le_bytes(buffer))
213 }
214}
215
216impl Deserializable for [u8; 16] {
217 /// Deserializes the 128-bit integer according to the following
218 /// definition:
219 ///
220 /// * `int128 4*[ int ] = Int128;`.
221 ///
222 /// # Examples
223 ///
224 /// ```
225 /// use gramme_types::Deserializable;
226 ///
227 /// let data = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16];
228 ///
229 /// assert_eq!(<[u8; 16]>::from_bytes(&data).unwrap(), data);
230 /// ```
231 fn deserialize(buf: Buffer) -> Result<Self> {
232 let mut buffer = [0u8; 16];
233 buf.read_exact(&mut buffer)?;
234 Ok(buffer)
235 }
236}
237
238impl Deserializable for [u8; 32] {
239 /// Deserializes the 128-bit integer according to the following
240 /// definition:
241 ///
242 /// * `int256 8*[ int ] = Int256;`.
243 ///
244 /// # Examples
245 ///
246 /// ```
247 /// use gramme_types::Deserializable;
248 ///
249 /// let data = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17,
250 /// 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32];
251 ///
252 /// assert_eq!(<[u8; 32]>::from_bytes(&data).unwrap(), data);
253 /// ```
254 fn deserialize(buf: Buffer) -> Result<Self> {
255 let mut buffer = [0u8; 32];
256 buf.read_exact(&mut buffer)?;
257 Ok(buffer)
258 }
259}
260
261impl Deserializable for f64 {
262 /// Deserializes a 64-bit floating point according to the
263 /// following definition:
264 ///
265 /// * `double ? = Double;`.
266 ///
267 /// # Examples
268 ///
269 /// ```
270 /// use std::f64;
271 /// use gramme_types::Deserializable;
272 ///
273 /// assert_eq!(f64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0]).unwrap(), 0f64);
274 /// assert_eq!(f64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xf8, 0x3f]).unwrap(), 1.5f64);
275 /// assert_eq!(f64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xf8, 0xbf]).unwrap(), -1.5f64);
276 /// assert_eq!(f64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xf0, 0x7f]).unwrap(), f64::INFINITY);
277 /// assert_eq!(f64::from_bytes(&[0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xf0, 0xff]).unwrap(), f64::NEG_INFINITY);
278 /// ```
279 fn deserialize(buf: Buffer) -> Result<Self> {
280 let mut buffer = [0u8; 8];
281 buf.read_exact(&mut buffer)?;
282 Ok(Self::from_le_bytes(buffer))
283 }
284}
285
286impl<T: Deserializable> Deserializable for Vec<T> {
287 /// Deserializes a vector of deserializable items according to the
288 /// following definition:
289 ///
290 /// * `vector#1cb5c415 {t:Type} # [ t ] = Vector t;`.
291 ///
292 /// # Examples
293 ///
294 /// ```
295 /// use gramme_types::Deserializable;
296 ///
297 /// assert_eq!(Vec::<i32>::from_bytes(&[0x15, 0xc4, 0xb5, 0x1c, 0x0, 0x0, 0x0, 0x0]).unwrap(), Vec::new());
298 /// assert_eq!(Vec::<i32>::from_bytes(&[0x15, 0xc4, 0xb5, 0x1c, 0x1, 0x0, 0x0, 0x0, 0x7f, 0x0, 0x0, 0x0]).unwrap(),
299 /// vec![0x7f_i32]);
300 /// ```
301 #[allow(clippy::unreadable_literal)]
302 fn deserialize(buf: Buffer) -> Result<Self> {
303 let id = u32::deserialize(buf)?;
304 if id != 0x1cb5c415u32 {
305 return Err(Error::UnexpectedConstructor { id });
306 }
307 let len = u32::deserialize(buf)?;
308 (0..len).map(|_| T::deserialize(buf)).collect()
309 }
310}
311
312impl<T: Deserializable> Deserializable for crate::RawVec<T> {
313 /// Deserializes a vector of deserializable items according to the
314 /// following definition:
315 ///
316 /// * `vector#1cb5c415 {t:Type} # [ t ] = Vector t;`.
317 ///
318 /// # Examples
319 ///
320 /// ```
321 /// use gramme_types::{RawVec, Deserializable};
322 ///
323 /// assert_eq!(RawVec::<i32>::from_bytes(&[0x0, 0x0, 0x0, 0x0]).unwrap().0, Vec::<i32>::new());
324 /// assert_eq!(RawVec::<i32>::from_bytes(&[0x1, 0x0, 0x0, 0x0, 0x7f, 0x0, 0x0, 0x0]).unwrap().0, vec![0x7f_i32]);
325 /// ```
326 fn deserialize(buf: Buffer) -> Result<Self> {
327 let len = u32::deserialize(buf)?;
328 Ok(Self(
329 (0..len)
330 .map(|_| T::deserialize(buf))
331 .collect::<Result<Vec<T>>>()?,
332 ))
333 }
334}
335
336impl Deserializable for String {
337 /// Deserializes a UTF-8 string according to the following definition:
338 ///
339 /// * `string ? = String;`.
340 ///
341 /// # Examples
342 ///
343 /// ```
344 /// use gramme_types::Deserializable;
345 ///
346 /// fn test_string(string: &str, prefix: &[u8], suffix: &[u8]) {
347 /// let bytes = {
348 /// let mut tmp = prefix.to_vec();
349 /// tmp.extend(string.as_bytes());
350 /// tmp.extend(suffix);
351 /// tmp
352 /// };
353 /// let expected = string.to_owned();
354 ///
355 /// assert_eq!(String::from_bytes(&bytes).unwrap(), expected);
356 /// }
357 ///
358 /// test_string("", &[0x00], &[0x00, 0x00, 0x00]);
359 /// test_string("Hi", &[0x02], &[0x0]);
360 /// test_string("Hi!", &[0x03], &[]);
361 /// test_string("Hello", &[0x05], &[0x0, 0x0]);
362 /// test_string("Hello, world!", &[0xd], &[0x0, 0x0]);
363 /// test_string(
364 /// "This is a very long string, and it has to be longer than 253 \
365 /// characters, which are quite a few but we can make it! Although, \
366 /// it is quite challenging. The quick brown fox jumps over the lazy \
367 /// fox. There is still some more text we need to type. Oh, this \
368 /// sentence made it past!",
369 /// &[0xfe, 0x11, 0x01, 0x00],
370 /// &[0x00, 0x00, 0x00]
371 /// );
372 /// ```
373 fn deserialize(buf: Buffer) -> Result<Self> {
374 Ok(String::from_utf8_lossy(&Vec::<u8>::deserialize(buf)?).into())
375 }
376}
377
378impl Deserializable for Vec<u8> {
379 /// Deserializes a vector of bytes as a byte-string according to the
380 /// following definition:
381 ///
382 /// * `string ? = String;`.
383 ///
384 /// # Examples
385 ///
386 /// ```
387 /// use gramme_types::{Deserializable};
388 ///
389 /// assert_eq!(Vec::<u8>::from_bytes(&[0x00, 0x00, 0x00, 0x00]).unwrap(), Vec::new());
390 /// assert_eq!(Vec::<u8>::from_bytes(&[0x01, 0x7f, 0x00, 0x00]).unwrap(), vec![0x7f_u8]);
391 /// ```
392 fn deserialize(buf: Buffer) -> Result<Self> {
393 let first_byte = buf.read_byte()?;
394 let (len, padding) = if first_byte == 254 {
395 let mut buffer = [0u8; 3];
396 buf.read_exact(&mut buffer)?;
397 let len =
398 (buffer[0] as usize) | ((buffer[1] as usize) << 8) | ((buffer[2] as usize) << 16);
399
400 (len, len % 4)
401 } else {
402 let len = first_byte as usize;
403 (len, (len + 1) % 4)
404 };
405
406 let mut result = vec![0u8; len];
407 buf.read_exact(&mut result)?;
408
409 if padding > 0 {
410 for _ in 0..(4 - padding) {
411 buf.read_byte()?;
412 }
413 }
414
415 Ok(result)
416 }
417}