#![cfg_attr(not(feature = "std"), no_std)]
mod allocated;
pub mod error;
mod from_u8;
pub mod funcs;
mod implements;
#[cfg(feature = "std")]
mod macros;
pub mod max_cap;
mod primitive;
pub use error::{RapiraError, Result};
pub use from_u8::{EnumFromU8Error, FromU8};
#[cfg(feature = "postcard")]
pub use implements::postcard;
#[cfg(feature = "zerocopy")]
pub use implements::zero;
pub use primitive::{byte_rapira, bytes_rapira, str_rapira};
#[cfg(feature = "alloc")]
extern crate alloc;
pub use funcs::{
check_bytes, deser_unchecked, deser_unsafe, deserialize, deserialize_ctx,
deserialize_versioned, size, size_ctx,
};
#[cfg(feature = "alloc")]
pub use funcs::{extend_vec, serialize, serialize_ctx};
pub use rapira_derive::{FromU8, PrimitiveFromEnum, Rapira};
#[derive(Clone, Copy, Default, Debug, PartialEq, Eq)]
pub struct RapiraFlags(pub u64);
impl RapiraFlags {
pub const NONE: Self = Self(0);
#[inline]
pub const fn new(flags: u64) -> Self {
Self(flags)
}
#[inline]
pub const fn has(self, flag: u64) -> bool {
self.0 & flag != 0
}
#[inline]
pub const fn with(self, flag: u64) -> Self {
Self(self.0 | flag)
}
}
pub trait Rapira {
const STATIC_SIZE: Option<usize> = None;
const MIN_SIZE: usize;
fn size(&self) -> usize;
fn check_bytes(slice: &mut &[u8]) -> Result<()>;
fn from_slice(slice: &mut &[u8]) -> Result<Self>
where
Self: Sized;
#[inline]
fn debug_from_slice(slice: &mut &[u8]) -> Result<Self>
where
Self: Sized + std::fmt::Debug,
{
let len = slice.len();
Self::from_slice(slice)
.inspect(|item| {
println!("len: {len}, item: {item:?}");
})
.inspect_err(|err| {
println!("len: {len}, err: {err:?}");
})
}
#[inline]
unsafe fn from_slice_unchecked(slice: &mut &[u8]) -> Result<Self>
where
Self: Sized,
{
Self::from_slice(slice)
}
unsafe fn from_slice_unsafe(slice: &mut &[u8]) -> Result<Self>
where
Self: Sized,
{
Self::from_slice(slice)
}
#[inline]
fn from_slice_versioned(slice: &mut &[u8], _version: u8) -> Result<Self>
where
Self: Sized,
{
Self::from_slice(slice)
}
#[inline]
fn try_convert_to_bytes(&self, slice: &mut [u8], cursor: &mut usize) -> Result<()> {
self.convert_to_bytes(slice, cursor);
Ok(())
}
fn convert_to_bytes(&self, slice: &mut [u8], cursor: &mut usize);
#[inline]
fn convert_to_bytes_ctx(&self, slice: &mut [u8], cursor: &mut usize, _flags: RapiraFlags) {
self.convert_to_bytes(slice, cursor)
}
#[inline]
fn from_slice_ctx(slice: &mut &[u8], _flags: RapiraFlags) -> Result<Self>
where
Self: Sized,
{
Self::from_slice(slice)
}
#[inline]
fn size_ctx(&self, _flags: RapiraFlags) -> usize {
self.size()
}
}
pub const LEN_SIZE: usize = 4;
#[inline]
pub fn push(slice: &mut [u8], cursor: &mut usize, item: u8) {
let s = slice.get_mut(*cursor).unwrap();
*s = item;
*cursor += 1;
}
#[inline]
pub fn try_push(slice: &mut [u8], cursor: &mut usize, item: u8) -> Result<()> {
let s = slice.get_mut(*cursor).ok_or(RapiraError::SliceLen)?;
*s = item;
*cursor += 1;
Ok(())
}
#[inline]
pub fn extend(slice: &mut [u8], cursor: &mut usize, items: &[u8]) {
let end = *cursor + items.len();
let s = slice.get_mut(*cursor..end).unwrap();
s.copy_from_slice(items);
*cursor = end;
}
#[inline]
pub fn try_extend(slice: &mut [u8], cursor: &mut usize, items: &[u8]) -> Result<()> {
let end = *cursor + items.len();
let s = slice.get_mut(*cursor..end).ok_or(RapiraError::SliceLen)?;
s.copy_from_slice(items);
*cursor = end;
Ok(())
}
pub const fn static_size<const N: usize>(arr: [Option<usize>; N]) -> Option<usize> {
let mut i = 0;
let mut size = 0;
while i < arr.len() {
let item = arr[i];
match item {
Some(s) => {
size += s;
}
None => {
return None;
}
}
i += 1;
}
Some(size)
}
pub const fn enum_size<const N: usize>(arr: [Option<usize>; N]) -> Option<usize> {
let mut i = 0;
let mut size = 0;
let mut is_init = false;
while i < arr.len() {
let item = arr[i];
match item {
Some(s) => {
if !is_init {
size = s;
is_init = true;
} else if s != size {
return None;
}
}
None => {
return None;
}
}
i += 1;
}
Some(size + 1)
}
pub const fn min_size(arr: &'static [usize]) -> usize {
let mut i = 0;
let mut size = 0;
while i < arr.len() {
let item = arr[i];
size += item;
i += 1;
}
size
}
pub const fn enum_min_size(arr: &'static [usize]) -> usize {
let mut i = 0;
let mut size = 0;
let mut is_init = false;
while i < arr.len() {
let item = arr[i];
if !is_init {
size = item;
is_init = true;
} else if size < item {
size = item;
}
i += 1;
}
size + 1
}