use alloc::string::String;
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum ResourceKind {
MessageLength,
FragmentCount,
Sequence,
FragmentData,
ReceivedParts,
BufferParts,
UriLen,
}
#[derive(Debug, Clone, PartialEq, Eq)]
pub struct CborError {
kind: CborErrorKind,
detail: String,
}
impl CborError {
#[cfg_attr(
not(feature = "dcbor"),
allow(dead_code, reason = "typed layer is the only constructor caller")
)]
pub(crate) fn new(kind: CborErrorKind, detail: impl Into<String>) -> Self {
Self {
kind,
detail: detail.into(),
}
}
#[must_use]
pub const fn kind(&self) -> CborErrorKind {
self.kind
}
#[must_use]
pub fn detail(&self) -> &str {
&self.detail
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum CborErrorKind {
Decode,
Type,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub(crate) enum Poison {
Limit(ResourceKind),
DecoderState,
}
impl Poison {
pub(crate) const fn to_error(self) -> Error {
match self {
Self::Limit(kind) => Error::ResourceLimit(kind),
Self::DecoderState => Error::DecoderState,
}
}
}
#[derive(Debug, Clone, PartialEq, Eq, thiserror::Error)]
#[non_exhaustive]
#[allow(
clippy::error_impl_error,
reason = "crate-root Error is the standard library-facing error type name"
)]
pub enum Error {
#[error("invalid bytewords word")]
InvalidWord,
#[error("invalid bytewords checksum")]
InvalidBytewordsChecksum,
#[error("invalid bytewords length")]
InvalidBytewordsLength,
#[error("bytewords string is not ASCII")]
NonAscii,
#[error("empty message")]
EmptyMessage,
#[error("empty fountain part")]
EmptyPart,
#[error("invalid maximum fragment length")]
InvalidFragmentLen,
#[error("invalid sequence number")]
InvalidSequence,
#[error("fountain part inconsistent with previous parts")]
InconsistentPart,
#[error("invalid fountain part padding")]
InvalidPadding,
#[error("invalid fountain message checksum")]
InvalidMessageChecksum,
#[error("invalid fountain part CBOR")]
InvalidPartCbor,
#[error("fountain decoder internal state error")]
DecoderState,
#[error("single-part fountain encoder already emitted its only part")]
SinglePartExhausted,
#[error("decoder resource limit exceeded: {0:?}")]
ResourceLimit(ResourceKind),
#[error("invalid UR scheme")]
InvalidScheme,
#[error("UR type unspecified")]
TypeUnspecified,
#[error("invalid UR type")]
InvalidType,
#[error("invalid multi-part indices")]
InvalidIndices,
#[error("expected single-part UR")]
NotSinglePart,
#[error("unexpected UR type: expected {expected}, found {found}")]
UnexpectedType {
expected: String,
found: String,
},
#[error("dCBOR error ({kind:?}): {detail}", kind = .0.kind(), detail = .0.detail())]
Cbor(CborError),
}
pub type Result<T> = core::result::Result<T, Error>;