fn main() {
println!("#[cfg_attr(rustfmt, rustfmt_skip)]");
println!("pub const DECODE_LENGTH_PER_NUM_TABLE: &'static [(u8, u8, u8, u8); 256] = &[");
for b in 0..256 {
let byte = b as u8;
let (len0, len1, len2, len3) = lengths_for_control_byte(byte);
println!(
" ({}, {}, {}, {}), // {} = 0x{:X} = 0b{:08b}, lengths {} {} {} {}",
len0, len1, len2, len3, byte, byte, byte, len0, len1, len2, len3
);
}
println!("];");
println!();
println!("#[cfg_attr(rustfmt, rustfmt_skip)]");
println!("pub const DECODE_LENGTH_PER_QUAD_TABLE: &'static [u8; 256] = &[");
for b in 0..256 {
let byte = b as u8;
let (len0, len1, len2, len3) = lengths_for_control_byte(byte);
println!(
" {}, // {} = 0x{:X} = 0b{:08b}, lengths {} {} {} {}",
len0 + len1 + len2 + len3,
byte,
byte,
byte,
len0,
len1,
len2,
len3
);
}
println!("];");
println!();
println!("#[cfg_attr(rustfmt, rustfmt_skip)]");
println!("#[cfg(feature = \"x86_ssse3\")]");
println!("pub const X86_SSSE3_DECODE_SHUFFLE_TABLE: &'static [[u8; 16]; 256] = &[");
for b in 0..256 {
let byte = b as u8;
let (len0, len1, len2, len3) = lengths_for_control_byte(byte);
let mut shuffle_bytes = Vec::new();
push_decode_u32_shuffle_bytes(0, len0, &mut shuffle_bytes);
push_decode_u32_shuffle_bytes(len0, len1, &mut shuffle_bytes);
push_decode_u32_shuffle_bytes(len0 + len1, len2, &mut shuffle_bytes);
push_decode_u32_shuffle_bytes(len0 + len1 + len2, len3, &mut shuffle_bytes);
assert_eq!(16, shuffle_bytes.len());
println!(
" // {} = 0x{:X} = 0b{:08b}, lengths {} {} {} {}",
byte, byte, byte, len0, len1, len2, len3
);
println!(
" [{}],",
shuffle_bytes
.iter()
.map(|b| format!("{:4 }", b))
.collect::<Vec<String>>()
.join(","),
);
}
println!("];");
println!();
println!("#[cfg_attr(rustfmt, rustfmt_skip)]");
println!("#[cfg(feature = \"x86_sse41\")]");
println!("pub const X86_ENCODE_SHUFFLE_TABLE: &'static [[u8; 16]; 256] = &[");
for b in 0..256 {
let byte = b as u8;
let (len0, len1, len2, len3) = lengths_for_control_byte(byte);
let mut shuffle_bytes = Vec::new();
push_encode_u32_shuffle_bytes(0, len0, &mut shuffle_bytes);
push_encode_u32_shuffle_bytes(4, len1, &mut shuffle_bytes);
push_encode_u32_shuffle_bytes(8, len2, &mut shuffle_bytes);
push_encode_u32_shuffle_bytes(12, len3, &mut shuffle_bytes);
shuffle_bytes.resize(16, 128);
assert_eq!(16, shuffle_bytes.len());
println!(
" // {} = 0x{:X} = 0b{:08b}, lengths {} {} {} {}",
byte, byte, byte, len0, len1, len2, len3
);
println!(
" [{}],",
shuffle_bytes
.iter()
.map(|b| format!("{:4 }", b))
.collect::<Vec<String>>()
.join(","),
);
}
println!("];");
}
fn push_decode_u32_shuffle_bytes(
start_of_encoded_num: usize,
encoded_length: usize,
shuffle_bytes: &mut Vec<u8>,
) {
for l in 0..encoded_length {
shuffle_bytes.push((start_of_encoded_num + l) as u8);
}
for _ in 0..(4 - encoded_length) {
shuffle_bytes.push(0x80);
}
}
fn push_encode_u32_shuffle_bytes(
start_of_num: usize,
encoded_length: usize,
shuffle_bytes: &mut Vec<u8>,
) {
for l in 0..encoded_length {
shuffle_bytes.push((start_of_num + l) as u8);
}
}
fn lengths_for_control_byte(byte: u8) -> (usize, usize, usize, usize) {
let len3 = (((byte & 0xC0) >> 6) + 1) as usize;
let len2 = (((byte & 0x30) >> 4) + 1) as usize;
let len1 = (((byte & 0x0C) >> 2) + 1) as usize;
let len0 = ((byte & 0x3) + 1) as usize;
(len0, len1, len2, len3)
}