pub trait BitRead {
Show 27 methods
// Required methods
fn read_unsigned_counted<const MAX: u32, U>(
&mut self,
bits: BitCount<MAX>,
) -> Result<U, Error>
where U: UnsignedInteger;
fn read_signed_counted<const MAX: u32, S>(
&mut self,
bits: impl TryInto<SignedBitCount<MAX>>,
) -> Result<S, Error>
where S: SignedInteger;
fn read_to<V>(&mut self) -> Result<V, Error>
where V: Primitive;
fn read_as_to<F, V>(&mut self) -> Result<V, Error>
where F: Endianness,
V: Primitive;
fn byte_aligned(&self) -> bool;
fn byte_align(&mut self);
// Provided methods
fn read_bit(&mut self) -> Result<bool, Error> { ... }
fn read<const BITS: u32, I>(&mut self) -> Result<I, Error>
where I: Integer { ... }
fn read_var<I>(&mut self, bits: u32) -> Result<I, Error>
where I: Integer { ... }
fn read_count<const MAX: u32>(&mut self) -> Result<BitCount<MAX>, Error> { ... }
fn read_counted<const MAX: u32, I>(
&mut self,
bits: BitCount<MAX>,
) -> Result<I, Error>
where I: Integer { ... }
fn read_unsigned<const BITS: u32, U>(&mut self) -> Result<U, Error>
where U: UnsignedInteger { ... }
fn read_unsigned_var<U>(&mut self, bits: u32) -> Result<U, Error>
where U: UnsignedInteger { ... }
fn read_signed<const BITS: u32, S>(&mut self) -> Result<S, Error>
where S: SignedInteger { ... }
fn read_signed_var<S>(&mut self, bits: u32) -> Result<S, Error>
where S: SignedInteger { ... }
fn read_const<const BITS: u32, const VALUE: u32, E>(
&mut self,
err: E,
) -> Result<(), E>
where E: From<Error> { ... }
fn skip(&mut self, bits: u32) -> Result<(), Error> { ... }
fn read_bytes(&mut self, buf: &mut [u8]) -> Result<(), Error> { ... }
fn read_to_bytes<const SIZE: usize>(&mut self) -> Result<[u8; SIZE], Error> { ... }
fn read_to_vec(&mut self, bytes: usize) -> Result<Vec<u8>, Error> { ... }
fn read_unary<const STOP_BIT: u8>(&mut self) -> Result<u32, Error> { ... }
fn read_checked<C>(
&mut self,
count: <C as CheckablePrimitive>::CountType,
) -> Result<C, Error>
where C: CheckablePrimitive { ... }
fn parse<F>(&mut self) -> Result<F, <F as FromBitStream>::Error>
where F: FromBitStream { ... }
fn parse_with<'a, F>(
&mut self,
context: &<F as FromBitStreamWith<'a>>::Context,
) -> Result<F, <F as FromBitStreamWith<'a>>::Error>
where F: FromBitStreamWith<'a> { ... }
fn parse_using<F>(
&mut self,
context: <F as FromBitStreamUsing>::Context,
) -> Result<F, <F as FromBitStreamUsing>::Error>
where F: FromBitStreamUsing { ... }
fn read_huffman<T>(&mut self) -> Result<<T as FromBits>::Symbol, Error>
where T: FromBits { ... }
fn by_ref(&mut self) -> &mut Self { ... }
}
Expand description
A trait for anything that can read a variable number of potentially un-aligned values from an input stream
Required Methods§
Sourcefn read_unsigned_counted<const MAX: u32, U>(
&mut self,
bits: BitCount<MAX>,
) -> Result<U, Error>where
U: UnsignedInteger,
fn read_unsigned_counted<const MAX: u32, U>(
&mut self,
bits: BitCount<MAX>,
) -> Result<U, Error>where
U: UnsignedInteger,
Reads an unsigned value from the stream with the given number of bits.
§Errors
Passes along any I/O error from the underlying stream. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian, BitCount};
let bytes: &[u8] = &[0b1111_0000];
let mut r = BitReader::endian(bytes, BigEndian);
// reading 4 bits with a maximum of 4 will fit into a u8
// so no runtime check needed
assert_eq!(r.read_unsigned_counted::<4, u8>(BitCount::new::<4>()).unwrap(), 0b1111);
// reading 4 bits with a maximum of 64 might not fit into a u8
// so we need to verify this at runtime
assert_eq!(r.read_unsigned_counted::<64, u8>(BitCount::new::<4>()).unwrap(), 0b0000);
Sourcefn read_signed_counted<const MAX: u32, S>(
&mut self,
bits: impl TryInto<SignedBitCount<MAX>>,
) -> Result<S, Error>where
S: SignedInteger,
fn read_signed_counted<const MAX: u32, S>(
&mut self,
bits: impl TryInto<SignedBitCount<MAX>>,
) -> Result<S, Error>where
S: SignedInteger,
Reads a twos-complement signed value from the stream with the given number of bits.
§Errors
Passes along any I/O error from the underlying stream. Returns an error if the number of bits is 0, since one bit is always needed for the sign. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian, BitCount};
let bytes: &[u8] = &[0b0001_1111];
let mut r = BitReader::endian(bytes, BigEndian);
// reading 4 bits with a maximum of 4 will fit into an i8
// so no runtime check needed
assert_eq!(r.read_signed_counted::<4, i8>(BitCount::new::<4>()).unwrap(), 1);
// reading 4 bits with a maximum of 64 might not fit into an i8
// so we need to verify this at runtime
assert_eq!(r.read_signed_counted::<64, i8>(BitCount::new::<4>()).unwrap(), -1);
Sourcefn read_to<V>(&mut self) -> Result<V, Error>where
V: Primitive,
fn read_to<V>(&mut self) -> Result<V, Error>where
V: Primitive,
Reads whole value from the stream whose size in bits is equal to its type’s size.
§Errors
Passes along any I/O error from the underlying stream.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0x12, 0x34, 0x56, 0x78];
let mut r = BitReader::endian(bytes, BigEndian);
assert_eq!(r.read_to::<u32>().unwrap(), 0x12_34_56_78);
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0x12, 0x34, 0x56, 0x78];
let mut r = BitReader::endian(bytes, BigEndian);
assert_eq!(r.read_to::<[u8; 4]>().unwrap(), [0x12, 0x34, 0x56, 0x78]);
Sourcefn read_as_to<F, V>(&mut self) -> Result<V, Error>where
F: Endianness,
V: Primitive,
fn read_as_to<F, V>(&mut self) -> Result<V, Error>where
F: Endianness,
V: Primitive,
Reads whole value from the stream whose size in bits is equal to its type’s size in an endianness that may be different from the stream’s endianness.
§Errors
Passes along any I/O error from the underlying stream.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian, LittleEndian};
let bytes: &[u8] = &[0x12, 0x34, 0x56, 0x78];
let mut r = BitReader::endian(bytes, BigEndian);
assert_eq!(r.read_as_to::<LittleEndian, u32>().unwrap(), 0x78_56_34_12);
Sourcefn byte_aligned(&self) -> bool
fn byte_aligned(&self) -> bool
Returns true if the stream is aligned at a whole byte.
§Example
use std::io::Read;
use bitstream_io::{BigEndian, BitReader, BitRead};
let data = [0];
let mut reader = BitReader::endian(data.as_slice(), BigEndian);
assert_eq!(reader.byte_aligned(), true);
assert!(reader.skip(1).is_ok());
assert_eq!(reader.byte_aligned(), false);
assert!(reader.skip(7).is_ok());
assert_eq!(reader.byte_aligned(), true);
Sourcefn byte_align(&mut self)
fn byte_align(&mut self)
Throws away all unread bit values until the next whole byte. Does nothing if the stream is already aligned.
§Example
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0x00, 0xFF];
let mut reader = BitReader::endian(data, BigEndian);
assert_eq!(reader.read::<4, u8>().unwrap(), 0);
reader.byte_align();
assert_eq!(reader.read::<8, u8>().unwrap(), 0xFF);
Provided Methods§
Sourcefn read_bit(&mut self) -> Result<bool, Error>
fn read_bit(&mut self) -> Result<bool, Error>
Reads a single bit from the stream.
true
indicates 1, false
indicates 0
§Errors
Passes along any I/O error from the underlying stream.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b1000_1110];
let mut r = BitReader::endian(bytes, BigEndian);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), false);
assert!(r.read_bit().is_err()); // no more bits to read
use bitstream_io::{BitReader, BitRead, LittleEndian};
let bytes: &[u8] = &[0b1000_1110];
let mut r = BitReader::endian(bytes, LittleEndian);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), false);
assert_eq!(r.read_bit().unwrap(), true);
assert!(r.read_bit().is_err()); // no more bits to read
Sourcefn read<const BITS: u32, I>(&mut self) -> Result<I, Error>where
I: Integer,
fn read<const BITS: u32, I>(&mut self) -> Result<I, Error>where
I: Integer,
Reads a signed or unsigned value from the stream with the given constant number of bits.
§Errors
Passes along any I/O error from the underlying stream. A compile-time error occurs if the given number of bits is larger than the output type.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b0001_1111, 0b1011_11_00];
let mut r = BitReader::endian(bytes, BigEndian);
// reading unsigned value is ok
assert_eq!(r.read::<4, u8>().unwrap(), 1);
// reading signed value is also ok
assert_eq!(r.read::<4, i8>().unwrap(), -1);
// reading an array of bits is ok too
assert_eq!(r.read::<1, [bool; 4]>().unwrap(), [true, false, true, true]);
// reading an array of any Integer type is ok
assert_eq!(r.read::<2, [u8; 2]>().unwrap(), [0b11, 0b00]);
// reading more bytes than we have is an error
assert!(r.read::<4, u8>().is_err());
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b0001_1111, 0, 0];
let mut r = BitReader::endian(bytes, BigEndian);
// reading 9 bits to a u8 is a compile-time error
r.read::<9, u8>();
Sourcefn read_var<I>(&mut self, bits: u32) -> Result<I, Error>where
I: Integer,
fn read_var<I>(&mut self, bits: u32) -> Result<I, Error>where
I: Integer,
Reads a signed or unsigned value from the stream with the given variable number of bits.
§Errors
Passes along any I/O error from the underlying stream. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b0001_1111];
let mut r = BitReader::endian(bytes, BigEndian);
// reading unsigned value is ok
assert_eq!(r.read_var::<u8>(4).unwrap(), 1);
// reading signed value is also ok
assert_eq!(r.read_var::<i8>(4).unwrap(), -1);
// reading more bytes than we have is an error
assert!(r.read_var::<u8>(4).is_err());
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0, 0, 0, 0, 0];
let mut r = BitReader::endian(bytes, BigEndian);
// reading 9 bits to a u8 is a runtime error
// no matter how much data is left
assert!(r.read_var::<u8>(9).is_err());
Sourcefn read_count<const MAX: u32>(&mut self) -> Result<BitCount<MAX>, Error>
fn read_count<const MAX: u32>(&mut self) -> Result<BitCount<MAX>, Error>
Given a desired maximum value for a bit count, reads the necessary bits to fill up to that amount.
For example, if the maximum bit count is 15 - or 0b1111
-
reads a 4-bit unsigned value from the stream and returns a BitCount
which can be used in subsequent reads.
Note that MAX
must be greater than 0, and MAX + 1
must be
an exact power of two.
§Errors
Passes along an I/O error from the underlying stream.
§Examples
use bitstream_io::{BigEndian, BitReader, BitRead};
let bytes: &[u8] = &[0b100_11110];
let mut r = BitReader::endian(bytes, BigEndian);
let count = r.read::<3, u32>().unwrap();
assert_eq!(count, 4); // reads 0b100 - or 4
// may need to verify count is not larger than u8 at runtime
assert_eq!(r.read_var::<u8>(count).unwrap(), 0b1111);
use bitstream_io::{BigEndian, BitReader, BitRead, BitCount};
let bytes: &[u8] = &[0b100_11110];
let mut r = BitReader::endian(bytes, BigEndian);
let count = r.read_count::<0b111>().unwrap();
assert_eq!(count, BitCount::new::<4>()); // reads 0b100 - or 4
// maximum size of bit count is known to be 7 at compile-time,
// so no runtime check needed to know 7 bits is not larger than a u8
assert_eq!(r.read_counted::<0b111, u8>(count).unwrap(), 0b1111);
use bitstream_io::{BigEndian, BitReader, BitRead};
let bytes: &[u8] = &[0b100_11110];
let mut r = BitReader::endian(bytes, BigEndian);
// maximum bit count is 6 (0b110), so we need to read 3 bits
// but no idea what to do if a value of 7 (0b111) is read,
// so this does not compile at all
let count = r.read_count::<0b110>();
Sourcefn read_counted<const MAX: u32, I>(
&mut self,
bits: BitCount<MAX>,
) -> Result<I, Error>where
I: Integer,
fn read_counted<const MAX: u32, I>(
&mut self,
bits: BitCount<MAX>,
) -> Result<I, Error>where
I: Integer,
Reads a signed or unsigned value from the stream with the given number of bits.
§Errors
Passes along any I/O error from the underlying stream. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian, BitCount};
let bytes: &[u8] = &[0b1111_0000];
let mut r = BitReader::endian(bytes, BigEndian);
// reading 4 bits with a maximum of 4 will fit into a u8
// so no runtime check needed
assert_eq!(r.read_counted::<4, u8>(BitCount::new::<4>()).unwrap(), 0b1111);
// reading 4 bits with a maximum of 64 might not fit into a u8
// so we need to verify this at runtime
assert_eq!(r.read_counted::<64, u8>(BitCount::new::<4>()).unwrap(), 0b0000);
Sourcefn read_unsigned<const BITS: u32, U>(&mut self) -> Result<U, Error>where
U: UnsignedInteger,
fn read_unsigned<const BITS: u32, U>(&mut self) -> Result<U, Error>where
U: UnsignedInteger,
Reads an unsigned value from the stream with the given constant number of bits.
§Errors
Passes along any I/O error from the underlying stream. A compile-time error occurs if the given number of bits is larger than the output type.
§Examples
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0b1_01_10111];
let mut reader = BitReader::endian(data, BigEndian);
assert_eq!(reader.read_unsigned::<1, u8>().unwrap(), 0b1);
assert_eq!(reader.read_unsigned::<2, u8>().unwrap(), 0b01);
assert_eq!(reader.read_unsigned::<5, u8>().unwrap(), 0b10111);
use bitstream_io::{LittleEndian, BitReader, BitRead};
let data: &[u8] = &[0b10110_11_1];
let mut reader = BitReader::endian(data, LittleEndian);
assert_eq!(reader.read_unsigned::<1, u8>().unwrap(), 0b1);
assert_eq!(reader.read_unsigned::<2, u8>().unwrap(), 0b11);
assert_eq!(reader.read_unsigned::<5, u8>().unwrap(), 0b10110);
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0, 0, 0, 0, 0];
let mut reader = BitReader::endian(data, BigEndian);
// doesn't compile at all
reader.read_unsigned::<9, u8>(); // can't read 9 bits to u8
Sourcefn read_unsigned_var<U>(&mut self, bits: u32) -> Result<U, Error>where
U: UnsignedInteger,
fn read_unsigned_var<U>(&mut self, bits: u32) -> Result<U, Error>where
U: UnsignedInteger,
Reads an unsigned value from the stream with the given number of bits.
§Errors
Passes along any I/O error from the underlying stream. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0b1_01_10111];
let mut reader = BitReader::endian(data, BigEndian);
assert_eq!(reader.read_unsigned_var::<u8>(1).unwrap(), 0b1);
assert_eq!(reader.read_unsigned_var::<u8>(2).unwrap(), 0b01);
assert_eq!(reader.read_unsigned_var::<u8>(5).unwrap(), 0b10111);
use bitstream_io::{LittleEndian, BitReader, BitRead};
let data: &[u8] = &[0b10110_11_1];
let mut reader = BitReader::endian(data, LittleEndian);
assert_eq!(reader.read_unsigned_var::<u8>(1).unwrap(), 0b1);
assert_eq!(reader.read_unsigned_var::<u8>(2).unwrap(), 0b11);
assert_eq!(reader.read_unsigned_var::<u8>(5).unwrap(), 0b10110);
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0, 0, 0, 0, 0];
let mut reader = BitReader::endian(data, BigEndian);
assert!(reader.read_unsigned_var::<u8>(9).is_err()); // can't read 9 bits to u8
assert!(reader.read_unsigned_var::<u16>(17).is_err()); // can't read 17 bits to u16
assert!(reader.read_unsigned_var::<u32>(33).is_err()); // can't read 33 bits to u32
assert!(reader.read_unsigned_var::<u64>(65).is_err()); // can't read 65 bits to u64
Sourcefn read_signed<const BITS: u32, S>(&mut self) -> Result<S, Error>where
S: SignedInteger,
fn read_signed<const BITS: u32, S>(&mut self) -> Result<S, Error>where
S: SignedInteger,
Reads a twos-complement signed value from the stream with the given constant number of bits.
§Errors
Passes along any I/O error from the underlying stream. A compile-time error occurs if the number of bits is 0, since one bit is always needed for the sign. A compile-time error occurs if the given number of bits is larger than the output type.
§Examples
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0b1011_0111];
let mut reader = BitReader::endian(data, BigEndian);
assert_eq!(reader.read_signed::<4, i8>().unwrap(), -5);
assert_eq!(reader.read_signed::<4, i8>().unwrap(), 7);
assert!(reader.read_signed::<4, i8>().is_err());
use bitstream_io::{LittleEndian, BitReader, BitRead};
let data: &[u8] = &[0b1011_0111];
let mut reader = BitReader::endian(data, LittleEndian);
assert_eq!(reader.read_signed::<4, i8>().unwrap(), 7);
assert_eq!(reader.read_signed::<4, i8>().unwrap(), -5);
assert!(reader.read_signed::<4, i8>().is_err());
use bitstream_io::{LittleEndian, BitReader, BitRead};
let data: &[u8] = &[0, 0, 0, 0, 0];
let mut reader = BitReader::endian(data, LittleEndian);
// reading 9 bits to an i8 is a compile-time error
reader.read_signed::<9, i8>();
Sourcefn read_signed_var<S>(&mut self, bits: u32) -> Result<S, Error>where
S: SignedInteger,
fn read_signed_var<S>(&mut self, bits: u32) -> Result<S, Error>where
S: SignedInteger,
Reads a twos-complement signed value from the stream with the given number of bits.
§Errors
Passes along any I/O error from the underlying stream. Returns an error if the number of bits is 0, since one bit is always needed for the sign. Also returns an error if the output type is too small to hold the requested number of bits.
§Examples
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0b1011_0111];
let mut reader = BitReader::endian(data, BigEndian);
assert_eq!(reader.read_signed_var::<i8>(4).unwrap(), -5);
assert_eq!(reader.read_signed_var::<i8>(4).unwrap(), 7);
use bitstream_io::{LittleEndian, BitReader, BitRead};
let data: &[u8] = &[0b1011_0111];
let mut reader = BitReader::endian(data, LittleEndian);
assert_eq!(reader.read_signed_var::<i8>(4).unwrap(), 7);
assert_eq!(reader.read_signed_var::<i8>(4).unwrap(), -5);
use std::io::Read;
use bitstream_io::{BigEndian, BitReader, BitRead};
let data: &[u8] = &[0, 0, 0, 0, 0, 0, 0, 0, 0, 0];
let mut r = BitReader::endian(data, BigEndian);
assert!(r.read_signed_var::<i8>(9).is_err()); // can't read 9 bits to i8
assert!(r.read_signed_var::<i16>(17).is_err()); // can't read 17 bits to i16
assert!(r.read_signed_var::<i32>(33).is_err()); // can't read 33 bits to i32
assert!(r.read_signed_var::<i64>(65).is_err()); // can't read 65 bits to i64
Sourcefn read_const<const BITS: u32, const VALUE: u32, E>(
&mut self,
err: E,
) -> Result<(), E>
fn read_const<const BITS: u32, const VALUE: u32, E>( &mut self, err: E, ) -> Result<(), E>
Reads the given constant value from the stream with the given number of bits.
Due to current limitations of constant paramters,
this is limited to u32
values.
If the constant read from the stream doesn’t match the expected value, returns the generated error from the closure.
§Errors
Passes along any I/O error from the underlying stream, converted to the mismatch error. Returns the generated error if the read value doesn’t match the expected constant.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
enum Error {
Mismatch,
Io,
}
impl From<std::io::Error> for Error {
fn from(_err: std::io::Error) -> Self {
Self::Io
}
}
let data: &[u8] = &[0b1000_1011, 0b0000_0001];
let mut r = BitReader::endian(data, BigEndian);
assert!(r.read_const::<4, 0b1000, _>(Error::Mismatch).is_ok());
assert!(r.read_const::<4, 0b1011, _>(Error::Mismatch).is_ok());
// 0b1000 doesn't match 0b0000
assert!(matches!(r.read_const::<4, 0b1000, _>(Error::Mismatch), Err(Error::Mismatch)));
// 0b1011 doesn't match 0b0001
assert!(matches!(r.read_const::<4, 0b1011, _>(Error::Mismatch), Err(Error::Mismatch)));
// run out of bits to check
assert!(matches!(r.read_const::<4, 0b0000, _>(Error::Mismatch), Err(Error::Io)));
Sourcefn skip(&mut self, bits: u32) -> Result<(), Error>
fn skip(&mut self, bits: u32) -> Result<(), Error>
Skips the given number of bits in the stream.
Since this method does not need an accumulator,
it may be slightly faster than reading to an empty variable.
In addition, since there is no accumulator,
there is no upper limit on the number of bits
which may be skipped.
These bits are still read from the stream, however,
and are never skipped via a seek
method.
§Errors
Passes along any I/O error from the underlying stream.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b1_00000_10];
let mut r = BitReader::endian(bytes, BigEndian);
assert_eq!(r.read_bit().unwrap(), true);
assert!(r.skip(5).is_ok());
assert_eq!(r.read_bit().unwrap(), true);
assert_eq!(r.read_bit().unwrap(), false);
assert!(r.read_bit().is_err());
Sourcefn read_bytes(&mut self, buf: &mut [u8]) -> Result<(), Error>
fn read_bytes(&mut self, buf: &mut [u8]) -> Result<(), Error>
Completely fills the given buffer with whole bytes.
If the stream is already byte-aligned, it will map
to a faster read_exact
call. Otherwise it will read
bytes individually in 8-bit increments.
§Errors
Passes along any I/O error from the underlying stream.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0x00, 0x01, 0x02, 0x03, 0x04];
let mut r = BitReader::endian(bytes, BigEndian);
let mut buf = [0; 3];
assert_eq!(r.read::<8, u8>().unwrap(), 0x00);
assert!(r.read_bytes(&mut buf).is_ok());
assert_eq!(&buf, &[0x01, 0x02, 0x03]);
assert_eq!(r.read::<8, u8>().unwrap(), 0x04);
Sourcefn read_to_bytes<const SIZE: usize>(&mut self) -> Result<[u8; SIZE], Error>
👎Deprecated since 1.8.0: use read_to() method instead
fn read_to_bytes<const SIZE: usize>(&mut self) -> Result<[u8; SIZE], Error>
Completely fills a whole buffer with bytes and returns it.
If the stream is already byte-aligned, it will map
to a faster read_exact
call. Otherwise it will read
bytes individually in 8-bit increments.
§Errors
Passes along any I/O error from the underlying stream.
Sourcefn read_to_vec(&mut self, bytes: usize) -> Result<Vec<u8>, Error>
fn read_to_vec(&mut self, bytes: usize) -> Result<Vec<u8>, Error>
Completely fills a vector of bytes and returns it.
If the stream is already byte-aligned, it will map
to a faster read_exact
call. Otherwise it will read
bytes individually in 8-bit increments.
§Errors
Passes along any I/O error from the underlying stream.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0x00, 0x01, 0x02, 0x03, 0x04];
let mut r = BitReader::endian(bytes, BigEndian);
let mut buf = [0; 3];
assert_eq!(r.read::<8, u8>().unwrap(), 0x00);
assert_eq!(r.read_to_vec(3).unwrap().as_slice(), &[0x01, 0x02, 0x03]);
assert_eq!(r.read::<8, u8>().unwrap(), 0x04);
Sourcefn read_unary<const STOP_BIT: u8>(&mut self) -> Result<u32, Error>
fn read_unary<const STOP_BIT: u8>(&mut self) -> Result<u32, Error>
Counts the number of bits in the stream until STOP_BIT
and returns the amount read.
STOP_BIT
must be 0 or 1.
Because this field is variably-sized and may be large,
its output is always a u32
type.
§Errors
Passes along any I/O error from the underlying stream.
May panic if the number of bits exceeds u32
.
§Examples
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b0_10_11111, 0b10_000000];
let mut r = BitReader::endian(bytes, BigEndian);
// read 1 bits until stop bit of 0, big-endian order
assert_eq!(r.read_unary::<0>().unwrap(), 0);
assert_eq!(r.read_unary::<0>().unwrap(), 1);
assert_eq!(r.read_unary::<0>().unwrap(), 6);
use bitstream_io::{BitReader, BitRead, BigEndian};
let bytes: &[u8] = &[0b1_01_00000, 0b01_000000];
let mut r = BitReader::endian(bytes, BigEndian);
// read 0 bits until stop bit of 1, big-endian order
assert_eq!(r.read_unary::<1>().unwrap(), 0);
assert_eq!(r.read_unary::<1>().unwrap(), 1);
assert_eq!(r.read_unary::<1>().unwrap(), 6);
use bitstream_io::{BitReader, BitRead, LittleEndian};
let bytes: &[u8] = &[0b11111_01_0, 0b000000_01];
let mut r = BitReader::endian(bytes, LittleEndian);
// read 1 bits until stop bit of 0, little-endian order
assert_eq!(r.read_unary::<0>().unwrap(), 0);
assert_eq!(r.read_unary::<0>().unwrap(), 1);
assert_eq!(r.read_unary::<0>().unwrap(), 6);
use bitstream_io::{BitReader, BitRead, LittleEndian};
let bytes: &[u8] = &[0b00000_10_1, 0b111111_10];
let mut r = BitReader::endian(bytes, LittleEndian);
// read 0 bits until stop bit of 1, little-endian order
assert_eq!(r.read_unary::<1>().unwrap(), 0);
assert_eq!(r.read_unary::<1>().unwrap(), 1);
assert_eq!(r.read_unary::<1>().unwrap(), 6);
Sourcefn read_checked<C>(
&mut self,
count: <C as CheckablePrimitive>::CountType,
) -> Result<C, Error>where
C: CheckablePrimitive,
fn read_checked<C>(
&mut self,
count: <C as CheckablePrimitive>::CountType,
) -> Result<C, Error>where
C: CheckablePrimitive,
Reads to a checked value that is known to fit a given number of bits
§Example
use bitstream_io::{
BitRead, BitReader, BigEndian, Checked, CheckedUnsigned, CheckedSigned,
BitCount, SignedBitCount, BitWrite, BitWriter,
};
let data: &[u8] = &[0b1001_1111];
let mut r = BitReader::endian(data, BigEndian);
let bit_count = BitCount::<4>::new::<4>();
let checked_u8 = r.read_checked::<CheckedUnsigned<4, u8>>(bit_count).unwrap();
assert_eq!(checked_u8.into_value(), 0b1001);
let bit_count = SignedBitCount::<4>::new::<4>();
let checked_i8 = r.read_checked::<CheckedSigned<4, i8>>(bit_count).unwrap();
assert_eq!(checked_i8.into_value(), -1);
// note that checked values already know their bit count
// so none is required when writing them to a stream
let mut w = BitWriter::endian(vec![], BigEndian);
w.write_checked(checked_u8).unwrap();
w.write_checked(checked_i8).unwrap();
assert_eq!(w.into_writer().as_slice(), data);
Sourcefn parse<F>(&mut self) -> Result<F, <F as FromBitStream>::Error>where
F: FromBitStream,
fn parse<F>(&mut self) -> Result<F, <F as FromBitStream>::Error>where
F: FromBitStream,
Parses and returns complex type
Sourcefn parse_with<'a, F>(
&mut self,
context: &<F as FromBitStreamWith<'a>>::Context,
) -> Result<F, <F as FromBitStreamWith<'a>>::Error>where
F: FromBitStreamWith<'a>,
fn parse_with<'a, F>(
&mut self,
context: &<F as FromBitStreamWith<'a>>::Context,
) -> Result<F, <F as FromBitStreamWith<'a>>::Error>where
F: FromBitStreamWith<'a>,
Parses and returns complex type with context
Sourcefn parse_using<F>(
&mut self,
context: <F as FromBitStreamUsing>::Context,
) -> Result<F, <F as FromBitStreamUsing>::Error>where
F: FromBitStreamUsing,
fn parse_using<F>(
&mut self,
context: <F as FromBitStreamUsing>::Context,
) -> Result<F, <F as FromBitStreamUsing>::Error>where
F: FromBitStreamUsing,
Parses and returns complex type with owned context
Sourcefn read_huffman<T>(&mut self) -> Result<<T as FromBits>::Symbol, Error>where
T: FromBits,
fn read_huffman<T>(&mut self) -> Result<<T as FromBits>::Symbol, Error>where
T: FromBits,
Given a compiled Huffman tree, reads bits from the stream until the next symbol is encountered.
§Errors
Passes along any I/O error from the underlying stream.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian, define_huffman_tree, huffman::FromBits};
define_huffman_tree!(TreeName : char = ['a', ['b', ['c', 'd']]]);
// 'a' is 0
// 'b' is 1 -> 0
// 'c' is 1 -> 1 -> 0
// 'd' is 1 -> 1 -> 1
let data: &[u8] = &[0b0_10_110_11, 0b1_0000000];
let mut r = BitReader::endian(data, BigEndian);
assert_eq!(r.read_huffman::<TreeName>().unwrap(), 'a');
assert_eq!(r.read_huffman::<TreeName>().unwrap(), 'b');
assert_eq!(r.read_huffman::<TreeName>().unwrap(), 'c');
assert_eq!(r.read_huffman::<TreeName>().unwrap(), 'd');
Sourcefn by_ref(&mut self) -> &mut Self
fn by_ref(&mut self) -> &mut Self
Creates a “by reference” adaptor for this BitRead
The returned adapter also implements BitRead
and will borrow the current reader.
§Example
use bitstream_io::{BitReader, BitRead, BigEndian};
fn parse<R: BitRead>(r: R) {
// perform some parsing
}
let data: &[u8] = &[0];
let mut reader = BitReader::endian(data, BigEndian);
// performing parsing by reference
parse(reader.by_ref());
// original owned reader still available
assert_eq!(reader.read::<8, u8>().unwrap(), 0);
Dyn Compatibility§
This trait is not dyn compatible.
In older versions of Rust, dyn compatibility was called "object safety", so this trait is not object safe.