1pub struct HpackHuffman;
2
3pub const CODES: [(u32, u8); 257] = [
4 (0x1ff8, 13),
5 (0x7fffd8, 23),
6 (0xfffffe2, 28),
7 (0xfffffe3, 28),
8 (0xfffffe4, 28),
9 (0xfffffe5, 28),
10 (0xfffffe6, 28),
11 (0xfffffe7, 28),
12 (0xfffffe8, 28),
13 (0xffffea, 24),
14 (0x3ffffffc, 30),
15 (0xfffffe9, 28),
16 (0xfffffea, 28),
17 (0x3ffffffd, 30),
18 (0xfffffeb, 28),
19 (0xfffffec, 28),
20 (0xfffffed, 28),
21 (0xfffffee, 28),
22 (0xfffffef, 28),
23 (0xffffff0, 28),
24 (0xffffff1, 28),
25 (0xffffff2, 28),
26 (0x3ffffffe, 30),
27 (0xffffff3, 28),
28 (0xffffff4, 28),
29 (0xffffff5, 28),
30 (0xffffff6, 28),
31 (0xffffff7, 28),
32 (0xffffff8, 28),
33 (0xffffff9, 28),
34 (0xffffffa, 28),
35 (0xffffffb, 28),
36 (0x14, 6),
37 (0x3f8, 10),
38 (0x3f9, 10),
39 (0xffa, 12),
40 (0x1ff9, 13),
41 (0x15, 6),
42 (0xf8, 8),
43 (0x7fa, 11),
44 (0x3fa, 10),
45 (0x3fb, 10),
46 (0xf9, 8),
47 (0x7fb, 11),
48 (0xfa, 8),
49 (0x16, 6),
50 (0x17, 6),
51 (0x18, 6),
52 (0x0, 5),
53 (0x1, 5),
54 (0x2, 5),
55 (0x19, 6),
56 (0x1a, 6),
57 (0x1b, 6),
58 (0x1c, 6),
59 (0x1d, 6),
60 (0x1e, 6),
61 (0x1f, 6),
62 (0x5c, 7),
63 (0xfb, 8),
64 (0x7ffc, 15),
65 (0x20, 6),
66 (0xffb, 12),
67 (0x3fc, 10),
68 (0x1ffa, 13),
69 (0x21, 6),
70 (0x5d, 7),
71 (0x5e, 7),
72 (0x5f, 7),
73 (0x60, 7),
74 (0x61, 7),
75 (0x62, 7),
76 (0x63, 7),
77 (0x64, 7),
78 (0x65, 7),
79 (0x66, 7),
80 (0x67, 7),
81 (0x68, 7),
82 (0x69, 7),
83 (0x6a, 7),
84 (0x6b, 7),
85 (0x6c, 7),
86 (0x6d, 7),
87 (0x6e, 7),
88 (0x6f, 7),
89 (0x70, 7),
90 (0x71, 7),
91 (0x72, 7),
92 (0xfc, 8),
93 (0x73, 7),
94 (0xfd, 8),
95 (0x1ffb, 13),
96 (0x7fff0, 19),
97 (0x1ffc, 13),
98 (0x3ffc, 14),
99 (0x22, 6),
100 (0x7ffd, 15),
101 (0x3, 5),
102 (0x23, 6),
103 (0x4, 5),
104 (0x24, 6),
105 (0x5, 5),
106 (0x25, 6),
107 (0x26, 6),
108 (0x27, 6),
109 (0x6, 5),
110 (0x74, 7),
111 (0x75, 7),
112 (0x28, 6),
113 (0x29, 6),
114 (0x2a, 6),
115 (0x7, 5),
116 (0x2b, 6),
117 (0x76, 7),
118 (0x2c, 6),
119 (0x8, 5),
120 (0x9, 5),
121 (0x2d, 6),
122 (0x77, 7),
123 (0x78, 7),
124 (0x79, 7),
125 (0x7a, 7),
126 (0x7b, 7),
127 (0x7ffe, 15),
128 (0x7fc, 11),
129 (0x3ffd, 14),
130 (0x1ffd, 13),
131 (0xffffffc, 28),
132 (0xfffe6, 20),
133 (0x3fffd2, 22),
134 (0xfffe7, 20),
135 (0xfffe8, 20),
136 (0x3fffd3, 22),
137 (0x3fffd4, 22),
138 (0x3fffd5, 22),
139 (0x7fffd9, 23),
140 (0x3fffd6, 22),
141 (0x7fffda, 23),
142 (0x7fffdb, 23),
143 (0x7fffdc, 23),
144 (0x7fffdd, 23),
145 (0x7fffde, 23),
146 (0xffffeb, 24),
147 (0x7fffdf, 23),
148 (0xffffec, 24),
149 (0xffffed, 24),
150 (0x3fffd7, 22),
151 (0x7fffe0, 23),
152 (0xffffee, 24),
153 (0x7fffe1, 23),
154 (0x7fffe2, 23),
155 (0x7fffe3, 23),
156 (0x7fffe4, 23),
157 (0x1fffdc, 21),
158 (0x3fffd8, 22),
159 (0x7fffe5, 23),
160 (0x3fffd9, 22),
161 (0x7fffe6, 23),
162 (0x7fffe7, 23),
163 (0xffffef, 24),
164 (0x3fffda, 22),
165 (0x1fffdd, 21),
166 (0xfffe9, 20),
167 (0x3fffdb, 22),
168 (0x3fffdc, 22),
169 (0x7fffe8, 23),
170 (0x7fffe9, 23),
171 (0x1fffde, 21),
172 (0x7fffea, 23),
173 (0x3fffdd, 22),
174 (0x3fffde, 22),
175 (0xfffff0, 24),
176 (0x1fffdf, 21),
177 (0x3fffdf, 22),
178 (0x7fffeb, 23),
179 (0x7fffec, 23),
180 (0x1fffe0, 21),
181 (0x1fffe1, 21),
182 (0x3fffe0, 22),
183 (0x1fffe2, 21),
184 (0x7fffed, 23),
185 (0x3fffe1, 22),
186 (0x7fffee, 23),
187 (0x7fffef, 23),
188 (0xfffea, 20),
189 (0x3fffe2, 22),
190 (0x3fffe3, 22),
191 (0x3fffe4, 22),
192 (0x7ffff0, 23),
193 (0x3fffe5, 22),
194 (0x3fffe6, 22),
195 (0x7ffff1, 23),
196 (0x3ffffe0, 26),
197 (0x3ffffe1, 26),
198 (0xfffeb, 20),
199 (0x7fff1, 19),
200 (0x3fffe7, 22),
201 (0x7ffff2, 23),
202 (0x3fffe8, 22),
203 (0x1ffffec, 25),
204 (0x3ffffe2, 26),
205 (0x3ffffe3, 26),
206 (0x3ffffe4, 26),
207 (0x7ffffde, 27),
208 (0x7ffffdf, 27),
209 (0x3ffffe5, 26),
210 (0xfffff1, 24),
211 (0x1ffffed, 25),
212 (0x7fff2, 19),
213 (0x1fffe3, 21),
214 (0x3ffffe6, 26),
215 (0x7ffffe0, 27),
216 (0x7ffffe1, 27),
217 (0x3ffffe7, 26),
218 (0x7ffffe2, 27),
219 (0xfffff2, 24),
220 (0x1fffe4, 21),
221 (0x1fffe5, 21),
222 (0x3ffffe8, 26),
223 (0x3ffffe9, 26),
224 (0xffffffd, 28),
225 (0x7ffffe3, 27),
226 (0x7ffffe4, 27),
227 (0x7ffffe5, 27),
228 (0xfffec, 20),
229 (0xfffff3, 24),
230 (0xfffed, 20),
231 (0x1fffe6, 21),
232 (0x3fffe9, 22),
233 (0x1fffe7, 21),
234 (0x1fffe8, 21),
235 (0x7ffff3, 23),
236 (0x3fffea, 22),
237 (0x3fffeb, 22),
238 (0x1ffffee, 25),
239 (0x1ffffef, 25),
240 (0xfffff4, 24),
241 (0xfffff5, 24),
242 (0x3ffffea, 26),
243 (0x7ffff4, 23),
244 (0x3ffffeb, 26),
245 (0x7ffffe6, 27),
246 (0x3ffffec, 26),
247 (0x3ffffed, 26),
248 (0x7ffffe7, 27),
249 (0x7ffffe8, 27),
250 (0x7ffffe9, 27),
251 (0x7ffffea, 27),
252 (0x7ffffeb, 27),
253 (0xffffffe, 28),
254 (0x7ffffec, 27),
255 (0x7ffffed, 27),
256 (0x7ffffee, 27),
257 (0x7ffffef, 27),
258 (0x7fffff0, 27),
259 (0x3ffffee, 26),
260 (0x3fffffff, 30),
261];
262
263impl HpackHuffman {
264 pub fn encoded_len(input: &[u8]) -> usize {
265 let mut bits: u64 = 0;
266 for &b in input {
267 bits += CODES[b as usize].1 as u64;
268 }
269 bits.div_ceil(8) as usize
270 }
271
272 pub fn encode(input: &[u8], out: &mut Vec<u8>) {
273 let mut buffer: u64 = 0;
274 let mut bits_in: u32 = 0;
275 for &b in input {
276 let (code, len) = CODES[b as usize];
277 let len = len as u32;
278 buffer = (buffer << len) | (code as u64);
279 bits_in += len;
280 while bits_in >= 8 {
281 bits_in -= 8;
282 out.push((buffer >> bits_in) as u8);
283 }
284 }
285 if bits_in > 0 {
286 let pad_bits = 8 - bits_in;
287 buffer = (buffer << pad_bits) | ((1u64 << pad_bits) - 1);
288 out.push(buffer as u8);
289 }
290 }
291
292 pub fn decode(input: &[u8], out: &mut Vec<u8>) -> Result<(), HpackHuffmanError> {
293 let mut buffer: u64 = 0;
294 let mut bits_in: u32 = 0;
295 let total_bits: u64 = (input.len() as u64) * 8;
296 let mut consumed_bits: u64 = 0;
297 let mut input_pos: usize = 0;
298 loop {
299 while bits_in < 30 && input_pos < input.len() {
300 buffer = (buffer << 8) | (input[input_pos] as u64);
301 input_pos += 1;
302 bits_in += 8;
303 }
304 if bits_in == 0 {
305 return Ok(());
306 }
307 let mut matched = false;
308 for (sym, &(code, len)) in CODES.iter().take(256).enumerate() {
309 let len = len as u32;
310 if len > bits_in {
311 continue;
312 }
313 let candidate = ((buffer >> (bits_in - len)) & ((1u64 << len) - 1)) as u32;
314 if candidate == code {
315 if consumed_bits + len as u64 > total_bits {
316 return Err(HpackHuffmanError);
317 }
318 out.push(sym as u8);
319 bits_in -= len;
320 consumed_bits += len as u64;
321 buffer &= (1u64 << bits_in) - 1;
322 matched = true;
323 break;
324 }
325 }
326 if matched {
327 continue;
328 }
329 if input_pos >= input.len() {
330 let remaining = bits_in;
331 if remaining == 0 {
332 return Ok(());
333 }
334 if remaining > 7 {
335 return Err(HpackHuffmanError);
336 }
337 let expected = (1u64 << remaining) - 1;
338 let tail = buffer & expected;
339 if tail == expected {
340 return Ok(());
341 }
342 return Err(HpackHuffmanError);
343 }
344 return Err(HpackHuffmanError);
345 }
346 }
347}
348
349#[derive(Copy, Clone, Debug, PartialEq, Eq)]
350pub struct HpackHuffmanError;