1use oximedia_core::{OxiError, OxiResult};
4
5#[derive(Debug, Clone)]
36pub struct BitReader<'a> {
37 data: &'a [u8],
39 byte_pos: usize,
41 bit_pos: u8,
43}
44
45#[allow(clippy::elidable_lifetime_names)]
46impl<'a> BitReader<'a> {
47 #[must_use]
59 pub const fn new(data: &'a [u8]) -> Self {
60 Self {
61 data,
62 byte_pos: 0,
63 bit_pos: 0,
64 }
65 }
66
67 pub fn read_bit(&mut self) -> OxiResult<u8> {
88 if self.byte_pos >= self.data.len() {
89 return Err(OxiError::UnexpectedEof);
90 }
91
92 let bit = (self.data[self.byte_pos] >> (7 - self.bit_pos)) & 1;
94 self.bit_pos += 1;
95
96 if self.bit_pos == 8 {
97 self.bit_pos = 0;
98 self.byte_pos += 1;
99 }
100
101 Ok(bit)
102 }
103
104 pub fn read_bits(&mut self, n: u8) -> OxiResult<u64> {
129 if n > 64 {
130 return Err(OxiError::InvalidData(
131 "Cannot read more than 64 bits at once".to_string(),
132 ));
133 }
134
135 if n == 0 {
136 return Ok(0);
137 }
138
139 let mut value = 0u64;
140 for _ in 0..n {
141 value = (value << 1) | u64::from(self.read_bit()?);
142 }
143
144 Ok(value)
145 }
146
147 #[allow(clippy::cast_possible_truncation)]
166 pub fn read_u8(&mut self) -> OxiResult<u8> {
167 Ok(self.read_bits(8)? as u8)
168 }
169
170 #[allow(clippy::cast_possible_truncation)]
188 pub fn read_u16(&mut self) -> OxiResult<u16> {
189 Ok(self.read_bits(16)? as u16)
190 }
191
192 #[allow(clippy::cast_possible_truncation)]
210 pub fn read_u32(&mut self) -> OxiResult<u32> {
211 Ok(self.read_bits(32)? as u32)
212 }
213
214 pub fn read_u64(&mut self) -> OxiResult<u64> {
232 self.read_bits(64)
233 }
234
235 pub fn read_flag(&mut self) -> OxiResult<bool> {
256 Ok(self.read_bit()? != 0)
257 }
258
259 pub fn skip_bits(&mut self, n: usize) {
275 for _ in 0..n {
276 if self.read_bit().is_err() {
277 break;
278 }
279 }
280 }
281
282 pub fn byte_align(&mut self) {
301 if self.bit_pos != 0 {
302 self.bit_pos = 0;
303 self.byte_pos += 1;
304 }
305 }
306
307 #[must_use]
323 pub fn has_more_data(&self) -> bool {
324 self.byte_pos < self.data.len()
325 }
326
327 #[must_use]
345 pub fn remaining_bytes(&self) -> usize {
346 if self.byte_pos >= self.data.len() {
347 0
348 } else {
349 self.data.len() - self.byte_pos - usize::from(self.bit_pos > 0)
350 }
351 }
352
353 #[must_use]
371 pub fn bits_read(&self) -> usize {
372 self.byte_pos * 8 + self.bit_pos as usize
373 }
374
375 #[must_use]
391 pub fn remaining_bits(&self) -> usize {
392 if self.byte_pos >= self.data.len() {
393 0
394 } else {
395 (self.data.len() - self.byte_pos) * 8 - self.bit_pos as usize
396 }
397 }
398
399 pub fn peek_bit(&self) -> OxiResult<u8> {
420 if self.byte_pos >= self.data.len() {
421 return Err(OxiError::UnexpectedEof);
422 }
423
424 Ok((self.data[self.byte_pos] >> (7 - self.bit_pos)) & 1)
425 }
426
427 #[must_use]
429 pub const fn data(&self) -> &'a [u8] {
430 self.data
431 }
432
433 #[must_use]
435 pub const fn byte_position(&self) -> usize {
436 self.byte_pos
437 }
438
439 #[must_use]
441 pub const fn bit_position(&self) -> u8 {
442 self.bit_pos
443 }
444}
445
446#[cfg(test)]
447mod tests {
448 use super::*;
449
450 #[test]
451 fn test_new() {
452 let data = [0xFF, 0x00];
453 let reader = BitReader::new(&data);
454 assert_eq!(reader.byte_position(), 0);
455 assert_eq!(reader.bit_position(), 0);
456 assert!(reader.has_more_data());
457 }
458
459 #[test]
460 fn test_read_bit() {
461 let data = [0b10110100];
462 let mut reader = BitReader::new(&data);
463
464 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 1);
465 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 0);
466 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 1);
467 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 1);
468 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 0);
469 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 1);
470 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 0);
471 assert_eq!(reader.read_bit().expect("read_bit should succeed"), 0);
472 }
473
474 #[test]
475 fn test_read_bits() {
476 let data = [0b10110100, 0b11001010];
477 let mut reader = BitReader::new(&data);
478
479 assert_eq!(
480 reader.read_bits(4).expect("read_bits should succeed"),
481 0b1011
482 );
483 assert_eq!(
484 reader.read_bits(4).expect("read_bits should succeed"),
485 0b0100
486 );
487 assert_eq!(
488 reader.read_bits(8).expect("read_bits should succeed"),
489 0b11001010
490 );
491 }
492
493 #[test]
494 fn test_read_bits_across_bytes() {
495 let data = [0b10110100, 0b11001010];
496 let mut reader = BitReader::new(&data);
497
498 assert_eq!(
499 reader.read_bits(12).expect("read_bits should succeed"),
500 0b101101001100
501 );
502 assert_eq!(
503 reader.read_bits(4).expect("read_bits should succeed"),
504 0b1010
505 );
506 }
507
508 #[test]
509 fn test_read_bits_zero() {
510 let data = [0xFF];
511 let mut reader = BitReader::new(&data);
512 assert_eq!(reader.read_bits(0).expect("read_bits should succeed"), 0);
513 assert_eq!(reader.bits_read(), 0);
514 }
515
516 #[test]
517 fn test_read_bits_too_many() {
518 let data = [0xFF];
519 let mut reader = BitReader::new(&data);
520 let result = reader.read_bits(65);
521 assert!(result.is_err());
522 }
523
524 #[test]
525 fn test_read_u8() {
526 let data = [0x12, 0x34];
527 let mut reader = BitReader::new(&data);
528 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x12);
529 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x34);
530 }
531
532 #[test]
533 fn test_read_u16() {
534 let data = [0x12, 0x34];
535 let mut reader = BitReader::new(&data);
536 assert_eq!(reader.read_u16().expect("read_u16 should succeed"), 0x1234);
537 }
538
539 #[test]
540 fn test_read_u32() {
541 let data = [0x12, 0x34, 0x56, 0x78];
542 let mut reader = BitReader::new(&data);
543 assert_eq!(
544 reader.read_u32().expect("read_u32 should succeed"),
545 0x1234_5678
546 );
547 }
548
549 #[test]
550 fn test_read_u64() {
551 let data = [0x12, 0x34, 0x56, 0x78, 0x9A, 0xBC, 0xDE, 0xF0];
552 let mut reader = BitReader::new(&data);
553 assert_eq!(
554 reader.read_u64().expect("read_u64 should succeed"),
555 0x1234_5678_9ABC_DEF0
556 );
557 }
558
559 #[test]
560 fn test_read_flag() {
561 let data = [0b10100000];
562 let mut reader = BitReader::new(&data);
563 assert!(reader.read_flag().expect("read_flag should succeed"));
564 assert!(!reader.read_flag().expect("read_flag should succeed"));
565 assert!(reader.read_flag().expect("read_flag should succeed"));
566 }
567
568 #[test]
569 fn test_skip_bits() {
570 let data = [0xFF, 0x12];
571 let mut reader = BitReader::new(&data);
572 reader.skip_bits(8);
573 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x12);
574 }
575
576 #[test]
577 fn test_byte_align() {
578 let data = [0xFF, 0x12];
579 let mut reader = BitReader::new(&data);
580 reader.read_bits(3).expect("read_bits should succeed");
581 reader.byte_align();
582 assert_eq!(reader.bits_read(), 8);
583 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x12);
584 }
585
586 #[test]
587 fn test_byte_align_already_aligned() {
588 let data = [0xFF, 0x12];
589 let mut reader = BitReader::new(&data);
590 reader.byte_align();
591 assert_eq!(reader.bits_read(), 0);
592 }
593
594 #[test]
595 fn test_has_more_data() {
596 let data = [0xFF];
597 let mut reader = BitReader::new(&data);
598 assert!(reader.has_more_data());
599 reader.read_bits(8).expect("read_bits should succeed");
600 assert!(!reader.has_more_data());
601 }
602
603 #[test]
604 fn test_remaining_bytes() {
605 let data = [0xFF, 0x00, 0xFF];
606 let mut reader = BitReader::new(&data);
607 assert_eq!(reader.remaining_bytes(), 3);
608 reader.read_bits(4).expect("read_bits should succeed");
609 assert_eq!(reader.remaining_bytes(), 2);
610 reader.read_bits(4).expect("read_bits should succeed");
611 assert_eq!(reader.remaining_bytes(), 2);
612 }
613
614 #[test]
615 fn test_bits_read() {
616 let data = [0xFF, 0x00];
617 let mut reader = BitReader::new(&data);
618 assert_eq!(reader.bits_read(), 0);
619 reader.read_bits(5).expect("read_bits should succeed");
620 assert_eq!(reader.bits_read(), 5);
621 reader.read_bits(3).expect("read_bits should succeed");
622 assert_eq!(reader.bits_read(), 8);
623 }
624
625 #[test]
626 fn test_remaining_bits() {
627 let data = [0xFF, 0x00];
628 let mut reader = BitReader::new(&data);
629 assert_eq!(reader.remaining_bits(), 16);
630 reader.read_bits(5).expect("read_bits should succeed");
631 assert_eq!(reader.remaining_bits(), 11);
632 }
633
634 #[test]
635 fn test_peek_bit() {
636 let data = [0b10000000];
637 let mut reader = BitReader::new(&data);
638 assert_eq!(reader.peek_bit().expect("peek_bit should succeed"), 1);
639 assert_eq!(reader.peek_bit().expect("peek_bit should succeed"), 1);
640 assert_eq!(reader.bits_read(), 0);
641 reader.read_bit().expect("read_bit should succeed");
642 assert_eq!(reader.peek_bit().expect("peek_bit should succeed"), 0);
643 }
644
645 #[test]
646 fn test_eof() {
647 let data = [0xFF];
648 let mut reader = BitReader::new(&data);
649 reader.read_bits(8).expect("read_bits should succeed");
650 assert!(reader.read_bit().is_err());
651 assert!(reader.read_bits(1).is_err());
652 assert!(reader.peek_bit().is_err());
653 }
654
655 #[test]
656 fn test_empty_data() {
657 let data: [u8; 0] = [];
658 let reader = BitReader::new(&data);
659 assert!(!reader.has_more_data());
660 assert_eq!(reader.remaining_bytes(), 0);
661 assert_eq!(reader.remaining_bits(), 0);
662 }
663
664 #[test]
667 fn test_read_64_bits_max() {
668 let data = [0xFF; 8];
669 let mut reader = BitReader::new(&data);
670 let value = reader.read_bits(64).expect("read_bits should succeed");
671 assert_eq!(value, u64::MAX);
672 }
673
674 #[test]
675 fn test_read_across_multiple_bytes() {
676 let data = [0b10101010, 0b11001100, 0b11110000];
678 let mut reader = BitReader::new(&data);
679
680 assert_eq!(
681 reader.read_bits(4).expect("read_bits should succeed"),
682 0b1010
683 );
684 assert_eq!(
685 reader.read_bits(8).expect("read_bits should succeed"),
686 0b1010_1100
687 );
688 assert_eq!(
689 reader.read_bits(12).expect("read_bits should succeed"),
690 0b1100_1111_0000
691 );
692 }
693
694 #[test]
695 fn test_mixed_read_operations() {
696 let data = [0b11010010, 0b10110100];
697 let mut reader = BitReader::new(&data);
698
699 assert!(reader.read_flag().expect("read_flag should succeed")); assert!(reader.read_flag().expect("read_flag should succeed")); assert!(!reader.read_flag().expect("read_flag should succeed")); assert_eq!(
703 reader.read_bits(5).expect("read_bits should succeed"),
704 0b10010
705 ); assert_eq!(
707 reader.read_u8().expect("read_u8 should succeed"),
708 0b10110100
709 );
710 }
711
712 #[test]
713 fn test_byte_align_at_boundary() {
714 let data = [0xFF, 0x12, 0x34];
715 let mut reader = BitReader::new(&data);
716
717 reader.byte_align(); assert_eq!(reader.bits_read(), 0);
719
720 reader.read_bits(8).expect("read_bits should succeed");
721 reader.byte_align(); assert_eq!(reader.bits_read(), 8);
723 }
724
725 #[test]
726 fn test_skip_bits_partial_byte() {
727 let data = [0xFF, 0x12];
728 let mut reader = BitReader::new(&data);
729
730 reader.skip_bits(3);
731 assert_eq!(
732 reader.read_bits(5).expect("read_bits should succeed"),
733 0b11111
734 );
735 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x12);
736 }
737
738 #[test]
739 fn test_skip_bits_beyond_end() {
740 let data = [0xFF];
741 let mut reader = BitReader::new(&data);
742
743 reader.skip_bits(100); assert!(!reader.has_more_data());
745 }
746
747 #[test]
748 fn test_remaining_methods_consistency() {
749 let data = [0xFF, 0x00, 0xFF, 0x00];
750 let mut reader = BitReader::new(&data);
751
752 assert_eq!(reader.remaining_bits(), 32);
753 assert_eq!(reader.remaining_bytes(), 4);
754
755 reader.read_bits(5).expect("read_bits should succeed");
756 assert_eq!(reader.remaining_bits(), 27);
757 assert_eq!(reader.remaining_bytes(), 3);
758
759 reader.read_bits(11).expect("read_bits should succeed"); assert_eq!(reader.remaining_bits(), 16);
761 assert_eq!(reader.remaining_bytes(), 2);
762 }
763
764 #[test]
765 fn test_peek_doesnt_consume() {
766 let data = [0b10110100];
767 let mut reader = BitReader::new(&data);
768
769 for _ in 0..10 {
770 assert_eq!(reader.peek_bit().expect("peek_bit should succeed"), 1);
771 }
772 assert_eq!(reader.bits_read(), 0);
773
774 reader.read_bit().expect("read_bit should succeed");
775 for _ in 0..10 {
776 assert_eq!(reader.peek_bit().expect("peek_bit should succeed"), 0);
777 }
778 assert_eq!(reader.bits_read(), 1);
779 }
780
781 #[test]
782 fn test_read_all_integer_types() {
783 let data = [
785 0x12, 0x34, 0x56, 0x78, 0x9A, 0xBC, 0xDE, 0xF0, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, ];
790 let mut reader = BitReader::new(&data);
791
792 assert_eq!(reader.read_u8().expect("read_u8 should succeed"), 0x12);
793 assert_eq!(reader.read_u16().expect("read_u16 should succeed"), 0x3456);
794 assert_eq!(
795 reader.read_u32().expect("read_u32 should succeed"),
796 0x789A_BCDE
797 );
798 assert_eq!(
799 reader.read_u64().expect("read_u64 should succeed"),
800 0xF011_2233_4455_6677
801 );
802 assert!(!reader.has_more_data());
803 }
804
805 #[test]
806 fn test_unaligned_integer_reads() {
807 let data = [0xFF, 0x12, 0x34, 0x56, 0x78];
808 let mut reader = BitReader::new(&data);
809
810 reader.read_bits(4).expect("read_bits should succeed"); assert_eq!(reader.read_bits(8).expect("read_bits should succeed"), 0xF1);
814 assert_eq!(
815 reader.read_bits(16).expect("read_bits should succeed"),
816 0x2345
817 );
818 assert_eq!(reader.read_bits(8).expect("read_bits should succeed"), 0x67);
819 }
820
821 #[test]
822 fn test_position_tracking() {
823 let data = [0xFF, 0x00, 0xFF];
824 let mut reader = BitReader::new(&data);
825
826 assert_eq!(reader.byte_position(), 0);
827 assert_eq!(reader.bit_position(), 0);
828
829 reader.read_bits(10).expect("read_bits should succeed");
830 assert_eq!(reader.byte_position(), 1);
831 assert_eq!(reader.bit_position(), 2);
832
833 reader.byte_align();
834 assert_eq!(reader.byte_position(), 2);
835 assert_eq!(reader.bit_position(), 0);
836 }
837
838 #[test]
839 fn test_data_accessor() {
840 let data = [0xFF, 0x00, 0xFF];
841 let reader = BitReader::new(&data);
842
843 assert_eq!(reader.data(), &data);
844 assert_eq!(reader.data().len(), 3);
845 }
846
847 #[test]
848 fn test_single_bit_pattern() {
849 let data = [0b10101010];
851 let mut reader = BitReader::new(&data);
852
853 for i in 0..8 {
854 let expected = if i % 2 == 0 { 1 } else { 0 };
855 assert_eq!(
856 reader.read_bit().expect("read_bit should succeed"),
857 expected
858 );
859 }
860 }
861
862 #[test]
863 fn test_eof_on_exact_boundary() {
864 let data = [0xFF];
865 let mut reader = BitReader::new(&data);
866
867 reader.read_bits(8).expect("read_bits should succeed");
868 assert!(!reader.has_more_data());
869 assert_eq!(reader.remaining_bits(), 0);
870
871 let result = reader.read_bit();
872 assert!(result.is_err());
873 }
874}