Skip to main content

BitReader

Struct BitReader 

Source
pub struct BitReader<'a> { /* private fields */ }
Expand description

Bit-level reader for parsing binary formats.

BitReader allows reading individual bits and multi-bit values from a byte slice. It tracks both byte position and bit position within the current byte.

§Bit Ordering

Bits are read from MSB (most significant bit) to LSB (least significant bit) within each byte. This is the standard ordering used by most video codecs including H.264, HEVC, AV1, and VP9.

§Example

use oximedia_io::bits::BitReader;

let data = [0b10110100, 0b11001010];
let mut reader = BitReader::new(&data);

// Read individual bits (from MSB to LSB)
assert_eq!(reader.read_bit()?, 1);
assert_eq!(reader.read_bit()?, 0);
assert_eq!(reader.read_bit()?, 1);
assert_eq!(reader.read_bit()?, 1);

// Read multiple bits as a value
assert_eq!(reader.read_bits(4)?, 0b0100);

Implementations§

Source§

impl BitReader<'_>

Source

pub fn read_exp_golomb(&mut self) -> OxiResult<u64>

Reads an unsigned Exp-Golomb coded integer (ue(v)).

This is used extensively in H.264 for encoding syntax elements.

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits. Returns OxiError::InvalidData if the code is malformed or too long.

§Example
use oximedia_io::bits::BitReader;

// ue(0) = 1 (single bit)
let data = [0b10000000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_exp_golomb()?, 0);

// ue(1) = 010
let data = [0b01000000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_exp_golomb()?, 1);

// ue(2) = 011
let data = [0b01100000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_exp_golomb()?, 2);
Source

pub fn read_signed_exp_golomb(&mut self) -> OxiResult<i64>

Reads a signed Exp-Golomb coded integer (se(v)).

Maps unsigned Exp-Golomb values to signed:

  • 0 -> 0
  • 1 -> 1
  • 2 -> -1
  • 3 -> 2
  • 4 -> -2
  • etc.
§Errors

Returns OxiError::UnexpectedEof if there are not enough bits. Returns OxiError::InvalidData if the code is malformed.

§Example
use oximedia_io::bits::BitReader;

// se(0) = 1 -> value 0
let data = [0b10000000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_signed_exp_golomb()?, 0);

// se(+1) = 010 -> value 1
let data = [0b01000000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_signed_exp_golomb()?, 1);

// se(-1) = 011 -> value 2
let data = [0b01100000];
let mut reader = BitReader::new(&data);
assert_eq!(reader.read_signed_exp_golomb()?, -1);
Source

pub fn read_ue(&mut self) -> OxiResult<u64>

Reads an unsigned Exp-Golomb coded integer, alias for read_exp_golomb.

This follows H.264 naming convention (ue(v)).

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits. Returns OxiError::InvalidData if the code is malformed.

Source

pub fn read_se(&mut self) -> OxiResult<i64>

Reads a signed Exp-Golomb coded integer, alias for read_signed_exp_golomb.

This follows H.264 naming convention (se(v)).

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits. Returns OxiError::InvalidData if the code is malformed.

Source§

impl<'a> BitReader<'a>

Source

pub const fn new(data: &'a [u8]) -> Self

Creates a new BitReader from a byte slice.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00];
let reader = BitReader::new(&data);
assert!(reader.has_more_data());
Source

pub fn read_bit(&mut self) -> OxiResult<u8>

Reads a single bit from the stream.

Returns 0 or 1.

§Errors

Returns OxiError::UnexpectedEof if there are no more bits to read.

§Example
use oximedia_io::bits::BitReader;

let data = [0b10000000];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_bit()?, 1);
assert_eq!(reader.read_bit()?, 0);
Source

pub fn read_bits(&mut self, n: u8) -> OxiResult<u64>

Reads up to 64 bits from the stream.

§Arguments
  • n - Number of bits to read (0-64)
§Errors

Returns OxiError::InvalidData if n > 64. Returns OxiError::UnexpectedEof if there are not enough bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0b10110100, 0b11001010];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_bits(4)?, 0b1011);
assert_eq!(reader.read_bits(4)?, 0b0100);
assert_eq!(reader.read_bits(8)?, 0b11001010);
Source

pub fn read_u8(&mut self) -> OxiResult<u8>

Reads an 8-bit unsigned integer.

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0x12, 0x34];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_u8()?, 0x12);
assert_eq!(reader.read_u8()?, 0x34);
Source

pub fn read_u16(&mut self) -> OxiResult<u16>

Reads a 16-bit unsigned integer in big-endian order.

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0x12, 0x34];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_u16()?, 0x1234);
Source

pub fn read_u32(&mut self) -> OxiResult<u32>

Reads a 32-bit unsigned integer in big-endian order.

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0x12, 0x34, 0x56, 0x78];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_u32()?, 0x12345678);
Source

pub fn read_u64(&mut self) -> OxiResult<u64>

Reads a 64-bit unsigned integer in big-endian order.

§Errors

Returns OxiError::UnexpectedEof if there are not enough bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0x12, 0x34, 0x56, 0x78, 0x9A, 0xBC, 0xDE, 0xF0];
let mut reader = BitReader::new(&data);

assert_eq!(reader.read_u64()?, 0x123456789ABCDEF0);
Source

pub fn read_flag(&mut self) -> OxiResult<bool>

Reads a boolean flag (single bit).

Returns true if the bit is 1, false if 0.

§Errors

Returns OxiError::UnexpectedEof if there are no more bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0b10000000];
let mut reader = BitReader::new(&data);

assert!(reader.read_flag()?);
assert!(!reader.read_flag()?);
Source

pub fn skip_bits(&mut self, n: usize)

Skips the specified number of bits.

This method silently ignores attempts to skip past the end of data.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00];
let mut reader = BitReader::new(&data);

reader.skip_bits(4);
assert_eq!(reader.bits_read(), 4);
Source

pub fn byte_align(&mut self)

Aligns the reader to the next byte boundary.

If the reader is already at a byte boundary, this is a no-op. Otherwise, the remaining bits in the current byte are skipped.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00];
let mut reader = BitReader::new(&data);

reader.read_bits(3)?;  // Read 3 bits
reader.byte_align();           // Skip remaining 5 bits
assert_eq!(reader.bits_read(), 8);
Source

pub fn has_more_data(&self) -> bool

Returns true if there is more data available to read.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF];
let mut reader = BitReader::new(&data);

assert!(reader.has_more_data());
reader.read_bits(8)?;
assert!(!reader.has_more_data());
Source

pub fn remaining_bytes(&self) -> usize

Returns the number of complete bytes remaining.

This does not count partial bytes at the current position.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00, 0xFF];
let mut reader = BitReader::new(&data);

assert_eq!(reader.remaining_bytes(), 3);
reader.read_bits(4)?;
assert_eq!(reader.remaining_bytes(), 2);  // Partial byte not counted
Source

pub fn bits_read(&self) -> usize

Returns the total number of bits read so far.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00];
let mut reader = BitReader::new(&data);

assert_eq!(reader.bits_read(), 0);
reader.read_bits(5)?;
assert_eq!(reader.bits_read(), 5);
reader.read_bits(3)?;
assert_eq!(reader.bits_read(), 8);
Source

pub fn remaining_bits(&self) -> usize

Returns the total number of remaining bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0xFF, 0x00];
let mut reader = BitReader::new(&data);

assert_eq!(reader.remaining_bits(), 16);
reader.read_bits(5)?;
assert_eq!(reader.remaining_bits(), 11);
Source

pub fn peek_bit(&self) -> OxiResult<u8>

Peeks at the next bit without consuming it.

§Errors

Returns OxiError::UnexpectedEof if there are no more bits.

§Example
use oximedia_io::bits::BitReader;

let data = [0b10000000];
let mut reader = BitReader::new(&data);

assert_eq!(reader.peek_bit()?, 1);
assert_eq!(reader.peek_bit()?, 1);  // Still 1, not consumed
assert_eq!(reader.read_bit()?, 1);  // Now consumed
assert_eq!(reader.peek_bit()?, 0);  // Next bit
Source

pub const fn data(&self) -> &'a [u8]

Returns the underlying byte slice.

Source

pub const fn byte_position(&self) -> usize

Returns the current byte position.

Source

pub const fn bit_position(&self) -> u8

Returns the current bit position within the current byte (0-7).

Trait Implementations§

Source§

impl<'a> Clone for BitReader<'a>

Source§

fn clone(&self) -> BitReader<'a>

Returns a duplicate of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<'a> Debug for BitReader<'a>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more

Auto Trait Implementations§

§

impl<'a> Freeze for BitReader<'a>

§

impl<'a> RefUnwindSafe for BitReader<'a>

§

impl<'a> Send for BitReader<'a>

§

impl<'a> Sync for BitReader<'a>

§

impl<'a> Unpin for BitReader<'a>

§

impl<'a> UnsafeUnpin for BitReader<'a>

§

impl<'a> UnwindSafe for BitReader<'a>

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.