const_serialize/
array.rs

1use crate::*;
2
3/// The layout for a constant sized array. The array layout is just a length and an item layout.
4#[derive(Debug, Copy, Clone)]
5pub struct ArrayLayout {
6    pub(crate) len: usize,
7    pub(crate) item_layout: &'static Layout,
8}
9
10impl ArrayLayout {
11    /// Create a new array layout
12    pub const fn new(len: usize, item_layout: &'static Layout) -> Self {
13        Self { len, item_layout }
14    }
15}
16
17unsafe impl<const N: usize, T: SerializeConst> SerializeConst for [T; N] {
18    const MEMORY_LAYOUT: Layout = Layout::Array(ArrayLayout {
19        len: N,
20        item_layout: &T::MEMORY_LAYOUT,
21    });
22}
23
24/// Serialize a constant sized array that is stored at the pointer passed in
25pub(crate) const unsafe fn serialize_const_array(
26    ptr: *const (),
27    mut to: ConstVec<u8>,
28    layout: &ArrayLayout,
29) -> ConstVec<u8> {
30    let len = layout.len;
31    let mut i = 0;
32    to = write_array(to, len);
33    while i < len {
34        let field = ptr.wrapping_byte_offset((i * layout.item_layout.size()) as _);
35        to = serialize_const_ptr(field, to, layout.item_layout);
36        i += 1;
37    }
38    to
39}
40
41/// Deserialize an array type into the out buffer at the offset passed in. Returns a new version of the buffer with the data added.
42pub(crate) const fn deserialize_const_array<'a>(
43    from: &'a [u8],
44    layout: &ArrayLayout,
45    mut out: &mut [MaybeUninit<u8>],
46) -> Option<&'a [u8]> {
47    let item_layout = layout.item_layout;
48    let Ok((_, mut from)) = take_array(from) else {
49        return None;
50    };
51    let mut i = 0;
52    while i < layout.len {
53        let Some(new_from) = deserialize_const_ptr(from, item_layout, out) else {
54            return None;
55        };
56        let Some((_, item_out)) = out.split_at_mut_checked(item_layout.size()) else {
57            return None;
58        };
59        out = item_out;
60        from = new_from;
61        i += 1;
62    }
63    Some(from)
64}