pub mod cursor;
#[cfg(feature = "x86_ssse3")]
pub mod ssse3;
#[cfg(test)]
mod tests;
pub trait Decoder {
type DecodedQuad;
fn decode_quads<S: DecodeQuadSink<Self>>(
control_bytes: &[u8],
encoded_nums: &[u8],
max_control_bytes_to_decode: usize,
nums_already_decoded: usize,
sink: &mut S,
) -> (usize, usize);
}
pub trait WriteQuadToSlice: Decoder {
fn write_quad_to_slice(quad: Self::DecodedQuad, slice: &mut [u32]);
}
pub trait DecodeSingleSink {
fn on_number(&mut self, num: u32, nums_decoded: usize);
}
pub trait DecodeQuadSink<D: Decoder + ?Sized>: DecodeSingleSink {
fn on_quad(&mut self, quad: D::DecodedQuad, nums_decoded: usize);
}
pub(crate) struct SliceDecodeSink<'a> {
output: &'a mut [u32],
}
impl<'a> SliceDecodeSink<'a> {
fn new(output: &'a mut [u32]) -> SliceDecodeSink<'a> {
SliceDecodeSink { output }
}
}
impl<'a> DecodeSingleSink for SliceDecodeSink<'a> {
#[inline]
fn on_number(&mut self, num: u32, nums_decoded: usize) {
self.output[nums_decoded] = num;
}
}
impl<'a, D: Decoder + WriteQuadToSlice> DecodeQuadSink<D> for SliceDecodeSink<'a> {
fn on_quad(&mut self, quad: D::DecodedQuad, nums_decoded: usize) {
D::write_quad_to_slice(quad, &mut self.output[nums_decoded..(nums_decoded + 4)]);
}
}
pub fn decode<D: Decoder + WriteQuadToSlice>(
input: &[u8],
count: usize,
output: &mut [u32],
) -> usize {
let mut cursor = cursor::DecodeCursor::new(&input, count);
assert_eq!(
count,
cursor.decode_slice::<D>(output),
"output buffer was not large enough"
);
cursor.input_consumed()
}
#[inline]
pub fn decode_num_scalar(len: usize, input: &[u8]) -> u32 {
let mut buf = [0_u8; 4];
buf[0..len].copy_from_slice(&input[0..len]);
u32::from_le_bytes(buf)
}