1use crate::bit_io::GetBitsError;
4use crate::blocks::block::BlockType;
5use crate::blocks::literals_section::LiteralsSectionType;
6use crate::io::Error;
7use alloc::vec::Vec;
8use core::fmt;
9#[cfg(feature = "std")]
10use std::error::Error as StdError;
11
12#[derive(Debug)]
13#[non_exhaustive]
14pub enum FrameDescriptorError {
15 InvalidFrameContentSizeFlag {
16 got: u8,
17 },
18 ReservedBitSet,
21}
22
23impl fmt::Display for FrameDescriptorError {
24 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
25 match self {
26 Self::InvalidFrameContentSizeFlag { got } => write!(
27 f,
28 "Invalid Frame_Content_Size_Flag; Is: {got}, Should be one of: 0, 1, 2, 3"
29 ),
30 Self::ReservedBitSet => write!(
31 f,
32 "Reserved_bit of the Frame_Header_Descriptor is set; it must be zero"
33 ),
34 }
35 }
36}
37
38#[cfg(feature = "std")]
39impl StdError for FrameDescriptorError {}
40
41#[derive(Debug)]
42#[non_exhaustive]
43pub enum FrameHeaderError {
44 WindowTooBig { got: u64 },
45 WindowTooSmall { got: u64 },
46 FrameDescriptorError(FrameDescriptorError),
47 DictIdTooSmall { got: usize, expected: usize },
48 MismatchedFrameSize { got: usize, expected: u8 },
49 FrameSizeIsZero,
50 InvalidFrameSize { got: u8 },
51}
52
53impl fmt::Display for FrameHeaderError {
54 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
55 match self {
56 Self::WindowTooBig { got } => write!(
57 f,
58 "window_size bigger than allowed maximum. Is: {}, Should be lower than: {}",
59 got,
60 crate::common::MAX_WINDOW_SIZE
61 ),
62 Self::WindowTooSmall { got } => write!(
63 f,
64 "window_size smaller than allowed minimum. Is: {}, Should be greater than: {}",
65 got,
66 crate::common::MIN_WINDOW_SIZE
67 ),
68 Self::FrameDescriptorError(e) => write!(f, "{e:?}"),
69 Self::DictIdTooSmall { got, expected } => write!(
70 f,
71 "Not enough bytes in dict_id. Is: {got}, Should be: {expected}"
72 ),
73 Self::MismatchedFrameSize { got, expected } => write!(
74 f,
75 "frame_content_size does not have the right length. Is: {got}, Should be: {expected}"
76 ),
77 Self::FrameSizeIsZero => write!(f, "frame_content_size was zero"),
78 Self::InvalidFrameSize { got } => write!(
79 f,
80 "Invalid frame_content_size. Is: {got}, Should be one of 1, 2, 4, 8 bytes"
81 ),
82 }
83 }
84}
85
86#[cfg(feature = "std")]
87impl StdError for FrameHeaderError {
88 fn source(&self) -> Option<&(dyn StdError + 'static)> {
89 match self {
90 FrameHeaderError::FrameDescriptorError(source) => Some(source),
91 _ => None,
92 }
93 }
94}
95
96impl From<FrameDescriptorError> for FrameHeaderError {
97 fn from(error: FrameDescriptorError) -> Self {
98 Self::FrameDescriptorError(error)
99 }
100}
101
102#[derive(Debug)]
103#[non_exhaustive]
104pub enum ReadFrameHeaderError {
105 MagicNumberReadError(Error),
106 BadMagicNumber(u32),
107 FrameDescriptorReadError(Error),
108 InvalidFrameDescriptor(FrameDescriptorError),
109 WindowDescriptorReadError(Error),
110 DictionaryIdReadError(Error),
111 FrameContentSizeReadError(Error),
112 SkipFrame { magic_number: u32, length: u32 },
113}
114
115impl fmt::Display for ReadFrameHeaderError {
116 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
117 match self {
118 Self::MagicNumberReadError(e) => write!(f, "Error while reading magic number: {e}"),
119 Self::BadMagicNumber(e) => write!(f, "Read wrong magic number: 0x{e:X}"),
120 Self::FrameDescriptorReadError(e) => {
121 write!(f, "Error while reading frame descriptor: {e}")
122 }
123 Self::InvalidFrameDescriptor(e) => write!(f, "{e:?}"),
124 Self::WindowDescriptorReadError(e) => {
125 write!(f, "Error while reading window descriptor: {e}")
126 }
127 Self::DictionaryIdReadError(e) => write!(f, "Error while reading dictionary id: {e}"),
128 Self::FrameContentSizeReadError(e) => {
129 write!(f, "Error while reading frame content size: {e}")
130 }
131 Self::SkipFrame {
132 magic_number,
133 length,
134 } => write!(
135 f,
136 "SkippableFrame encountered with MagicNumber 0x{magic_number:X} and length {length} bytes"
137 ),
138 }
139 }
140}
141
142#[cfg(feature = "std")]
143impl StdError for ReadFrameHeaderError {
144 fn source(&self) -> Option<&(dyn StdError + 'static)> {
145 match self {
146 ReadFrameHeaderError::MagicNumberReadError(source) => Some(source),
147 ReadFrameHeaderError::FrameDescriptorReadError(source) => Some(source),
148 ReadFrameHeaderError::InvalidFrameDescriptor(source) => Some(source),
149 ReadFrameHeaderError::WindowDescriptorReadError(source) => Some(source),
150 ReadFrameHeaderError::DictionaryIdReadError(source) => Some(source),
151 ReadFrameHeaderError::FrameContentSizeReadError(source) => Some(source),
152 _ => None,
153 }
154 }
155}
156
157impl From<FrameDescriptorError> for ReadFrameHeaderError {
158 fn from(error: FrameDescriptorError) -> Self {
159 Self::InvalidFrameDescriptor(error)
160 }
161}
162
163#[derive(Debug)]
164#[non_exhaustive]
165pub enum BlockHeaderReadError {
166 ReadError(Error),
167 FoundReservedBlock,
168 BlockTypeError(BlockTypeError),
169 BlockSizeError(BlockSizeError),
170}
171
172#[cfg(feature = "std")]
173impl std::error::Error for BlockHeaderReadError {
174 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
175 match self {
176 BlockHeaderReadError::ReadError(source) => Some(source),
177 BlockHeaderReadError::BlockTypeError(source) => Some(source),
178 BlockHeaderReadError::BlockSizeError(source) => Some(source),
179 BlockHeaderReadError::FoundReservedBlock => None,
180 }
181 }
182}
183
184impl ::core::fmt::Display for BlockHeaderReadError {
185 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> ::core::fmt::Result {
186 match self {
187 BlockHeaderReadError::ReadError(_) => write!(f, "Error while reading the block header"),
188 BlockHeaderReadError::FoundReservedBlock => write!(
189 f,
190 "Reserved block occured. This is considered corruption by the documentation"
191 ),
192 BlockHeaderReadError::BlockTypeError(e) => write!(f, "Error getting block type: {e}"),
193 BlockHeaderReadError::BlockSizeError(e) => {
194 write!(f, "Error getting block content size: {e}")
195 }
196 }
197 }
198}
199
200impl From<Error> for BlockHeaderReadError {
201 fn from(val: Error) -> Self {
202 Self::ReadError(val)
203 }
204}
205
206impl From<BlockTypeError> for BlockHeaderReadError {
207 fn from(val: BlockTypeError) -> Self {
208 Self::BlockTypeError(val)
209 }
210}
211
212impl From<BlockSizeError> for BlockHeaderReadError {
213 fn from(val: BlockSizeError) -> Self {
214 Self::BlockSizeError(val)
215 }
216}
217
218#[derive(Debug)]
219#[non_exhaustive]
220pub enum BlockTypeError {
221 InvalidBlocktypeNumber { num: u8 },
222}
223
224#[cfg(feature = "std")]
225impl std::error::Error for BlockTypeError {}
226
227impl core::fmt::Display for BlockTypeError {
228 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
229 match self {
230 BlockTypeError::InvalidBlocktypeNumber { num } => {
231 write!(
232 f,
233 "Invalid Blocktype number. Is: {num}. Should be one of: 0, 1, 2, 3 (3 is reserved).",
234 )
235 }
236 }
237 }
238}
239
240#[derive(Debug)]
241#[non_exhaustive]
242pub enum BlockSizeError {
243 BlockSizeTooLarge { size: u32 },
244}
245
246#[cfg(feature = "std")]
247impl std::error::Error for BlockSizeError {}
248
249impl core::fmt::Display for BlockSizeError {
250 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
251 match self {
252 BlockSizeError::BlockSizeTooLarge { size } => {
253 write!(
254 f,
255 "Blocksize was bigger than the absolute maximum {} (128kb). Is: {}",
256 crate::common::MAX_BLOCK_SIZE,
257 size,
258 )
259 }
260 }
261 }
262}
263
264#[derive(Debug)]
265#[non_exhaustive]
266pub enum DecompressBlockError {
267 BlockContentReadError(Error),
268 MalformedSectionHeader {
269 expected_len: usize,
270 remaining_bytes: usize,
271 },
272 DecompressLiteralsError(DecompressLiteralsError),
273 LiteralsSectionParseError(LiteralsSectionParseError),
274 SequencesHeaderParseError(SequencesHeaderParseError),
275 DecodeSequenceError(DecodeSequenceError),
276 ExecuteSequencesError(ExecuteSequencesError),
277 ExpandsPastBlockMaximum {
282 size: usize,
283 maximum: usize,
284 },
285 ContentPastBlockMaximum {
289 size: usize,
290 maximum: usize,
291 },
292 LiteralsOutputOverflow {
299 tail: usize,
300 requested: usize,
301 capacity: usize,
302 },
303}
304
305#[cfg(feature = "std")]
306impl std::error::Error for DecompressBlockError {
307 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
308 match self {
309 DecompressBlockError::BlockContentReadError(source) => Some(source),
310 DecompressBlockError::DecompressLiteralsError(source) => Some(source),
311 DecompressBlockError::LiteralsSectionParseError(source) => Some(source),
312 DecompressBlockError::SequencesHeaderParseError(source) => Some(source),
313 DecompressBlockError::DecodeSequenceError(source) => Some(source),
314 DecompressBlockError::ExecuteSequencesError(source) => Some(source),
315 _ => None,
316 }
317 }
318}
319
320impl core::fmt::Display for DecompressBlockError {
321 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
322 match self {
323 DecompressBlockError::BlockContentReadError(e) => {
324 write!(f, "Error while reading the block content: {e}")
325 }
326 DecompressBlockError::MalformedSectionHeader {
327 expected_len,
328 remaining_bytes,
329 } => {
330 write!(
331 f,
332 "Malformed section header. Says literals would be this long: {expected_len} but there are only {remaining_bytes} bytes left",
333 )
334 }
335 DecompressBlockError::DecompressLiteralsError(e) => write!(f, "{e:?}"),
336 DecompressBlockError::LiteralsSectionParseError(e) => write!(f, "{e:?}"),
337 DecompressBlockError::SequencesHeaderParseError(e) => write!(f, "{e:?}"),
338 DecompressBlockError::DecodeSequenceError(e) => write!(f, "{e:?}"),
339 DecompressBlockError::ExecuteSequencesError(e) => write!(f, "{e:?}"),
340 DecompressBlockError::ExpandsPastBlockMaximum { size, maximum } => write!(
341 f,
342 "Block expands to {size} bytes, past this frame's maximum of {maximum}"
343 ),
344 DecompressBlockError::ContentPastBlockMaximum { size, maximum } => write!(
345 f,
346 "Compressed block of {size} bytes, past this frame's maximum of {maximum}"
347 ),
348 DecompressBlockError::LiteralsOutputOverflow {
349 tail,
350 requested,
351 capacity,
352 } => write!(
353 f,
354 "Literals would write past the output buffer: tail={tail}, requested={requested}, capacity={capacity}"
355 ),
356 }
357 }
358}
359
360impl From<Error> for DecompressBlockError {
361 fn from(val: Error) -> Self {
362 Self::BlockContentReadError(val)
363 }
364}
365
366impl From<DecompressLiteralsError> for DecompressBlockError {
367 fn from(val: DecompressLiteralsError) -> Self {
368 Self::DecompressLiteralsError(val)
369 }
370}
371
372impl From<LiteralsSectionParseError> for DecompressBlockError {
373 fn from(val: LiteralsSectionParseError) -> Self {
374 Self::LiteralsSectionParseError(val)
375 }
376}
377
378impl From<SequencesHeaderParseError> for DecompressBlockError {
379 fn from(val: SequencesHeaderParseError) -> Self {
380 Self::SequencesHeaderParseError(val)
381 }
382}
383
384impl From<DecodeSequenceError> for DecompressBlockError {
385 fn from(val: DecodeSequenceError) -> Self {
386 Self::DecodeSequenceError(val)
387 }
388}
389
390impl From<ExecuteSequencesError> for DecompressBlockError {
391 fn from(val: ExecuteSequencesError) -> Self {
392 Self::ExecuteSequencesError(val)
393 }
394}
395
396#[derive(Debug)]
397#[non_exhaustive]
398pub enum DecodeBlockContentError {
399 DecoderStateIsFailed,
400 ExpectedHeaderOfPreviousBlock,
401 ReadError {
402 step: BlockType,
403 source: Error,
404 },
405 DecompressBlockError(DecompressBlockError),
406 BackendOverflow {
417 step: BlockType,
418 },
419}
420
421#[cfg(feature = "std")]
422impl std::error::Error for DecodeBlockContentError {
423 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
424 match self {
425 DecodeBlockContentError::ReadError { step: _, source } => Some(source),
426 DecodeBlockContentError::DecompressBlockError(source) => Some(source),
427 _ => None,
428 }
429 }
430}
431
432impl core::fmt::Display for DecodeBlockContentError {
433 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
434 match self {
435 DecodeBlockContentError::DecoderStateIsFailed => {
436 write!(
437 f,
438 "Can't decode next block if failed along the way. Results will be nonsense",
439 )
440 }
441 DecodeBlockContentError::ExpectedHeaderOfPreviousBlock => {
442 write!(
443 f,
444 "Can't decode next block body, while expecting to decode the header of the previous block. Results will be nonsense",
445 )
446 }
447 DecodeBlockContentError::ReadError { step, source } => {
448 write!(f, "Error while reading bytes for {step}: {source}",)
449 }
450 DecodeBlockContentError::DecompressBlockError(e) => write!(f, "{e:?}"),
451 DecodeBlockContentError::BackendOverflow { step } => write!(
452 f,
453 "{step} block's decompressed payload exceeds the caller-provided output buffer",
454 ),
455 }
456 }
457}
458
459impl From<DecompressBlockError> for DecodeBlockContentError {
460 fn from(val: DecompressBlockError) -> Self {
461 Self::DecompressBlockError(val)
462 }
463}
464
465#[derive(Debug)]
466#[non_exhaustive]
467pub enum DecodeBufferError {
468 NotEnoughBytesInDictionary {
469 got: usize,
470 need: usize,
471 },
472 OffsetTooBig {
473 offset: usize,
474 buf_len: usize,
475 },
476 ZeroOffset,
477 BackendOverflow,
489 OutputBufferOverflow {
499 tail: usize,
500 requested: usize,
501 capacity: usize,
502 },
503}
504
505#[cfg(feature = "std")]
506impl std::error::Error for DecodeBufferError {}
507
508impl core::fmt::Display for DecodeBufferError {
509 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
510 match self {
511 DecodeBufferError::NotEnoughBytesInDictionary { got, need } => {
512 write!(
513 f,
514 "Need {need} bytes from the dictionary but it is only {got} bytes long",
515 )
516 }
517 DecodeBufferError::OffsetTooBig { offset, buf_len } => {
518 write!(f, "offset: {offset} bigger than buffer: {buf_len}",)
519 }
520 DecodeBufferError::ZeroOffset => {
521 write!(f, "Illegal offset: 0 found")
522 }
523 DecodeBufferError::BackendOverflow => {
524 write!(
525 f,
526 "Match repeat would overflow the output buffer's fixed capacity"
527 )
528 }
529 DecodeBufferError::OutputBufferOverflow {
530 tail,
531 requested,
532 capacity,
533 } => {
534 write!(
535 f,
536 "Match repeat would write past fixed-capacity buffer: tail={tail}, requested={requested}, capacity={capacity}"
537 )
538 }
539 }
540 }
541}
542
543#[derive(Debug)]
544#[non_exhaustive]
545pub enum DictionaryDecodeError {
546 BadMagicNum { got: [u8; 4] },
547 DictionaryTooSmall { got: usize, need: usize },
548 ZeroDictionaryId,
549 ZeroRepeatOffsetInDictionary { index: u8 },
550 FSETableError(FSETableError),
551 HuffmanTableError(HuffmanTableError),
552}
553
554#[cfg(feature = "std")]
555impl std::error::Error for DictionaryDecodeError {
556 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
557 match self {
558 DictionaryDecodeError::FSETableError(source) => Some(source),
559 DictionaryDecodeError::HuffmanTableError(source) => Some(source),
560 _ => None,
561 }
562 }
563}
564
565impl core::fmt::Display for DictionaryDecodeError {
566 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
567 match self {
568 DictionaryDecodeError::BadMagicNum { got } => {
569 write!(
570 f,
571 "Bad magic_num at start of the dictionary; Got: {:#04X?}, Expected: {:#04x?}",
572 got,
573 crate::decoding::dictionary::MAGIC_NUM,
574 )
575 }
576 DictionaryDecodeError::DictionaryTooSmall { got, need } => {
577 write!(
578 f,
579 "Dictionary is too small: got {got} bytes, need at least {need} bytes",
580 )
581 }
582 DictionaryDecodeError::ZeroDictionaryId => {
583 write!(f, "Dictionary id must be non-zero")
584 }
585 DictionaryDecodeError::ZeroRepeatOffsetInDictionary { index } => {
586 write!(f, "Dictionary repeat offset rep{index} must be non-zero")
587 }
588 DictionaryDecodeError::FSETableError(e) => write!(f, "{e:?}"),
589 DictionaryDecodeError::HuffmanTableError(e) => write!(f, "{e:?}"),
590 }
591 }
592}
593
594impl From<FSETableError> for DictionaryDecodeError {
595 fn from(val: FSETableError) -> Self {
596 Self::FSETableError(val)
597 }
598}
599
600impl From<HuffmanTableError> for DictionaryDecodeError {
601 fn from(val: HuffmanTableError) -> Self {
602 Self::HuffmanTableError(val)
603 }
604}
605
606#[derive(Debug)]
607#[non_exhaustive]
608pub enum FrameDecoderError {
609 ReadFrameHeaderError(ReadFrameHeaderError),
610 FrameHeaderError(FrameHeaderError),
611 #[non_exhaustive]
615 WindowSizeTooBig {
616 requested: u64,
618 limit: u64,
620 },
621 WindowCeilingOutOfRange {
625 requested: u64,
627 },
628 DictionaryDecodeError(DictionaryDecodeError),
629 FailedToReadBlockHeader(BlockHeaderReadError),
630 FailedToReadBlockBody(DecodeBlockContentError),
631 FailedToReadChecksum(Error),
632 NotYetInitialized,
633 FailedToInitialize(FrameHeaderError),
634 FailedToDrainDecodebuffer(Error),
635 FailedToSkipFrame,
636 TargetTooSmall,
637 FrameContentSizeMismatch {
645 declared: u64,
646 produced: u64,
647 },
648 ChecksumMismatch {
655 expected: u32,
656 calculated: u32,
657 },
658 DictNotProvided {
659 dict_id: u32,
660 },
661 DictIdMismatch {
662 expected: u32,
663 provided: u32,
664 },
665 DictAlreadyRegistered {
666 dict_id: u32,
667 },
668 #[cfg(feature = "lsm")]
681 UnexpectedDictId {
682 expected: Option<u32>,
683 found: Option<u32>,
684 },
685 #[cfg(feature = "lsm")]
692 UnexpectedWindowDescriptor {
693 expected: u8,
694 found: Option<u8>,
695 },
696 #[cfg(feature = "lsm")]
704 FailedToReadBlockHeaderAt {
705 source: BlockHeaderReadError,
706 block_index: u32,
707 frame_offset: u32,
708 },
709 #[cfg(feature = "lsm")]
717 FailedToReadBlockBodyAt {
718 source: DecodeBlockContentError,
719 block_index: u32,
720 frame_offset: u32,
721 block: crate::encoding::frame_emit_info::FrameBlock,
722 },
723 #[cfg(feature = "lsm")]
730 InvalidBlockRange {
731 start_block: u32,
732 end_block: u32,
733 },
734 #[cfg(feature = "lsm")]
744 ResumeWindowTooShort {
745 got: usize,
746 need: usize,
747 },
748 #[cfg(feature = "lsm")]
760 ResumeFrameMismatch,
761 #[cfg(feature = "lsm")]
775 ResumeUnidentifiedDictionary,
776}
777
778#[cfg(feature = "std")]
779impl StdError for FrameDecoderError {
780 fn source(&self) -> Option<&(dyn StdError + 'static)> {
781 match self {
782 FrameDecoderError::ReadFrameHeaderError(source) => Some(source),
783 FrameDecoderError::FrameHeaderError(source) => Some(source),
784 FrameDecoderError::DictionaryDecodeError(source) => Some(source),
785 FrameDecoderError::FailedToReadBlockHeader(source) => Some(source),
786 FrameDecoderError::FailedToReadBlockBody(source) => Some(source),
787 #[cfg(feature = "lsm")]
788 FrameDecoderError::FailedToReadBlockHeaderAt { source, .. } => Some(source),
789 #[cfg(feature = "lsm")]
790 FrameDecoderError::FailedToReadBlockBodyAt { source, .. } => Some(source),
791 FrameDecoderError::FailedToReadChecksum(source) => Some(source),
792 FrameDecoderError::FailedToInitialize(source) => Some(source),
793 FrameDecoderError::FailedToDrainDecodebuffer(source) => Some(source),
794 _ => None,
795 }
796 }
797}
798
799impl core::fmt::Display for FrameDecoderError {
800 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> ::core::fmt::Result {
801 match self {
802 FrameDecoderError::ReadFrameHeaderError(e) => {
803 write!(f, "{e:?}")
804 }
805 FrameDecoderError::FrameHeaderError(e) => {
806 write!(f, "{e:?}")
807 }
808 FrameDecoderError::WindowSizeTooBig { requested, limit } => {
809 write!(
810 f,
811 "Specified window_size is too big; Requested: {requested}, Allowed: {limit}",
812 )
813 }
814 FrameDecoderError::WindowCeilingOutOfRange { requested } => {
815 write!(
816 f,
817 "window ceiling {requested} is outside {}..={}",
818 crate::common::MIN_WINDOW_SIZE,
819 crate::common::MAX_DECODER_WINDOW_SIZE,
820 )
821 }
822 FrameDecoderError::DictionaryDecodeError(e) => {
823 write!(f, "{e:?}")
824 }
825 FrameDecoderError::FailedToReadBlockHeader(e) => {
826 write!(f, "Failed to parse/decode block body: {e}")
827 }
828 FrameDecoderError::FailedToReadBlockBody(e) => {
829 write!(f, "Failed to parse block header: {e}")
830 }
831 #[cfg(feature = "lsm")]
832 FrameDecoderError::FailedToReadBlockHeaderAt {
833 source,
834 block_index,
835 frame_offset,
836 } => {
837 write!(
838 f,
839 "Failed to read block header at block {block_index} (frame offset {frame_offset}): {source}"
840 )
841 }
842 #[cfg(feature = "lsm")]
843 FrameDecoderError::FailedToReadBlockBodyAt {
844 source,
845 block_index,
846 frame_offset,
847 ..
848 } => {
849 write!(
850 f,
851 "Failed to decode block body at block {block_index} (frame offset {frame_offset}): {source}"
852 )
853 }
854 FrameDecoderError::FailedToReadChecksum(e) => {
855 write!(f, "Failed to read checksum: {e}")
856 }
857 FrameDecoderError::NotYetInitialized => {
858 write!(f, "Decoder must initialized or reset before using it",)
859 }
860 FrameDecoderError::FailedToInitialize(e) => {
861 write!(f, "Decoder encountered error while initializing: {e}")
862 }
863 FrameDecoderError::FailedToDrainDecodebuffer(e) => {
864 write!(
865 f,
866 "Decoder encountered error while draining the decodebuffer: {e}",
867 )
868 }
869 FrameDecoderError::FailedToSkipFrame => {
870 write!(
871 f,
872 "Failed to skip bytes for the length given in the frame header"
873 )
874 }
875 FrameDecoderError::TargetTooSmall => {
876 write!(
877 f,
878 "Target must have at least as many bytes as the content size reported by the frame"
879 )
880 }
881 FrameDecoderError::FrameContentSizeMismatch { declared, produced } => {
882 write!(
883 f,
884 "Frame content size mismatch (corrupt frame): declared {declared} bytes, blocks summed to {produced} bytes"
885 )
886 }
887 FrameDecoderError::ChecksumMismatch {
888 expected,
889 calculated,
890 } => {
891 write!(
892 f,
893 "Content checksum mismatch (corrupt frame): frame stored 0x{expected:08X}, decoder calculated 0x{calculated:08X}"
894 )
895 }
896 FrameDecoderError::DictNotProvided { dict_id } => {
897 write!(
898 f,
899 "Frame header specified dictionary id 0x{dict_id:X} that wasn't provided via add_dict()/add_dict_from_bytes() (or add_dict_handle() on atomic targets) or reset_with_dict_handle()/decode_all_with_dict_handle()/decode_all_with_dict_bytes()"
900 )
901 }
902 FrameDecoderError::DictIdMismatch { expected, provided } => {
903 write!(
904 f,
905 "Frame header dictionary id 0x{expected:X} does not match provided dictionary id 0x{provided:X}"
906 )
907 }
908 FrameDecoderError::DictAlreadyRegistered { dict_id } => {
909 write!(
910 f,
911 "Dictionary id 0x{dict_id:X} already registered in decoder"
912 )
913 }
914 #[cfg(feature = "lsm")]
915 FrameDecoderError::UnexpectedDictId { expected, found } => {
916 write!(f, "Frame header dict_id mismatch: expected ")?;
917 match expected {
918 Some(id) => write!(f, "0x{id:X}")?,
919 None => write!(f, "<none>")?,
920 }
921 write!(f, ", found ")?;
922 match found {
923 Some(id) => write!(f, "0x{id:X}"),
924 None => write!(f, "<none>"),
925 }
926 }
927 #[cfg(feature = "lsm")]
928 FrameDecoderError::UnexpectedWindowDescriptor { expected, found } => {
929 write!(
930 f,
931 "Frame header window_descriptor mismatch: expected 0x{expected:02X}, found "
932 )?;
933 match found {
934 Some(byte) => write!(f, "0x{byte:02X}"),
935 None => write!(f, "<none> (single-segment frame omits window_descriptor)"),
936 }
937 }
938 #[cfg(feature = "lsm")]
939 FrameDecoderError::InvalidBlockRange {
940 start_block,
941 end_block,
942 } => {
943 write!(
944 f,
945 "Invalid block range for partial decode: start_block {start_block} > end_block {end_block}"
946 )
947 }
948 #[cfg(feature = "lsm")]
949 FrameDecoderError::ResumeWindowTooShort { got, need } => {
950 write!(
951 f,
952 "resume window_prime too short: got {got} bytes, need at least {need}"
953 )
954 }
955 #[cfg(feature = "lsm")]
956 FrameDecoderError::ResumeFrameMismatch => {
957 write!(
958 f,
959 "resume state was captured from a frame with a different decode shape than the current frame"
960 )
961 }
962 #[cfg(feature = "lsm")]
963 FrameDecoderError::ResumeUnidentifiedDictionary => {
964 write!(
965 f,
966 "a dictionary with no ID cannot be told from another one, so it cannot carry a resume state across frames"
967 )
968 }
969 }
970 }
971}
972
973impl From<DictionaryDecodeError> for FrameDecoderError {
974 fn from(val: DictionaryDecodeError) -> Self {
975 Self::DictionaryDecodeError(val)
976 }
977}
978
979impl From<BlockHeaderReadError> for FrameDecoderError {
980 fn from(val: BlockHeaderReadError) -> Self {
981 Self::FailedToReadBlockHeader(val)
982 }
983}
984
985impl From<FrameHeaderError> for FrameDecoderError {
986 fn from(val: FrameHeaderError) -> Self {
987 Self::FrameHeaderError(val)
988 }
989}
990
991impl From<ReadFrameHeaderError> for FrameDecoderError {
992 fn from(val: ReadFrameHeaderError) -> Self {
993 Self::ReadFrameHeaderError(val)
994 }
995}
996
997#[derive(Debug)]
998#[non_exhaustive]
999pub enum DecompressLiteralsError {
1000 MissingCompressedSize,
1001 MissingNumStreams,
1002 GetBitsError(GetBitsError),
1003 HuffmanTableError(HuffmanTableError),
1004 HuffmanDecoderError(HuffmanDecoderError),
1005 UninitializedHuffmanTable,
1006 MissingBytesForJumpHeader { got: usize },
1007 MissingBytesForLiterals { got: usize, needed: usize },
1008 ExtraPadding { skipped_bits: i32 },
1009 BitstreamReadMismatch { read_til: isize, expected: isize },
1010 DecodedLiteralCountMismatch { decoded: usize, expected: usize },
1011}
1012
1013#[cfg(feature = "std")]
1014impl std::error::Error for DecompressLiteralsError {
1015 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1016 match self {
1017 DecompressLiteralsError::GetBitsError(source) => Some(source),
1018 DecompressLiteralsError::HuffmanTableError(source) => Some(source),
1019 DecompressLiteralsError::HuffmanDecoderError(source) => Some(source),
1020 _ => None,
1021 }
1022 }
1023}
1024impl core::fmt::Display for DecompressLiteralsError {
1025 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1026 match self {
1027 DecompressLiteralsError::MissingCompressedSize => {
1028 write!(
1029 f,
1030 "compressed size was none even though it must be set to something for compressed literals",
1031 )
1032 }
1033 DecompressLiteralsError::MissingNumStreams => {
1034 write!(
1035 f,
1036 "num_streams was none even though it must be set to something (1 or 4) for compressed literals",
1037 )
1038 }
1039 DecompressLiteralsError::GetBitsError(e) => write!(f, "{e:?}"),
1040 DecompressLiteralsError::HuffmanTableError(e) => write!(f, "{e:?}"),
1041 DecompressLiteralsError::HuffmanDecoderError(e) => write!(f, "{e:?}"),
1042 DecompressLiteralsError::UninitializedHuffmanTable => {
1043 write!(
1044 f,
1045 "Tried to reuse huffman table but it was never initialized",
1046 )
1047 }
1048 DecompressLiteralsError::MissingBytesForJumpHeader { got } => {
1049 write!(f, "Need 6 bytes to decode jump header, got {got} bytes",)
1050 }
1051 DecompressLiteralsError::MissingBytesForLiterals { got, needed } => {
1052 write!(
1053 f,
1054 "Need at least {needed} bytes to decode literals. Have: {got} bytes",
1055 )
1056 }
1057 DecompressLiteralsError::ExtraPadding { skipped_bits } => {
1058 write!(
1059 f,
1060 "Padding at the end of the sequence_section was more than a byte long: {skipped_bits} bits. Probably caused by data corruption",
1061 )
1062 }
1063 DecompressLiteralsError::BitstreamReadMismatch { read_til, expected } => {
1064 write!(
1065 f,
1066 "Bitstream was read till: {read_til}, should have been: {expected}",
1067 )
1068 }
1069 DecompressLiteralsError::DecodedLiteralCountMismatch { decoded, expected } => {
1070 write!(
1071 f,
1072 "Did not decode enough literals: {decoded}, Should have been: {expected}",
1073 )
1074 }
1075 }
1076 }
1077}
1078
1079impl From<HuffmanDecoderError> for DecompressLiteralsError {
1080 fn from(val: HuffmanDecoderError) -> Self {
1081 Self::HuffmanDecoderError(val)
1082 }
1083}
1084
1085impl From<GetBitsError> for DecompressLiteralsError {
1086 fn from(val: GetBitsError) -> Self {
1087 Self::GetBitsError(val)
1088 }
1089}
1090
1091impl From<HuffmanTableError> for DecompressLiteralsError {
1092 fn from(val: HuffmanTableError) -> Self {
1093 Self::HuffmanTableError(val)
1094 }
1095}
1096
1097#[derive(Debug)]
1098#[non_exhaustive]
1099pub enum ExecuteSequencesError {
1100 DecodebufferError(DecodeBufferError),
1101 NotEnoughBytesForSequence {
1102 wanted: usize,
1103 have: usize,
1104 },
1105 ZeroOffset,
1106 OutputBufferOverflow {
1116 tail: usize,
1117 requested: usize,
1118 capacity: usize,
1119 },
1120}
1121
1122impl core::fmt::Display for ExecuteSequencesError {
1123 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1124 match self {
1125 ExecuteSequencesError::DecodebufferError(e) => {
1126 write!(f, "{e:?}")
1127 }
1128 ExecuteSequencesError::NotEnoughBytesForSequence { wanted, have } => {
1129 write!(
1130 f,
1131 "Sequence wants to copy up to byte {wanted}. Bytes in literalsbuffer: {have}"
1132 )
1133 }
1134 ExecuteSequencesError::ZeroOffset => {
1135 write!(f, "Illegal offset: 0 found")
1136 }
1137 ExecuteSequencesError::OutputBufferOverflow {
1138 tail,
1139 requested,
1140 capacity,
1141 } => {
1142 write!(
1143 f,
1144 "Inline sequence would write past the output buffer: tail={tail}, requested={requested}, capacity={capacity}"
1145 )
1146 }
1147 }
1148 }
1149}
1150
1151#[cfg(feature = "std")]
1152impl std::error::Error for ExecuteSequencesError {
1153 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1154 match self {
1155 ExecuteSequencesError::DecodebufferError(source) => Some(source),
1156 _ => None,
1157 }
1158 }
1159}
1160
1161impl From<DecodeBufferError> for ExecuteSequencesError {
1162 fn from(val: DecodeBufferError) -> Self {
1163 Self::DecodebufferError(val)
1164 }
1165}
1166
1167impl From<crate::decoding::buffer_backend::BackendOverflow> for ExecuteSequencesError {
1168 fn from(val: crate::decoding::buffer_backend::BackendOverflow) -> Self {
1169 Self::OutputBufferOverflow {
1170 tail: val.tail,
1171 requested: val.requested,
1172 capacity: val.capacity,
1173 }
1174 }
1175}
1176
1177impl ExecuteSequencesError {
1178 pub(crate) fn output_overflow_requested(&self) -> Option<usize> {
1192 match self {
1193 ExecuteSequencesError::OutputBufferOverflow { requested, .. } => Some(*requested),
1194 ExecuteSequencesError::DecodebufferError(DecodeBufferError::OutputBufferOverflow {
1195 requested,
1196 ..
1197 }) => Some(*requested),
1198 _ => None,
1199 }
1200 }
1201}
1202
1203#[derive(Debug)]
1204#[non_exhaustive]
1205pub enum DecodeSequenceError {
1206 GetBitsError(GetBitsError),
1207 FSEDecoderError(FSEDecoderError),
1208 FSETableError(FSETableError),
1209 ExtraPadding {
1210 skipped_bits: i32,
1211 },
1212 UnsupportedOffset {
1213 offset_code: u8,
1214 },
1215 ZeroOffset,
1216 NotEnoughBytesForNumSequences,
1217 ExtraBits {
1218 bits_remaining: isize,
1219 },
1220 MissingCompressionMode,
1221 MissingByteForRleLlTable,
1222 MissingByteForRleOfTable,
1223 MissingByteForRleMlTable,
1224 InvalidRleCode {
1228 axis: &'static str,
1229 code: u8,
1230 },
1231}
1232
1233#[cfg(feature = "std")]
1234impl std::error::Error for DecodeSequenceError {
1235 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1236 match self {
1237 DecodeSequenceError::GetBitsError(source) => Some(source),
1238 DecodeSequenceError::FSEDecoderError(source) => Some(source),
1239 DecodeSequenceError::FSETableError(source) => Some(source),
1240 _ => None,
1241 }
1242 }
1243}
1244
1245impl core::fmt::Display for DecodeSequenceError {
1246 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1247 match self {
1248 DecodeSequenceError::GetBitsError(e) => write!(f, "{e:?}"),
1249 DecodeSequenceError::FSEDecoderError(e) => write!(f, "{e:?}"),
1250 DecodeSequenceError::FSETableError(e) => write!(f, "{e:?}"),
1251 DecodeSequenceError::ExtraPadding { skipped_bits } => {
1252 write!(
1253 f,
1254 "Padding at the end of the sequence_section was more than a byte long: {skipped_bits} bits. Probably caused by data corruption",
1255 )
1256 }
1257 DecodeSequenceError::UnsupportedOffset { offset_code } => {
1258 write!(
1259 f,
1260 "Do not support offsets bigger than 1<<32; got: {offset_code}",
1261 )
1262 }
1263 DecodeSequenceError::ZeroOffset => write!(
1264 f,
1265 "Read an offset == 0. That is an illegal value for offsets"
1266 ),
1267 DecodeSequenceError::NotEnoughBytesForNumSequences => write!(
1268 f,
1269 "Bytestream did not contain enough bytes to decode num_sequences"
1270 ),
1271 DecodeSequenceError::ExtraBits { bits_remaining } => write!(f, "{bits_remaining}"),
1272 DecodeSequenceError::MissingCompressionMode => write!(
1273 f,
1274 "compression modes are none but they must be set to something"
1275 ),
1276 DecodeSequenceError::MissingByteForRleLlTable => {
1277 write!(f, "Need a byte to read for RLE ll table")
1278 }
1279 DecodeSequenceError::MissingByteForRleOfTable => {
1280 write!(f, "Need a byte to read for RLE of table")
1281 }
1282 DecodeSequenceError::MissingByteForRleMlTable => {
1283 write!(f, "Need a byte to read for RLE ml table")
1284 }
1285 DecodeSequenceError::InvalidRleCode { axis, code } => {
1286 write!(f, "RLE {axis} table code {code} is out of range")
1287 }
1288 }
1289 }
1290}
1291
1292impl From<GetBitsError> for DecodeSequenceError {
1293 fn from(val: GetBitsError) -> Self {
1294 Self::GetBitsError(val)
1295 }
1296}
1297
1298impl From<FSETableError> for DecodeSequenceError {
1299 fn from(val: FSETableError) -> Self {
1300 Self::FSETableError(val)
1301 }
1302}
1303
1304impl From<FSEDecoderError> for DecodeSequenceError {
1305 fn from(val: FSEDecoderError) -> Self {
1306 Self::FSEDecoderError(val)
1307 }
1308}
1309
1310#[derive(Debug)]
1311#[non_exhaustive]
1312pub enum LiteralsSectionParseError {
1313 IllegalLiteralSectionType { got: u8 },
1314 GetBitsError(GetBitsError),
1315 NotEnoughBytes { have: usize, need: u8 },
1316}
1317
1318#[cfg(feature = "std")]
1319impl std::error::Error for LiteralsSectionParseError {
1320 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1321 match self {
1322 LiteralsSectionParseError::GetBitsError(source) => Some(source),
1323 _ => None,
1324 }
1325 }
1326}
1327impl core::fmt::Display for LiteralsSectionParseError {
1328 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1329 match self {
1330 LiteralsSectionParseError::IllegalLiteralSectionType { got } => {
1331 write!(
1332 f,
1333 "Illegal literalssectiontype. Is: {got}, must be in: 0, 1, 2, 3"
1334 )
1335 }
1336 LiteralsSectionParseError::GetBitsError(e) => write!(f, "{e:?}"),
1337 LiteralsSectionParseError::NotEnoughBytes { have, need } => {
1338 write!(
1339 f,
1340 "Not enough byte to parse the literals section header. Have: {have}, Need: {need}",
1341 )
1342 }
1343 }
1344 }
1345}
1346
1347impl From<GetBitsError> for LiteralsSectionParseError {
1348 fn from(val: GetBitsError) -> Self {
1349 Self::GetBitsError(val)
1350 }
1351}
1352
1353impl core::fmt::Display for LiteralsSectionType {
1354 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> Result<(), core::fmt::Error> {
1355 match self {
1356 LiteralsSectionType::Compressed => write!(f, "Compressed"),
1357 LiteralsSectionType::Raw => write!(f, "Raw"),
1358 LiteralsSectionType::RLE => write!(f, "RLE"),
1359 LiteralsSectionType::Treeless => write!(f, "Treeless"),
1360 }
1361 }
1362}
1363
1364#[derive(Debug)]
1365#[non_exhaustive]
1366pub enum SequencesHeaderParseError {
1367 NotEnoughBytes { need_at_least: u8, got: usize },
1368}
1369
1370#[cfg(feature = "std")]
1371impl std::error::Error for SequencesHeaderParseError {}
1372
1373impl core::fmt::Display for SequencesHeaderParseError {
1374 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1375 match self {
1376 SequencesHeaderParseError::NotEnoughBytes { need_at_least, got } => {
1377 write!(
1378 f,
1379 "source must have at least {need_at_least} bytes to parse header; got {got} bytes",
1380 )
1381 }
1382 }
1383 }
1384}
1385
1386#[derive(Debug)]
1387#[non_exhaustive]
1388pub enum FSETableError {
1389 AccLogIsZero,
1390 AccLogTooBig {
1391 got: u8,
1392 max: u8,
1393 },
1394 GetBitsError(GetBitsError),
1395 ProbabilityCounterMismatch {
1396 got: u32,
1397 expected_sum: u32,
1398 symbol_probabilities: Vec<i32>,
1399 },
1400 TooManySymbols {
1401 got: usize,
1402 },
1403 InvalidProbability {
1408 value: i32,
1409 table_size: u32,
1410 accuracy_log: u8,
1411 },
1412 TableInvariantViolation {
1420 prob: i32,
1421 symbol: u8,
1422 num_bits: u8,
1423 accuracy_log: u8,
1424 },
1425}
1426
1427#[cfg(feature = "std")]
1428impl std::error::Error for FSETableError {
1429 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1430 match self {
1431 FSETableError::GetBitsError(source) => Some(source),
1432 _ => None,
1433 }
1434 }
1435}
1436
1437impl core::fmt::Display for FSETableError {
1438 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1439 match self {
1440 FSETableError::AccLogIsZero => write!(f, "Acclog must be at least 1"),
1441 FSETableError::AccLogTooBig { got, max } => {
1442 write!(
1443 f,
1444 "Found FSE acc_log: {got} bigger than allowed maximum in this case: {max}"
1445 )
1446 }
1447 FSETableError::GetBitsError(e) => write!(f, "{e:?}"),
1448 FSETableError::ProbabilityCounterMismatch {
1449 got,
1450 expected_sum,
1451 symbol_probabilities,
1452 } => {
1453 write!(
1454 f,
1455 "FSE probability sum mismatch: got {got}, expected {expected_sum}. Indicates corrupted data or an invalid distribution\n {symbol_probabilities:?}",
1456 )
1457 }
1458 FSETableError::TooManySymbols { got } => {
1459 write!(
1460 f,
1461 "There are too many symbols in this distribution: {got}. Max: 256",
1462 )
1463 }
1464 FSETableError::InvalidProbability {
1465 value,
1466 table_size,
1467 accuracy_log,
1468 } => {
1469 write!(
1470 f,
1471 "FSE probability value {value} is outside the RFC 8878 allowed set (must be -1, 0, or in 1..={table_size}; accuracy_log={accuracy_log})",
1472 )
1473 }
1474 FSETableError::TableInvariantViolation {
1475 prob,
1476 symbol,
1477 num_bits,
1478 accuracy_log,
1479 } => {
1480 write!(
1481 f,
1482 "FSE table invariant violation: symbol {symbol} (prob {prob}) produced num_bits {num_bits} > accuracy_log {accuracy_log}",
1483 )
1484 }
1485 }
1486 }
1487}
1488
1489impl From<GetBitsError> for FSETableError {
1490 fn from(val: GetBitsError) -> Self {
1491 Self::GetBitsError(val)
1492 }
1493}
1494
1495#[derive(Debug)]
1496#[non_exhaustive]
1497pub enum FSEDecoderError {
1498 GetBitsError(GetBitsError),
1499 TableIsUninitialized,
1500 InvalidTableShape {
1506 decode_len: usize,
1507 accuracy_log: u8,
1508 },
1509}
1510
1511#[cfg(feature = "std")]
1512impl std::error::Error for FSEDecoderError {
1513 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
1514 match self {
1515 FSEDecoderError::GetBitsError(source) => Some(source),
1516 _ => None,
1517 }
1518 }
1519}
1520
1521impl core::fmt::Display for FSEDecoderError {
1522 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1523 match self {
1524 FSEDecoderError::GetBitsError(e) => write!(f, "{e:?}"),
1525 FSEDecoderError::TableIsUninitialized => {
1526 write!(f, "Tried to use an uninitialized table!")
1527 }
1528 FSEDecoderError::InvalidTableShape {
1529 decode_len,
1530 accuracy_log,
1531 } => match 1usize.checked_shl((*accuracy_log).into()) {
1532 Some(expected) => write!(
1533 f,
1534 "FSETable shape invariant violated: decode.len() = {decode_len}, expected 1 << accuracy_log = {expected} (accuracy_log = {accuracy_log})",
1535 ),
1536 None => write!(
1537 f,
1538 "FSETable shape invariant violated: decode.len() = {decode_len}, accuracy_log = {accuracy_log} overflows 1 << accuracy_log for usize",
1539 ),
1540 },
1541 }
1542 }
1543}
1544
1545impl From<GetBitsError> for FSEDecoderError {
1546 fn from(val: GetBitsError) -> Self {
1547 Self::GetBitsError(val)
1548 }
1549}
1550
1551#[derive(Debug)]
1552#[non_exhaustive]
1553pub enum HuffmanTableError {
1554 GetBitsError(GetBitsError),
1555 FSEDecoderError(FSEDecoderError),
1556 FSETableError(FSETableError),
1557 SourceIsEmpty,
1558 NotEnoughBytesForWeights {
1559 got_bytes: usize,
1560 expected_bytes: u8,
1561 },
1562 ExtraPadding {
1563 skipped_bits: i32,
1564 },
1565 TooManyWeights {
1566 got: usize,
1567 },
1568 MissingWeights,
1569 LeftoverIsNotAPowerOf2 {
1570 got: u32,
1571 },
1572 NotEnoughBytesToDecompressWeights {
1573 have: usize,
1574 need: usize,
1575 },
1576 FSETableUsedTooManyBytes {
1577 used: usize,
1578 available_bytes: u8,
1579 },
1580 NotEnoughBytesInSource {
1581 got: usize,
1582 need: usize,
1583 },
1584 WeightBiggerThanMaxNumBits {
1585 got: u8,
1586 },
1587 MaxBitsTooHigh {
1588 got: u8,
1589 },
1590}
1591
1592#[cfg(feature = "std")]
1593impl StdError for HuffmanTableError {
1594 fn source(&self) -> Option<&(dyn StdError + 'static)> {
1595 match self {
1596 HuffmanTableError::GetBitsError(source) => Some(source),
1597 HuffmanTableError::FSEDecoderError(source) => Some(source),
1598 HuffmanTableError::FSETableError(source) => Some(source),
1599 _ => None,
1600 }
1601 }
1602}
1603
1604impl core::fmt::Display for HuffmanTableError {
1605 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> ::core::fmt::Result {
1606 match self {
1607 HuffmanTableError::GetBitsError(e) => write!(f, "{e:?}"),
1608 HuffmanTableError::FSEDecoderError(e) => write!(f, "{e:?}"),
1609 HuffmanTableError::FSETableError(e) => write!(f, "{e:?}"),
1610 HuffmanTableError::SourceIsEmpty => write!(f, "Source needs to have at least one byte"),
1611 HuffmanTableError::NotEnoughBytesForWeights {
1612 got_bytes,
1613 expected_bytes,
1614 } => {
1615 write!(
1616 f,
1617 "Header says there should be {expected_bytes} bytes for the weights but there are only {got_bytes} bytes in the stream"
1618 )
1619 }
1620 HuffmanTableError::ExtraPadding { skipped_bits } => {
1621 write!(
1622 f,
1623 "Padding at the end of the sequence_section was more than a byte long: {skipped_bits} bits. Probably caused by data corruption",
1624 )
1625 }
1626 HuffmanTableError::TooManyWeights { got } => {
1627 write!(
1628 f,
1629 "More than 255 weights decoded (got {got} weights). Stream is probably corrupted",
1630 )
1631 }
1632 HuffmanTableError::MissingWeights => {
1633 write!(f, "Can\'t build huffman table without any weights")
1634 }
1635 HuffmanTableError::LeftoverIsNotAPowerOf2 { got } => {
1636 write!(f, "Leftover must be power of two but is: {got}")
1637 }
1638 HuffmanTableError::NotEnoughBytesToDecompressWeights { have, need } => {
1639 write!(
1640 f,
1641 "Not enough bytes in stream to decompress weights. Is: {have}, Should be: {need}",
1642 )
1643 }
1644 HuffmanTableError::FSETableUsedTooManyBytes {
1645 used,
1646 available_bytes,
1647 } => {
1648 write!(
1649 f,
1650 "FSE table used more bytes: {used} than were meant to be used for the whole stream of huffman weights ({available_bytes})",
1651 )
1652 }
1653 HuffmanTableError::NotEnoughBytesInSource { got, need } => {
1654 write!(f, "Source needs to have at least {need} bytes, got: {got}",)
1655 }
1656 HuffmanTableError::WeightBiggerThanMaxNumBits { got } => {
1657 write!(
1658 f,
1659 "Cant have weight: {} bigger than max_num_bits: {}",
1660 got,
1661 crate::huff0::MAX_MAX_NUM_BITS,
1662 )
1663 }
1664 HuffmanTableError::MaxBitsTooHigh { got } => {
1665 write!(
1666 f,
1667 "max_bits derived from weights is: {} should be lower than: {}",
1668 got,
1669 crate::huff0::MAX_MAX_NUM_BITS,
1670 )
1671 }
1672 }
1673 }
1674}
1675
1676impl From<GetBitsError> for HuffmanTableError {
1677 fn from(val: GetBitsError) -> Self {
1678 Self::GetBitsError(val)
1679 }
1680}
1681
1682impl From<FSEDecoderError> for HuffmanTableError {
1683 fn from(val: FSEDecoderError) -> Self {
1684 Self::FSEDecoderError(val)
1685 }
1686}
1687
1688impl From<FSETableError> for HuffmanTableError {
1689 fn from(val: FSETableError) -> Self {
1690 Self::FSETableError(val)
1691 }
1692}
1693
1694#[derive(Debug)]
1695#[non_exhaustive]
1696pub enum HuffmanDecoderError {
1697 GetBitsError(GetBitsError),
1698}
1699
1700impl core::fmt::Display for HuffmanDecoderError {
1701 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1702 match self {
1703 HuffmanDecoderError::GetBitsError(e) => write!(f, "{e:?}"),
1704 }
1705 }
1706}
1707
1708#[cfg(feature = "std")]
1709impl StdError for HuffmanDecoderError {
1710 fn source(&self) -> Option<&(dyn StdError + 'static)> {
1711 match self {
1712 HuffmanDecoderError::GetBitsError(source) => Some(source),
1713 }
1714 }
1715}
1716
1717impl From<GetBitsError> for HuffmanDecoderError {
1718 fn from(val: GetBitsError) -> Self {
1719 Self::GetBitsError(val)
1720 }
1721}
1722
1723#[cfg(test)]
1724mod tests;