#![warn(missing_docs)]
use std::io;
#[cfg(feature = "alloc")]
use std::vec::Vec;
use super::{
BitCount, CheckablePrimitive, Endianness, Integer, PhantomData, Primitive, SignedBitCount,
SignedInteger, UnsignedInteger, VBRInteger,
};
mod bit_read;
mod bit_read2;
mod bit_reader;
mod byte_reader;
mod stream_traits;
pub use bit_read::BitRead;
pub use bit_read2::BitRead2;
pub use bit_reader::BitReader;
pub use byte_reader::{ByteRead, ByteReader};
pub use stream_traits::{
FromBitStream, FromBitStreamUsing, FromBitStreamWith, FromByteStream, FromByteStreamUsing,
FromByteStreamWith,
};
#[derive(Copy, Clone, Debug)]
pub(crate) struct VariableWidthOverflow;
impl core::fmt::Display for VariableWidthOverflow {
fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
"variable bit rate overflowed".fmt(f)
}
}
impl core::error::Error for VariableWidthOverflow {}
impl From<VariableWidthOverflow> for io::Error {
fn from(VariableWidthOverflow: VariableWidthOverflow) -> Self {
io::Error::new(
#[cfg(feature = "std")]
{
io::ErrorKind::StorageFull
},
#[cfg(not(feature = "std"))]
{
io::ErrorKind::Other
},
"variable bit rate overflow",
)
}
}
pub(crate) fn skip_aligned<R>(reader: R, bytes: u32) -> io::Result<()>
where
R: io::Read,
{
fn skip_chunks<const SIZE: usize, R>(mut reader: R, mut bytes: usize) -> io::Result<()>
where
R: io::Read,
{
let mut buf = [0; SIZE];
while bytes > 0 {
let to_read = bytes.min(SIZE);
reader.read_exact(&mut buf[0..to_read])?;
bytes -= to_read;
}
Ok(())
}
match bytes {
0..256 => skip_chunks::<8, R>(reader, bytes as usize),
256..1024 => skip_chunks::<256, R>(reader, bytes as usize),
1024..4096 => skip_chunks::<1024, R>(reader, bytes as usize),
_ => skip_chunks::<4096, R>(reader, bytes as usize),
}
}
#[cfg(feature = "alloc")]
pub(crate) fn read_to_vec(
mut read: impl FnMut(&mut [u8]) -> io::Result<()>,
bytes: usize,
) -> io::Result<Vec<u8>> {
const MAX_CHUNK: usize = 4096;
match bytes {
0 => Ok(Vec::new()),
bytes if bytes <= MAX_CHUNK => {
let mut buf = vec![0; bytes];
read(&mut buf)?;
Ok(buf)
}
mut bytes => {
let mut whole = Vec::with_capacity(MAX_CHUNK);
let mut chunk: [u8; MAX_CHUNK] = [0; MAX_CHUNK];
while bytes > 0 {
let chunk_size = bytes.min(MAX_CHUNK);
let chunk = &mut chunk[0..chunk_size];
read(chunk)?;
whole.extend_from_slice(chunk);
bytes -= chunk_size;
}
Ok(whole)
}
}
}