1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
use std::any::{type_name, Any, TypeId};
use crate::{error::Error, reader::DynamicByteReader, Endian, Result};
/// Trait for types that read bytes.
pub trait ByteRead<'input> {
/// Type returned by [`Self::at`], must implement [`ByteRead`] itself.
type AtByteRead: ByteRead<'input>;
/// A reference to a runtime specified amount of bytes.
///
/// # Errors
/// If the implementing type needs to.
fn read_ref(&mut self, count: usize) -> Result<&'input [u8]>;
/// Array of bytes with it's size specified at compile time.
///
/// # Errors
/// If the implementing type needs to.
fn read<const COUNT: usize>(&mut self) -> Result<[u8; COUNT]> {
Ok(self.read_ref(COUNT)?.try_into()?)
}
/// A reference to all remaining data.
///
/// # Errors
/// If the implementing type needs to.
fn remaining(&mut self) -> Result<&'input [u8]>;
/// The endianess of the reader.
fn endian(&self) -> Endian {
Endian::Little
}
/// All data managed by reader as a slice.
///
/// # Errors
/// If the implementing type needs to.
fn all(&self) -> Result<&'input [u8]>;
/// A new reader starting at the given position of this reader.
///
/// # Errors
/// If the implementing type needs to.
fn at(&self, _location: usize) -> Result<Self::AtByteRead> {
Err(Error::AtNotSupported(type_name::<Self>().into()))
}
/// Get a value of the specified type from the reader, usefull to pass along say a header.
///
/// # Errors
/// If the implementing type needs to.
fn flag<T>(&self) -> Result<&T>
where
T: Any,
{
self.get_flag(TypeId::of::<T>())
.and_then(<(dyn Any + 'static)>::downcast_ref)
.ok_or_else(Error::flag_not_found::<T>)
}
/// Get a flag as an any from the reader, read using a [`any::TypeId`].
fn get_flag(&self, id: TypeId) -> Option<&dyn Any>;
/// Convert self into a [`crate::DynamicByteReader`][DynamicByteReader] it still implements
/// [`ByteRead`] but has the same type regardless of the [`ByteRead`] that was converted, however
fn into_dynamic(self) -> DynamicByteReader<'input>
where
Self: Sized + 'input,
{
DynamicByteReader::from_reader(self)
}
}