use super::BitWindow;
#[derive(Debug, PartialEq)]
pub struct Error {
buffer_pos: BitWindow,
len: usize,
capacity: usize,
text: String,
}
#[derive(Clone, Debug)]
struct EncodeValue {
buffer: &'static [u8],
bit_count: u32,
}
#[derive(Clone, Debug)]
struct HuffmanEncoder {
buffer_pos: BitWindow,
buffer: Vec<u8>,
}
impl HuffmanEncoder {
fn new() -> HuffmanEncoder {
HuffmanEncoder {
buffer_pos: BitWindow::new(),
buffer: Vec::new(),
}
}
fn ensure_free_space(&mut self, bit_count: u32) {
let mut end_range = self.buffer_pos.clone();
end_range.forwards(bit_count);
end_range.forwards(0);
if self.buffer.len() > end_range.byte as usize {
return;
}
if self.buffer.capacity() <= end_range.byte as usize {
self.buffer.reserve(((7 * end_range.byte) / 4) as usize);
}
let forward =
end_range.byte as usize - self.buffer.len() + if end_range.bit > 0 { 1 } else { 0 };
for _ in 0..forward {
self.buffer.push(255);
}
}
fn put(&mut self, code: u8) -> Result<(), Error> {
let encode_value = &HPACK_STRING[code as usize];
self.ensure_free_space(encode_value.bit_count);
let mut rest = encode_value.bit_count;
for i in 0..encode_value.buffer.len() {
let part = encode_value.buffer[i];
self.buffer_pos.forwards(if rest < 8 { rest } else { 8 });
rest -= self.buffer_pos.count;
write_bits(&mut self.buffer, &self.buffer_pos, part)
}
Ok(())
}
fn ends(self) -> Result<Vec<u8>, Error> {
Ok(self.buffer)
}
}
fn write_bits(out: &mut [u8], pos: &BitWindow, value: u8) {
debug_assert!(pos.bit < 8);
debug_assert!(pos.count <= 8);
debug_assert!(pos.count > 0);
if (pos.bit + pos.count) <= 8 {
debug_assert_eq!(out[pos.byte as usize] | PAD_LEFT[pos.bit as usize], 255);
let pad_left = out[pos.byte as usize] | PAD_RIGHT[(8 - pos.bit) as usize];
let shifted = value << (8 - pos.bit - pos.count) | PAD_LEFT[pos.bit as usize];
let pad_right = PAD_RIGHT[(8 - pos.count - pos.bit) as usize];
out[pos.byte as usize] = (pad_left & shifted) | pad_right;
} else {
debug_assert_eq!(out[pos.byte as usize] | PAD_LEFT[pos.bit as usize], 255);
let split = 8 - pos.bit;
let pad_left = out[pos.byte as usize] | PAD_RIGHT[split as usize];
let shifted = (value >> (pos.count - split)) | PAD_LEFT[pos.bit as usize];
out[pos.byte as usize] = pad_left & shifted;
let rem = 8 - (pos.count - split);
out[(pos.byte + 1) as usize] = (value << rem) | PAD_RIGHT[rem as usize];
}
}
const PAD_RIGHT: [u8; 9] = [0, 1, 3, 7, 15, 31, 63, 127, 255];
const PAD_LEFT: [u8; 9] = [0, 128, 192, 224, 240, 248, 252, 254, 255];
macro_rules! bits_encode {
[ $( ( $len:expr => [ $( $byte:expr ),* ] ), )* ] => {
[ $(
EncodeValue{
buffer: &[ $( $byte as u8 ),* ],
bit_count: $len
} ,
)* ]
}
}
const HPACK_STRING: [EncodeValue; 256] = bits_encode![
( 13 => [0b1111_1111, 0b0001_1000]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1000]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0010]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0011]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0100]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0101]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0110]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0111]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1000]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1010]),
( 30 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0011_1100]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1001]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1010]),
( 30 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0011_1101]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1011]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1100]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1101]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1110]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_1111]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0000]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0001]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0010]),
( 30 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0011_1110]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0011]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0100]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0101]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0110]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_0111]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1000]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1001]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1010]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1011]),
( 6 => [0b0001_0100]),
( 10 => [0b1111_1110, 0b0000_0000]), ( 10 => [0b1111_1110, 0b0000_0001]), ( 12 => [0b1111_1111, 0b0000_1010]), ( 13 => [0b1111_1111, 0b0001_1001]), ( 6 => [0b0001_0101]), ( 8 => [0b1111_1000]), ( 11 => [0b1111_1111, 0b0000_0010]), ( 10 => [0b1111_1110, 0b0000_0010]), ( 10 => [0b1111_1110, 0b0000_0011]), ( 8 => [0b1111_1001]), ( 11 => [0b1111_1111, 0b0000_0011]), ( 8 => [0b1111_1010]), ( 6 => [0b0001_0110]), ( 6 => [0b0001_0111]), ( 6 => [0b0001_1000]), ( 5 => [0b0000_0000]), ( 5 => [0b0000_0001]), ( 5 => [0b0000_0010]), ( 6 => [0b0001_1001]), ( 6 => [0b0001_1010]), ( 6 => [0b0001_1011]), ( 6 => [0b0001_1100]), ( 6 => [0b0001_1101]), ( 6 => [0b0001_1110]), ( 6 => [0b0001_1111]), ( 7 => [0b0101_1100]), ( 8 => [0b1111_1011]),
( 15 => [0b1111_1111, 0b0111_1100]), ( 6 => [0b0010_0000]), ( 12 => [0b1111_1111, 0b0000_1011]), ( 10 => [0b1111_1111, 0b0000_0000]), ( 13 => [0b1111_1111, 0b0001_1010]), ( 6 => [0b0010_0001]), ( 7 => [0b0101_1101]), ( 7 => [0b0101_1110]), ( 7 => [0b0101_1111]), ( 7 => [0b0110_0000]), ( 7 => [0b0110_0001]), ( 7 => [0b0110_0010]), ( 7 => [0b0110_0011]), ( 7 => [0b0110_0100]), ( 7 => [0b0110_0101]), ( 7 => [0b0110_0110]), ( 7 => [0b0110_0111]), ( 7 => [0b0110_1000]), ( 7 => [0b0110_1001]), ( 7 => [0b0110_1010]), ( 7 => [0b0110_1011]), ( 7 => [0b0110_1100]), ( 7 => [0b0110_1101]), ( 7 => [0b0110_1110]), ( 7 => [0b0110_1111]), ( 7 => [0b0111_0000]), ( 7 => [0b0111_0001]), ( 7 => [0b0111_0010]), ( 8 => [0b1111_1100]), ( 7 => [0b0111_0011]), ( 8 => [0b1111_1101]), ( 13 => [0b1111_1111, 0b0001_1011]), ( 19 => [0b1111_1111, 0b1111_1110, 0b0000_0000]), ( 13 => [0b1111_1111, 0b0001_1100]), ( 14 => [0b1111_1111, 0b0011_1100]), ( 6 => [0b0010_0010]), ( 15 => [0b1111_1111, 0b0111_1101]), ( 5 => [0b0000_0011]), ( 6 => [0b0010_0011]), ( 5 => [0b0000_0100]), ( 6 => [0b0010_0100]), ( 5 => [0b0000_0101]), ( 6 => [0b0010_0101]), ( 6 => [0b0010_0110]), ( 6 => [0b0010_0111]), ( 5 => [0b0000_0110]), ( 7 => [0b0111_0100]), ( 7 => [0b0111_0101]), ( 6 => [0b0010_1000]), ( 6 => [0b0010_1001]), ( 6 => [0b0010_1010]), ( 5 => [0b0000_0111]), ( 6 => [0b0010_1011]), ( 7 => [0b0111_0110]), ( 6 => [0b0010_1100]), ( 5 => [0b0000_1000]), ( 5 => [0b0000_1001]), ( 6 => [0b0010_1101]), ( 7 => [0b0111_0111]), ( 7 => [0b0111_1000]), ( 7 => [0b0111_1001]), ( 7 => [0b0111_1010]), ( 7 => [0b0111_1011]), ( 15 => [0b1111_1111, 0b0111_1110]), ( 11 => [0b1111_1111, 0b0000_0100]), ( 14 => [0b1111_1111, 0b0011_1101]), ( 13 => [0b1111_1111, 0b0001_1101]), ( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1100]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_0110]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0010]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_0111]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1000]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0011]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0100]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0101]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1001]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1010]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1011]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1100]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1101]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1110]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1011]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0101_1111]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1100]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1101]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_0111]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0000]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0001]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0010]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0011]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0100]),
( 21 => [0b1111_1111, 0b1111_1110, 0b0001_1100]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1000]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0101]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1001]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_0111]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1110_1111]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1010]),
( 21 => [0b1111_1111, 0b1111_1110, 0b0001_1101]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1001]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1011]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1100]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1000]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1001]),
( 21 => [0b1111_1111, 0b1111_1110, 0b0001_1110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1010]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1101]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1110]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0000]),
( 21 => [0b1111_1111, 0b1111_1110, 0b0001_1111]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0001_1111]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1011]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1100]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0000]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0001]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0000]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0010]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1101]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0001]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0110_1111]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1010]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0010]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0011]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0100]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0111_0000]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0101]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0110]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0111_0001]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1000, 0b0000_0000]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1000, 0b0000_0001]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1011]),
( 19 => [0b1111_1111, 0b1111_1110, 0b0000_0001]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_0111]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0111_0010]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_1000]),
( 25 => [0b1111_1111, 0b1111_1111, 0b1111_0110, 0b0000_0000]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1000, 0b0000_0010]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1000, 0b0000_0011]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1001, 0b0000_0000]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1011, 0b0000_0110]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1011, 0b0000_0111]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1001, 0b0000_0001]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0001]),
( 25 => [0b1111_1111, 0b1111_1111, 0b1111_0110, 0b0000_0001]),
( 19 => [0b1111_1111, 0b1111_1110, 0b0000_0010]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0011]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1001, 0b0000_0010]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0000]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0001]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1001, 0b0000_0011]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0010]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0010]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0100]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0101]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1010, 0b0000_0000]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1010, 0b0000_0001]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1101]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0011]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0100]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0101]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1100]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0011]),
( 20 => [0b1111_1111, 0b1111_1110, 0b0000_1101]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0110]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_1001]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_0111]),
( 21 => [0b1111_1111, 0b1111_1111, 0b0000_1000]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0111_0011]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_1010]),
( 22 => [0b1111_1111, 0b1111_1111, 0b0010_1011]),
( 25 => [0b1111_1111, 0b1111_1111, 0b1111_0111, 0b0000_0000]),
( 25 => [0b1111_1111, 0b1111_1111, 0b1111_0111, 0b0000_0001]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0100]),
( 24 => [0b1111_1111, 0b1111_1111, 0b1111_0101]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1010, 0b0000_0010]),
( 23 => [0b1111_1111, 0b1111_1111, 0b0111_0100]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1010, 0b0000_0011]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0110]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1011, 0b0000_0000]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1011, 0b0000_0001]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1100, 0b0000_0111]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0000]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0001]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0010]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0011]),
( 28 => [0b1111_1111, 0b1111_1111, 0b1111_1111, 0b0000_1110]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0100]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0101]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0110]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1101, 0b0000_0111]),
( 27 => [0b1111_1111, 0b1111_1111, 0b1111_1110, 0b0000_0000]),
( 26 => [0b1111_1111, 0b1111_1111, 0b1111_1011, 0b0000_0010]),
];
pub trait HpackStringEncode {
fn hpack_encode(&self) -> Result<Vec<u8>, Error>;
}
impl HpackStringEncode for Vec<u8> {
fn hpack_encode(&self) -> Result<Vec<u8>, Error> {
let mut encoder = HuffmanEncoder::new();
for code in self {
encoder.put(*code)?;
}
encoder.ends()
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_set_bits() {
let mut buf = [0b1111_1111; 16];
let mut pos = BitWindow::default();
pos.count = 8;
write_bits(&mut buf, &pos, 0b1_0101);
assert_eq!(&buf[..1], &[0b1_0101]);
pos.byte += 1;
pos.count = 7;
for _ in 0..8 {
write_bits(&mut buf, &pos, 0b101_0101);
pos.forwards(7);
}
assert_eq!(
&buf[1..8],
&[
0b1010_1011,
0b0101_0110,
0b1010_1101,
0b0101_1010,
0b1011_0101,
0b0110_1010,
0b1101_0101
]
);
pos.count = 5;
write_bits(&mut buf, &pos, 0b1_0101);
assert_eq!(&buf[8..9], &[0b1010_1111]);
}
macro_rules! encoding {
[ $( $code:expr => $( $byte:expr ),* ; )* ] => { $( {
let bytes = vec![$( $byte ),*];
let res = vec![ $code ].hpack_encode();
assert_eq!(res, Ok(bytes), "fail to encode {}", $code);
} )* }
}
/**
* https://tools.ietf.org/html/rfc7541
* Appendix B. Huffman Code
*/
#[test]
#[allow(clippy::cognitive_complexity)]
fn test_encode_single_value() {
encoding![
48 => (0b0000_0000 << 3) | /* padding */ 0b0000_0111; // '0'
49 => (0b0000_0001 << 3) | /* padding */ 0b0000_0111; // '1'
50 => (0b0000_0010 << 3) | /* padding */ 0b0000_0111; // '2'
97 => (0b0000_0011 << 3) | /* padding */ 0b0000_0111; // 'a'
99 => (0b0000_0100 << 3) | /* padding */ 0b0000_0111; // 'c'
101 => (0b0000_0101 << 3) | /* padding */ 0b0000_0111; // 'e'
105 => (0b0000_0110 << 3) | /* padding */ 0b0000_0111; // 'i'
111 => (0b0000_0111 << 3) | /* padding */ 0b0000_0111; // 'o'
115 => (0b0000_1000 << 3) | /* padding */ 0b0000_0111; // 's'
116 => (0b0000_1001 << 3) | /* padding */ 0b0000_0111; // 't'
32 => (0b0001_0100 << 2) | /* padding */ 0b0000_0011;
37 => (0b0001_0101 << 2) | /* padding */ 0b0000_0011; // '%'
45 => (0b0001_0110 << 2) | /* padding */ 0b0000_0011; // '-'
46 => (0b0001_0111 << 2) | /* padding */ 0b0000_0011; // '.'
47 => (0b0001_1000 << 2) | /* padding */ 0b0000_0011; // '/'
51 => (0b0001_1001 << 2) | /* padding */ 0b0000_0011; // '3'
52 => (0b0001_1010 << 2) | /* padding */ 0b0000_0011; // '4'
53 => (0b0001_1011 << 2) | /* padding */ 0b0000_0011; // '5'
54 => (0b0001_1100 << 2) | /* padding */ 0b0000_0011; // '6'
55 => (0b0001_1101 << 2) | /* padding */ 0b0000_0011; // '7'
56 => (0b0001_1110 << 2) | /* padding */ 0b0000_0011; // '8'
57 => (0b0001_1111 << 2) | /* padding */ 0b0000_0011; // '9'
61 => (0b0010_0000 << 2) | /* padding */ 0b0000_0011; // '='
65 => (0b0010_0001 << 2) | /* padding */ 0b0000_0011; // 'A'
95 => (0b0010_0010 << 2) | /* padding */ 0b0000_0011; // '_'
98 => (0b0010_0011 << 2) | /* padding */ 0b0000_0011; // 'b'
100 => (0b0010_0100 << 2) | /* padding */ 0b0000_0011; // 'd'
102 => (0b0010_0101 << 2) | /* padding */ 0b0000_0011; // 'f'
103 => (0b0010_0110 << 2) | /* padding */ 0b0000_0011; // 'g'
104 => (0b0010_0111 << 2) | /* padding */ 0b0000_0011; // 'h'
108 => (0b0010_1000 << 2) | /* padding */ 0b0000_0011; // 'l'
109 => (0b0010_1001 << 2) | /* padding */ 0b0000_0011; // 'm'
110 => (0b0010_1010 << 2) | /* padding */ 0b0000_0011; // 'n'
112 => (0b0010_1011 << 2) | /* padding */ 0b0000_0011; // 'p'
114 => (0b0010_1100 << 2) | /* padding */ 0b0000_0011; // 'r'
117 => (0b0010_1101 << 2) | /* padding */ 0b0000_0011; // 'u'
58 => (0b0101_1100 << 1) | /* padding */ 0b0000_0001; // ':'
66 => (0b0101_1101 << 1) | /* padding */ 0b0000_0001; // 'B'
67 => (0b0101_1110 << 1) | /* padding */ 0b0000_0001; // 'C'
68 => (0b0101_1111 << 1) | /* padding */ 0b0000_0001; // 'D'
69 => (0b0110_0000 << 1) | /* padding */ 0b0000_0001; // 'E'
70 => (0b0110_0001 << 1) | /* padding */ 0b0000_0001; // 'F'
71 => (0b0110_0010 << 1) | /* padding */ 0b0000_0001; // 'G'
72 => (0b0110_0011 << 1) | /* padding */ 0b0000_0001; // 'H'
73 => (0b0110_0100 << 1) | /* padding */ 0b0000_0001; // 'I'
74 => (0b0110_0101 << 1) | /* padding */ 0b0000_0001; // 'J'
75 => (0b0110_0110 << 1) | /* padding */ 0b0000_0001; // 'K'
76 => (0b0110_0111 << 1) | /* padding */ 0b0000_0001; // 'L'
77 => (0b0110_1000 << 1) | /* padding */ 0b0000_0001; // 'M'
78 => (0b0110_1001 << 1) | /* padding */ 0b0000_0001; // 'N'
79 => (0b0110_1010 << 1) | /* padding */ 0b0000_0001; // 'O'
80 => (0b0110_1011 << 1) | /* padding */ 0b0000_0001; // 'P'
81 => (0b0110_1100 << 1) | /* padding */ 0b0000_0001; // 'Q'
82 => (0b0110_1101 << 1) | /* padding */ 0b0000_0001; // 'R'
83 => (0b0110_1110 << 1) | /* padding */ 0b0000_0001; // 'S'
84 => (0b0110_1111 << 1) | /* padding */ 0b0000_0001; // 'T'
85 => (0b0111_0000 << 1) | /* padding */ 0b0000_0001; // 'U'
86 => (0b0111_0001 << 1) | /* padding */ 0b0000_0001; // 'V'
87 => (0b0111_0010 << 1) | /* padding */ 0b0000_0001; // 'W'
89 => (0b0111_0011 << 1) | /* padding */ 0b0000_0001; // 'Y'
106 => (0b0111_0100 << 1) | /* padding */ 0b0000_0001; // 'j'
107 => (0b0111_0101 << 1) | /* padding */ 0b0000_0001; // 'k'
113 => (0b0111_0110 << 1) | /* padding */ 0b0000_0001; // 'q'
118 => (0b0111_0111 << 1) | /* padding */ 0b0000_0001; // 'v'
119 => (0b0111_1000 << 1) | /* padding */ 0b0000_0001; // 'w'
120 => (0b0111_1001 << 1) | /* padding */ 0b0000_0001; // 'x'
121 => (0b0111_1010 << 1) | /* padding */ 0b0000_0001; // 'y'
122 => (0b0111_1011 << 1) | /* padding */ 0b0000_0001; // 'z'
38 => 0b1111_1000; // '&'
42 => 0b1111_1001; // '*'
44 => 0b1111_1010; // ','
59 => 0b1111_1011;
88 => 0b1111_1100; // 'X'
90 => 0b1111_1101; // 'Z'
33 => 0b1111_1110, (0b0000_0000 << 6) | /* padding */ 0b0011_1111; // '!'
34 => 0b1111_1110, (0b0000_0001 << 6) | /* padding */ 0b0011_1111; // '"'
40 => 0b1111_1110, (0b0000_0010 << 6) | 0b0011_1111; 41 => 0b1111_1110, (0b0000_0011 << 6) | 0b0011_1111; 63 => 0b1111_1111, (0b0000_0000 << 6) | 0b0011_1111; 39 => 0b1111_1111, (0b0000_0010 << 5) | 0b0001_1111; 43 => 0b1111_1111, (0b0000_0011 << 5) | 0b0001_1111; 124 => 0b1111_1111, (0b0000_0100 << 5) | 0b0001_1111; 35 => 0b1111_1111, (0b0000_1010 << 4) | 0b0000_1111; 62 => 0b1111_1111, (0b0000_1011 << 4) | 0b0000_1111; 0 => 0b1111_1111, (0b0001_1000 << 3) | 0b0000_0111;
36 => 0b1111_1111, (0b0001_1001 << 3) | 0b0000_0111; 64 => 0b1111_1111, (0b0001_1010 << 3) | 0b0000_0111; 91 => 0b1111_1111, (0b0001_1011 << 3) | 0b0000_0111; 93 => 0b1111_1111, (0b0001_1100 << 3) | 0b0000_0111; 126 => 0b1111_1111, (0b0001_1101 << 3) | 0b0000_0111; 94 => 0b1111_1111, (0b0011_1100 << 2) | 0b0000_0011; 125 => 0b1111_1111, (0b0011_1101 << 2) | 0b0000_0011; 60 => 0b1111_1111, (0b0111_1100 << 1) | 0b0000_0001; 96 => 0b1111_1111, (0b0111_1101 << 1) | 0b0000_0001; 123 => 0b1111_1111, (0b0111_1110 << 1) | 0b0000_0001; 92 => 0b1111_1111, 0b1111_1110, (0b0000_0000 << 5) | 0b0001_1111; 195 => 0b1111_1111, 0b1111_1110, (0b0000_0001 << 5) | 0b0001_1111;
208 => 0b1111_1111, 0b1111_1110, (0b0000_0010 << 5) | 0b0001_1111;
128 => 0b1111_1111, 0b1111_1110, (0b0000_0110 << 4) | 0b0000_1111;
130 => 0b1111_1111, 0b1111_1110, (0b0000_0111 << 4) | 0b0000_1111;
131 => 0b1111_1111, 0b1111_1110, (0b0000_1000 << 4) | 0b0000_1111;
162 => 0b1111_1111, 0b1111_1110, (0b0000_1001 << 4) | 0b0000_1111;
184 => 0b1111_1111, 0b1111_1110, (0b0000_1010 << 4) | 0b0000_1111;
194 => 0b1111_1111, 0b1111_1110, (0b0000_1011 << 4) | 0b0000_1111;
224 => 0b1111_1111, 0b1111_1110, (0b0000_1100 << 4) | 0b0000_1111;
226 => 0b1111_1111, 0b1111_1110, (0b0000_1101 << 4) | 0b0000_1111;
153 => 0b1111_1111, 0b1111_1110, (0b0001_1100 << 3) | 0b0000_0111;
161 => 0b1111_1111, 0b1111_1110, (0b0001_1101 << 3) | 0b0000_0111;
167 => 0b1111_1111, 0b1111_1110, (0b0001_1110 << 3) | 0b0000_0111;
172 => 0b1111_1111, 0b1111_1110, (0b0001_1111 << 3) | 0b0000_0111;
176 => 0b1111_1111, 0b1111_1111, (0b0000_0000 << 3) | 0b0000_0111;
177 => 0b1111_1111, 0b1111_1111, (0b0000_0001 << 3) | 0b0000_0111;
179 => 0b1111_1111, 0b1111_1111, (0b0000_0010 << 3) | 0b0000_0111;
209 => 0b1111_1111, 0b1111_1111, (0b0000_0011 << 3) | 0b0000_0111;
216 => 0b1111_1111, 0b1111_1111, (0b0000_0100 << 3) | 0b0000_0111;
217 => 0b1111_1111, 0b1111_1111, (0b0000_0101 << 3) | 0b0000_0111;
227 => 0b1111_1111, 0b1111_1111, (0b0000_0110 << 3) | 0b0000_0111;
229 => 0b1111_1111, 0b1111_1111, (0b0000_0111 << 3) | 0b0000_0111;
230 => 0b1111_1111, 0b1111_1111, (0b0000_1000 << 3) | 0b0000_0111;
129 => 0b1111_1111, 0b1111_1111, (0b0001_0010 << 2) | 0b0000_0011;
132 => 0b1111_1111, 0b1111_1111, (0b0001_0011 << 2) | 0b0000_0011;
133 => 0b1111_1111, 0b1111_1111, (0b0001_0100 << 2) | 0b0000_0011;
134 => 0b1111_1111, 0b1111_1111, (0b0001_0101 << 2) | 0b0000_0011;
136 => 0b1111_1111, 0b1111_1111, (0b0001_0110 << 2) | 0b0000_0011;
146 => 0b1111_1111, 0b1111_1111, (0b0001_0111 << 2) | 0b0000_0011;
154 => 0b1111_1111, 0b1111_1111, (0b0001_1000 << 2) | 0b0000_0011;
156 => 0b1111_1111, 0b1111_1111, (0b0001_1001 << 2) | 0b0000_0011;
160 => 0b1111_1111, 0b1111_1111, (0b0001_1010 << 2) | 0b0000_0011;
163 => 0b1111_1111, 0b1111_1111, (0b0001_1011 << 2) | 0b0000_0011;
164 => 0b1111_1111, 0b1111_1111, (0b0001_1100 << 2) | 0b0000_0011;
169 => 0b1111_1111, 0b1111_1111, (0b0001_1101 << 2) | 0b0000_0011;
170 => 0b1111_1111, 0b1111_1111, (0b0001_1110 << 2) | 0b0000_0011;
173 => 0b1111_1111, 0b1111_1111, (0b0001_1111 << 2) | 0b0000_0011;
178 => 0b1111_1111, 0b1111_1111, (0b0010_0000 << 2) | 0b0000_0011;
181 => 0b1111_1111, 0b1111_1111, (0b0010_0001 << 2) | 0b0000_0011;
185 => 0b1111_1111, 0b1111_1111, (0b0010_0010 << 2) | 0b0000_0011;
186 => 0b1111_1111, 0b1111_1111, (0b0010_0011 << 2) | 0b0000_0011;
187 => 0b1111_1111, 0b1111_1111, (0b0010_0100 << 2) | 0b0000_0011;
189 => 0b1111_1111, 0b1111_1111, (0b0010_0101 << 2) | 0b0000_0011;
190 => 0b1111_1111, 0b1111_1111, (0b0010_0110 << 2) | 0b0000_0011;
196 => 0b1111_1111, 0b1111_1111, (0b0010_0111 << 2) | 0b0000_0011;
198 => 0b1111_1111, 0b1111_1111, (0b0010_1000 << 2) | 0b0000_0011;
228 => 0b1111_1111, 0b1111_1111, (0b0010_1001 << 2) | 0b0000_0011;
232 => 0b1111_1111, 0b1111_1111, (0b0010_1010 << 2) | 0b0000_0011;
233 => 0b1111_1111, 0b1111_1111, (0b0010_1011 << 2) | 0b0000_0011;
1 => 0b1111_1111, 0b1111_1111, (0b0101_1000 << 1) | 0b0000_0001;
135 => 0b1111_1111, 0b1111_1111, (0b0101_1001 << 1) | 0b0000_0001;
137 => 0b1111_1111, 0b1111_1111, (0b0101_1010 << 1) | 0b0000_0001;
138 => 0b1111_1111, 0b1111_1111, (0b0101_1011 << 1) | 0b0000_0001;
139 => 0b1111_1111, 0b1111_1111, (0b0101_1100 << 1) | 0b0000_0001;
140 => 0b1111_1111, 0b1111_1111, (0b0101_1101 << 1) | 0b0000_0001;
141 => 0b1111_1111, 0b1111_1111, (0b0101_1110 << 1) | 0b0000_0001;
143 => 0b1111_1111, 0b1111_1111, (0b0101_1111 << 1) | 0b0000_0001;
147 => 0b1111_1111, 0b1111_1111, (0b0110_0000 << 1) | 0b0000_0001;
149 => 0b1111_1111, 0b1111_1111, (0b0110_0001 << 1) | 0b0000_0001;
150 => 0b1111_1111, 0b1111_1111, (0b0110_0010 << 1) | 0b0000_0001;
151 => 0b1111_1111, 0b1111_1111, (0b0110_0011 << 1) | 0b0000_0001;
152 => 0b1111_1111, 0b1111_1111, (0b0110_0100 << 1) | 0b0000_0001;
155 => 0b1111_1111, 0b1111_1111, (0b0110_0101 << 1) | 0b0000_0001;
157 => 0b1111_1111, 0b1111_1111, (0b0110_0110 << 1) | 0b0000_0001;
158 => 0b1111_1111, 0b1111_1111, (0b0110_0111 << 1) | 0b0000_0001;
165 => 0b1111_1111, 0b1111_1111, (0b0110_1000 << 1) | 0b0000_0001;
166 => 0b1111_1111, 0b1111_1111, (0b0110_1001 << 1) | 0b0000_0001;
168 => 0b1111_1111, 0b1111_1111, (0b0110_1010 << 1) | 0b0000_0001;
174 => 0b1111_1111, 0b1111_1111, (0b0110_1011 << 1) | 0b0000_0001;
175 => 0b1111_1111, 0b1111_1111, (0b0110_1100 << 1) | 0b0000_0001;
180 => 0b1111_1111, 0b1111_1111, (0b0110_1101 << 1) | 0b0000_0001;
182 => 0b1111_1111, 0b1111_1111, (0b0110_1110 << 1) | 0b0000_0001;
183 => 0b1111_1111, 0b1111_1111, (0b0110_1111 << 1) | 0b0000_0001;
188 => 0b1111_1111, 0b1111_1111, (0b0111_0000 << 1) | 0b0000_0001;
191 => 0b1111_1111, 0b1111_1111, (0b0111_0001 << 1) | 0b0000_0001;
197 => 0b1111_1111, 0b1111_1111, (0b0111_0010 << 1) | 0b0000_0001;
231 => 0b1111_1111, 0b1111_1111, (0b0111_0011 << 1) | 0b0000_0001;
239 => 0b1111_1111, 0b1111_1111, (0b0111_0100 << 1) | 0b0000_0001;
9 => 0b1111_1111, 0b1111_1111, 0b1110_1010;
142 => 0b1111_1111, 0b1111_1111, 0b1110_1011;
144 => 0b1111_1111, 0b1111_1111, 0b1110_1100;
145 => 0b1111_1111, 0b1111_1111, 0b1110_1101;
148 => 0b1111_1111, 0b1111_1111, 0b1110_1110;
159 => 0b1111_1111, 0b1111_1111, 0b1110_1111;
171 => 0b1111_1111, 0b1111_1111, 0b1111_0000;
206 => 0b1111_1111, 0b1111_1111, 0b1111_0001;
215 => 0b1111_1111, 0b1111_1111, 0b1111_0010;
225 => 0b1111_1111, 0b1111_1111, 0b1111_0011;
236 => 0b1111_1111, 0b1111_1111, 0b1111_0100;
237 => 0b1111_1111, 0b1111_1111, 0b1111_0101;
199 => 0b1111_1111, 0b1111_1111, 0b1111_0110, (0b0000_0000 << 7) | 0b0111_1111;
207 => 0b1111_1111, 0b1111_1111, 0b1111_0110, (0b0000_0001 << 7) | 0b0111_1111;
234 => 0b1111_1111, 0b1111_1111, 0b1111_0111, (0b0000_0000 << 7) | 0b0111_1111;
235 => 0b1111_1111, 0b1111_1111, 0b1111_0111, (0b0000_0001 << 7) | 0b0111_1111;
192 => 0b1111_1111, 0b1111_1111, 0b1111_1000, (0b0000_0000 << 6) | 0b0011_1111;
193 => 0b1111_1111, 0b1111_1111, 0b1111_1000, (0b0000_0001 << 6) | 0b0011_1111;
200 => 0b1111_1111, 0b1111_1111, 0b1111_1000, (0b0000_0010 << 6) | 0b0011_1111;
201 => 0b1111_1111, 0b1111_1111, 0b1111_1000, (0b0000_0011 << 6) | 0b0011_1111;
202 => 0b1111_1111, 0b1111_1111, 0b1111_1001, (0b0000_0000 << 6) | 0b0011_1111;
205 => 0b1111_1111, 0b1111_1111, 0b1111_1001, (0b0000_0001 << 6) | 0b0011_1111;
210 => 0b1111_1111, 0b1111_1111, 0b1111_1001, (0b0000_0010 << 6) | 0b0011_1111;
213 => 0b1111_1111, 0b1111_1111, 0b1111_1001, (0b0000_0011 << 6) | 0b0011_1111;
218 => 0b1111_1111, 0b1111_1111, 0b1111_1010, (0b0000_0000 << 6) | 0b0011_1111;
219 => 0b1111_1111, 0b1111_1111, 0b1111_1010, (0b0000_0001 << 6) | 0b0011_1111;
238 => 0b1111_1111, 0b1111_1111, 0b1111_1010, (0b0000_0010 << 6) | 0b0011_1111;
240 => 0b1111_1111, 0b1111_1111, 0b1111_1010, (0b0000_0011 << 6) | 0b0011_1111;
242 => 0b1111_1111, 0b1111_1111, 0b1111_1011, (0b0000_0000 << 6) | 0b0011_1111;
243 => 0b1111_1111, 0b1111_1111, 0b1111_1011, (0b0000_0001 << 6) | 0b0011_1111;
255 => 0b1111_1111, 0b1111_1111, 0b1111_1011, (0b0000_0010 << 6) | 0b0011_1111;
203 => 0b1111_1111, 0b1111_1111, 0b1111_1011, (0b0000_0110 << 5) | 0b0001_1111;
204 => 0b1111_1111, 0b1111_1111, 0b1111_1011, (0b0000_0111 << 5) | 0b0001_1111;
211 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0000 << 5) | 0b0001_1111;
212 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0001 << 5) | 0b0001_1111;
214 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0010 << 5) | 0b0001_1111;
221 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0011 << 5) | 0b0001_1111;
222 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0100 << 5) | 0b0001_1111;
223 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0101 << 5) | 0b0001_1111;
241 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0110 << 5) | 0b0001_1111;
244 => 0b1111_1111, 0b1111_1111, 0b1111_1100, (0b0000_0111 << 5) | 0b0001_1111;
245 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0000 << 5) | 0b0001_1111;
246 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0001 << 5) | 0b0001_1111;
247 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0010 << 5) | 0b0001_1111;
248 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0011 << 5) | 0b0001_1111;
250 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0100 << 5) | 0b0001_1111;
251 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0101 << 5) | 0b0001_1111;
252 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0110 << 5) | 0b0001_1111;
253 => 0b1111_1111, 0b1111_1111, 0b1111_1101, (0b0000_0111 << 5) | 0b0001_1111;
254 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0000 << 5) | 0b0001_1111;
2 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0010 << 4) | 0b0000_1111;
3 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0011 << 4) | 0b0000_1111;
4 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0100 << 4) | 0b0000_1111;
5 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0101 << 4) | 0b0000_1111;
6 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0110 << 4) | 0b0000_1111;
7 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_0111 << 4) | 0b0000_1111;
8 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1000 << 4) | 0b0000_1111;
11 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1001 << 4) | 0b0000_1111;
12 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1010 << 4) | 0b0000_1111;
14 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1011 << 4) | 0b0000_1111;
15 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1100 << 4) | 0b0000_1111;
16 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1101 << 4) | 0b0000_1111;
17 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1110 << 4) | 0b0000_1111;
18 => 0b1111_1111, 0b1111_1111, 0b1111_1110, (0b0000_1111 << 4) | 0b0000_1111;
19 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0000 << 4) | 0b0000_1111;
20 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0001 << 4) | 0b0000_1111;
21 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0010 << 4) | 0b0000_1111;
23 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0011 << 4) | 0b0000_1111;
24 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0100 << 4) | 0b0000_1111;
25 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0101 << 4) | 0b0000_1111;
26 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0110 << 4) | 0b0000_1111;
27 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_0111 << 4) | 0b0000_1111;
28 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1000 << 4) | 0b0000_1111;
29 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1001 << 4) | 0b0000_1111;
30 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1010 << 4) | 0b0000_1111;
31 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1011 << 4) | 0b0000_1111;
127 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1100 << 4) | 0b0000_1111;
220 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1101 << 4) | 0b0000_1111;
249 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0000_1110 << 4) | 0b0000_1111;
10 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0011_1100 << 2) | 0b0000_0011;
13 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0011_1101 << 2) | 0b0000_0011;
22 => 0b1111_1111, 0b1111_1111, 0b1111_1111, (0b0011_1110 << 2) | 0b0000_0011;
];
}
#[test]
fn test_encode_all_code_joined() {
let bytes = vec![
0b1111_1111,
(0b0001_1000 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1101,
(0b0000_1000 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_0010,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0011 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_0100,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0101 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_0110,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0111 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_1000,
0b1111_1111,
0b1111_1111,
0b1110_1010,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0011_1100 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1010,
(0b0000_0001 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0010_1010 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0000_1101 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_1011,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_1101,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1110 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1110_1111,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0000 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1111_0001,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0010 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0011_0011 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0000 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0011_0101 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0011_0111 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0000 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0011_1001 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0011_1011 << 2)
+ 0b0000_0001,
(0b0000_0100 << 4)
+ 0b0000_1111,
(0b0011_1000 << 2)
+ 0b0000_0011,
0b1111_1001,
0b1111_1111,
(0b0000_1010 << 4)
+ 0b0000_1111,
0b1111_1100,
(0b0000_0001 << 7)
+ (0b0001_0101 << 1)
+ 0b0000_0001,
(0b0111_1000 << 1)
+ 0b0000_0001,
0b1111_1110,
(0b0000_0010 << 6)
+ 0b0011_1111,
(0b0000_1010 << 4)
+ 0b0000_1111,
(0b0011_1011 << 2)
+ 0b0000_0011,
(0b0011_1001 << 2)
+ 0b0000_0011,
0b1111_1101,
(0b0000_0001 << 7)
+ 0b0111_1101,
(0b0000_0000 << 7)
+ (0b0001_0110 << 1)
+ 0b0000_0000,
(0b0001_0111 << 3)
+ 0b0000_0011,
(0b0000_0000 << 5)
+ 0b0000_0000,
(0b0000_0001 << 3)
+ 0b0000_0000,
(0b0000_0010 << 6)
+ 0b0001_1001,
(0b0001_1010 << 2)
+ 0b0000_0001,
(0b0000_1011 << 4)
+ 0b0000_0111,
(0b0000_0000 << 6)
+ 0b0001_1101,
(0b0001_1110 << 2)
+ 0b0000_0001,
(0b0000_1111 << 4)
+ 0b0000_1011,
(0b0000_0100 << 5)
+ 0b0001_1111,
(0b0000_0011 << 5)
+ 0b0001_1111,
0b1111_1111,
(0b0000_0000 << 6)
+ 0b0010_0000,
0b1111_1111,
(0b0000_1011 << 4)
+ 0b0000_1111,
(0b0011_1100 << 2)
+ 0b0000_0011,
0b1111_1111,
(0b0000_0010 << 5)
+ 0b0001_0000,
(0b0000_0001 << 7)
+ 0b0101_1101,
(0b0101_1110 << 1)
+ 0b0000_0001,
(0b0001_1111 << 2)
+ 0b0000_0011,
(0b0000_0000 << 3)
+ 0b0000_0110,
(0b0000_0001 << 4)
+ 0b0000_1100,
(0b0000_0010 << 5)
+ 0b0001_1000,
(0b0000_0011 << 6)
+ 0b0011_0010,
(0b0000_0000 << 7)
+ 0b0110_0101,
(0b0110_0110 << 1)
+ 0b0000_0001,
(0b0010_0111 << 2)
+ 0b0000_0011,
(0b0000_1000 << 3)
+ 0b0000_0110,
(0b0000_1001 << 4)
+ 0b0000_1101,
(0b0000_0010 << 5)
+ 0b0001_1010,
(0b0000_0011 << 6)
+ 0b0011_0110,
(0b0000_0000 << 7)
+ 0b0110_1101,
(0b0110_1110 << 1)
+ 0b0000_0001,
(0b0010_1111 << 2)
+ 0b0000_0011,
(0b0001_0000 << 3)
+ 0b0000_0111,
(0b0000_0001 << 4)
+ 0b0000_1110,
(0b0000_0010 << 5)
+ 0b0001_1111,
(0b0000_0100 << 5)
+ 0b0001_1100,
(0b0000_0011 << 6)
+ 0b0011_1111,
(0b0000_0001 << 6)
+ 0b0011_1111,
(0b0111_1011 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1100,
(0b0000_0000 << 6)
+ 0b0011_1111,
(0b0111_1100 << 1)
+ 0b0000_0001,
0b1111_1111,
(0b0001_1100 << 3)
+ 0b0000_0100,
(0b0000_0010 << 5)
+ 0b0001_1111,
0b1111_1111,
(0b0000_0001 << 6)
+ (0b0000_0011 << 1)
+ 0b0000_0001,
(0b0000_0011 << 3)
+ 0b0000_0001,
(0b0000_0000 << 6)
+ 0b0010_0100,
(0b0000_0101 << 3)
+ 0b0000_0100,
(0b0000_0101 << 5)
+ 0b0001_0011,
(0b0000_0000 << 7)
+ (0b0010_0111 << 1)
+ 0b0000_0000,
(0b0000_0110 << 4)
+ 0b0000_1110,
(0b0000_0100 << 5)
+ 0b0001_1101,
(0b0000_0001 << 6)
+ 0b0010_1000,
(0b0010_1001 << 2)
+ 0b0000_0010,
(0b0000_1010 << 4)
+ 0b0000_0011,
(0b0000_0001 << 7)
+ (0b0010_1011 << 1)
+ 0b0000_0001,
(0b0011_0110 << 2)
+ 0b0000_0010,
(0b0000_1100 << 4)
+ 0b0000_0100,
(0b0000_0000 << 7)
+ (0b0000_1001 << 2)
+ 0b0000_0010,
(0b0000_1101 << 4)
+ 0b0000_1110,
(0b0000_0111 << 5)
+ 0b0001_1110,
(0b0000_0000 << 6)
+ 0b0011_1100,
(0b0000_0001 << 7)
+ 0b0111_1010,
(0b0111_1011 << 1)
+ 0b0000_0001,
0b1111_1111,
(0b0011_1110 << 2)
+ 0b0000_0011,
0b1111_1110,
(0b0000_0000 << 7)
+ 0b0111_1111,
(0b0111_1101 << 1)
+ 0b0000_0001,
0b1111_1111,
(0b0000_1101 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
0b1111_1100,
0b1111_1111,
0b1111_1110,
(0b0000_0110 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_0100,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
(0b0010_0111 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1010,
(0b0000_0000 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1101_0011,
0b1111_1111,
0b1111_1111,
(0b0001_0100 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1101,
(0b0000_0101 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0001 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1110_1011,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1101_1010,
0b1111_1111,
0b1111_1111,
(0b0101_1011 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0001_1100 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1110,
(0b0001_1101 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1101,
(0b0000_1110 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1011 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0111 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0100 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0101 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1110_1011,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1110_0000,
0b1111_1111,
0b1111_1111,
0b1110_1110,
0b1111_1111,
0b1111_1111,
(0b0110_0001 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0010_0010 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
(0b0000_0011 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1110,
(0b0000_0100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1110_1110,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
(0b0101_1000 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0010_0101 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1101,
(0b0000_1001 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1100,
(0b0000_0110 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1001,
(0b0000_0011 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0011 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1101_1010,
0b1111_1111,
0b1111_1110,
(0b0001_1101 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_0100,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
(0b0101_1011 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1110,
(0b0001_1100 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1110,
(0b0000_1000 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0001 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1101_1110,
0b1111_1111,
0b1111_1111,
(0b0110_1010 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1110,
(0b0001_1101 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1011,
(0b0000_0110 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0000 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1101_1111,
0b1111_1111,
0b1111_1111,
(0b0001_1111 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
(0b0000_1011 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1110,
(0b0000_1100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_0000,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
(0b0010_0001 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1110,
(0b0000_0000 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_0001,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1110_1101,
0b1111_1111,
0b1111_1111,
(0b0010_0001 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
(0b0000_1110 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1110,
(0b0000_1111 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1110_1010,
0b1111_1111,
0b1111_1111,
(0b0010_0010 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1110,
(0b0000_0011 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1001,
(0b0000_0000 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1000,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
(0b0110_0101 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0000_0110 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
(0b0000_0001 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0010_0000 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1110_0001,
0b1111_1111,
0b1111_1110,
(0b0000_1011 << 4)
+ 0b0000_1111,
0b1111_1111,
(0b0111_0001 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0000_0111 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
(0b0000_0010 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1010,
(0b0000_0000 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0100 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0010 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
(0b0110_0011 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_0010,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1101,
(0b0000_1110 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0101_1111 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_0010,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1000,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0001 << 6)
+ 0b0011_1111,
0b1111_1111,
(0b0001_0010 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1000,
(0b0000_0011 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0110 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0110_0000 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_1000,
(0b0000_0001 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0111 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0110_0010 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0111_0010 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1110,
(0b0000_0100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_0010,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0000 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1111,
(0b0000_1001 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_0011 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0110_0100 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_1001,
(0b0000_0001 << 6)
+ 0b0011_1111,
0b1111_1111,
(0b0010_1100 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
(0b0011_0011 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1011,
(0b0000_0001 << 6)
+ 0b0011_1111,
0b1111_1111,
(0b0110_0110 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0000_1001 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1001,
(0b0000_0011 << 6)
+ 0b0011_1111,
0b1111_1111,
(0b0110_1000 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
(0b0011_0011 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1110,
(0b0000_1010 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1010,
(0b0000_0011 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1101,
(0b0000_0110 << 5)
+ 0b0001_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1111 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0101 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0010_1010 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
(0b0001_0100 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
(0b0110_1011 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_1001,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0010_1101 << 2)
+ 0b0000_0011,
0b1111_1111,
0b1111_1111,
0b1111_0011,
(0b0000_0001 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1000 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0110_1001 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_1010,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0000_1011 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
0b1111_1111,
(0b0000_0000 << 7)
+ 0b0111_1111,
0b1111_1111,
0b1111_1110,
(0b0000_1100 << 4)
+ 0b0000_1111,
0b1111_1111,
0b1111_1111,
(0b0110_1101 << 1)
+ 0b0000_0001,
0b1111_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0010 << 6)
+ 0b0011_1111,
0b1111_1111,
0b1111_1111,
(0b0000_1111 << 3)
+ 0b0000_0111,
0b1111_1111,
0b1111_1111,
0b1111_0000,
0b1111_1111,
0b1111_1111,
0b1111_1011,
(0b0000_0010 << 6)
+ 0b0011_1111,
];
let values: Vec<u8> = (0..=255).collect();
let res = values.hpack_encode();
assert_eq!(res, Ok(bytes));
}
use super::super::HpackStringDecode;
#[test]
fn byte_count_exact_when_bit_count_multiple_of_8() {
let encoded = vec![
0x8c, 0x2d, 0x4b, 0x70, 0xdd, 0xf4, 0x5a, 0xbe, 0xfb, 0x40, 0x05, 0xdb,
];
let mut res = Vec::new();
for byte in encoded.hpack_decode() {
res.push(byte.unwrap());
}
let reencoded = res.hpack_encode();
assert_eq!(reencoded.unwrap().last(), Some(&0xdb));
}
#[test]
fn byte_() {
let encoded = vec![
0x55, 0x92, 0xbe, 0xff, 0x48, 0x36, 0xcb, 0x86, 0x37, 0x3d, 0x68, 0xca, 0xc9, 0x61,
0xce, 0xde, 0xdc, 0xe5, 0xfc,
];
let mut res = Vec::new();
for byte in encoded.hpack_decode() {
res.push(byte.unwrap());
}
let reencoded = res.hpack_encode();
assert_eq!(reencoded.unwrap().last(), Some(&0xfc));
}
}