use crate::{BYTES, TEXT, ARRAY, MAP, SIMPLE, TAGGED, SIGNED, UNSIGNED, Decoder, data::Type};
use super::{decoder::{info_of, type_of}, Error};
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum Size {
Head,
Bytes(u64),
Items(u64),
Indef
}
impl Size {
pub fn head(fst: u8) -> Result<usize, Error> {
match info_of(fst) {
0 ..= 0x17 => Ok(1),
0x18 => Ok(2),
0x19 => Ok(3),
0x1a => Ok(5),
0x1b => Ok(9),
0x1f => match type_of(fst) {
BYTES | TEXT | ARRAY | MAP | SIMPLE => Ok(1),
_ => Err(Error::message("invalid data item head"))
}
_ => Err(Error::message("invalid data item head"))
}
}
pub fn tail(head: &[u8]) -> Result<Self, Error> {
let fst = head.first().copied().ok_or_else(Error::end_of_input)?;
match type_of(fst) {
UNSIGNED | SIGNED | TAGGED | SIMPLE => Ok(Self::Head),
BYTES | TEXT => match info_of(fst) {
0x1f => Ok(Self::Indef),
info => {
let mut d = Decoder::new(&head[1 ..]);
let p = d.position();
let n = d.unsigned(info, p)?;
Ok(Self::Bytes(n))
}
}
ARRAY | MAP => match info_of(fst) {
0x1f => Ok(Self::Indef),
info => {
let mut d = Decoder::new(&head[1 ..]);
let p = d.position();
let n = d.unsigned(info, p)?;
Ok(Self::Items(n))
}
}
n => {
let t = Type::Unknown(n);
Err(Error::type_mismatch(t).at(0).with_message("unknown cbor type"))
}
}
}
}