bin-layout 7.1.0

This library used to serialize and deserialize data in binary format.
Documentation
use crate::*;
use std::iter::FromIterator;

#[inline]
pub fn invalid_input(error: impl Into<DynErr>) -> io::Error {
    io::Error::new(io::ErrorKind::InvalidInput, error)
}

#[inline]
pub fn get_slice<'a>(remaining: &mut &'a [u8], len: usize) -> Result<&'a [u8]> {
    if len <= remaining.len() {
        unsafe {
            let slice = remaining.get_unchecked(..len);
            *remaining = remaining.get_unchecked(len..);
            Ok(slice)
        }
    } else {
        Err("Insufficient bytes".into())
    }
}

#[inline]
pub fn try_collect<'de, T, I>(cursor: &mut &'de [u8], len: usize) -> Result<I>
where
    T: Decoder<'de>,
    I: FromIterator<T>,
{
    let mut error = None;
    let out = I::from_iter(Iter {
        len,
        err: &mut error,
        cursor,
        _marker: std::marker::PhantomData,
    });
    match error {
        Some(err) => Err(err),
        None => Ok(out),
    }
}

pub struct Iter<'err, 'c, 'de, T> {
    len: usize,
    err: &'err mut Option<DynErr>,
    cursor: &'c mut &'de [u8],
    _marker: std::marker::PhantomData<T>,
}

impl<'err, 'c, 'de, T: Decoder<'de>> Iterator for Iter<'err, 'c, 'de, T> {
    type Item = T;
    #[inline]
    fn next(&mut self) -> Option<Self::Item> {
        if self.len == 0 {
            return None;
        }
        match T::decoder(self.cursor) {
            Ok(val) => {
                self.len -= 1;
                Some(val)
            }
            Err(err) => {
                self.len = 0;
                *self.err = Some(err);
                None
            }
        }
    }

    #[inline]
    fn size_hint(&self) -> (usize, Option<usize>) {
        (self.len, Some(self.len))
    }
}