1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121
//! Errors possible when decoding deflate/zlib/gzip
//! streams
use alloc::string::String;
use alloc::vec;
use alloc::vec::Vec;
use core::fmt::{Debug, Display, Formatter};
/// A struct returned when decompression fails
///
/// This struct contains two fields,
///
/// - `error`:Tells you the error that actually occured.
/// - `data`: Gives you decoded data up until that point when
/// the error was encountered.
///
/// One can recover data up to the error if they so wish but
/// guarantees about data state is not given
pub struct InflateDecodeErrors
{
/// reason why decompression fails
pub error: DecodeErrorStatus,
/// Decoded data up until that decompression error
pub data: Vec<u8>
}
impl InflateDecodeErrors
{
/// Create a new decode wrapper with data being
/// how many bytes we actually decoded before hitting an error
///
/// # Arguments
/// - `error`: Error encountered during decoding
/// - `data`: Data up to that point of decoding
///
/// # Returns
/// Itself
pub fn new(error: DecodeErrorStatus, data: Vec<u8>) -> InflateDecodeErrors
{
InflateDecodeErrors { error, data }
}
/// Create a new decode wrapper with an empty vector
///
/// # Arguments
/// - `error`: Error encountered during decoding.
pub fn new_with_error(error: DecodeErrorStatus) -> InflateDecodeErrors
{
InflateDecodeErrors::new(error, vec![])
}
}
impl Debug for InflateDecodeErrors
{
fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result
{
writeln!(f, "{:?}", self.error)
}
}
pub enum DecodeErrorStatus
{
/// Input data is not enough to construct
/// a full output
InsufficientData,
/// Anything that isn't significant
Generic(&'static str),
/// Anything that isn't significant but we need to
/// pass back information to the user as to what went wrong
GenericStr(String),
///Input data was malformed.
CorruptData,
/// Limit set by the user was exceeded by
/// decompressed output
OutputLimitExceeded(usize, usize),
/// Output CRC does not match stored CRC.
///
/// Only present for zlib
MismatchedCRC(u32, u32),
/// Output Adler does not match stored adler
///
/// Only present for gzip
MismatchedAdler(u32, u32)
}
impl Debug for DecodeErrorStatus
{
fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result
{
match self
{
Self::InsufficientData => writeln!(f, "Insufficient data"),
Self::Generic(reason) => writeln!(f, "{reason}"),
Self::GenericStr(reason) => writeln!(f, "{reason}"),
Self::CorruptData => writeln!(f, "Corrupt data"),
Self::OutputLimitExceeded(limit, current) => writeln!(
f,
"Output limit exceeded, set limit was {limit} and output size is {current}"
),
Self::MismatchedCRC(expected, found) =>
{
writeln!(f, "Mismatched CRC, expected {expected} but found {found}")
}
Self::MismatchedAdler(expected, found) =>
{
writeln!(f, "Mismatched Adler, expected {expected} but found {found}")
}
}
}
}
impl Display for InflateDecodeErrors
{
#[allow(clippy::uninlined_format_args)]
fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result
{
writeln!(f, "{:?}", self)
}
}
#[cfg(feature = "std")]
impl std::error::Error for InflateDecodeErrors {}