httlib_huffman/decoder/mod.rs
1//! Provides an implementation of the [canonical Huffman] decoder.
2//!
3//! When an entity receives a header, for which it determines that it contains
4//! content encoded with the [canonical Huffman] algorithm, it has to decode
5//! this content in the shortest possible time with as few resources as
6//! possible. The execution speed of this “simple“ task will contribute
7//! significantly to the response time, and this time must be as short as
8//! possible.
9//!
10//! Reading and decoding a sequence bit by bit appears to be inadequate
11//! performance-wise. Reading in buffered chunks outperforms reading bit by bit.
12//! The trick of fast Huffman decoding is reading N-bits at a time. Since we
13//! cannot determine how the seemingly “random” Huffman sequence corresponds to
14//! actual data, we use flattened Huffman tree matrix that enables decoding of
15//! N-bits at a time. This matrix is created by the `flatten` module.
16//!
17//! Let's learn the decoded mechanics based on a simple matrix that allowsfor
18//! reading 2 bits at a time.
19//!
20//! | Path | ID | SYM | LFT | 00 | 01 | 10 | 11
21//! |-|-|-|-|-|-|-|-
22//! | // | 0 | - | - | 1 | 2 | 3 | 6
23//! | //00 | 1 | A | 0 | - | - | - | -
24//! | //01 | 2 | B | 0 | - | - | - | -
25//! | //10 | 2 | B | 0 | - | - | - | -
26//! | //10 | 3 | - | - | 4 | 4 | 5 | 5
27//! | //100X | 4 | C | 1 | - | - | - | -
28//! | //101X | 5 | D | 1 | - | - | - | -
29//! | //11 | 6 | E | 0 | - | - | - | -
30//!
31//! We'll be using a sequence of characters: A, D, and B.
32//!
33//! ```txt
34//! ADE = 0010101
35//! ```
36//!
37//! The Huffman sequence will be decoded by reading 2 bits at a time. Every
38//! reading begins at the root symbol `//`. First, we read the first two bits
39//! `00`. In line one of the matrix at `ID=0`, we need to check where this code
40//! leads, or if it corresponds to any of the characters. Read bits lead to the
41//! second line with `ID=1` and they represent the letter A.
42//!
43//! The process is repeated for the next 2 bits `10`. This code leads us to the
44//! line with `ID=3` which doesn’t represent a character, so we continue the
45//! process for the next 2 bits `10`. This code then leads us to line 5,
46//! representing the letter D. Here we can see that the value of the column
47//! `LFT=1`, meaning that there is a leftover 1. This means that in order to
48//! continue reading bits we have to shift to one bit back and continue the
49//! process there.
50//!
51//! We position ourselves back to the root position while keeping the last bit
52//! `0`, and keep reading until we reach the sum of 2 bits. This means that we
53//! need to read only 1 bit `1`. Code `01` corresponds with character B and with
54//! this we conclude the decoding process.
55//!
56//! ```txt
57//! 00XXXXX => A
58//! XX10XXX => continue
59//! XXXX10X => D
60//! XXXXX01 => B
61//! ```
62//!
63//! With the use of the translation matrix we successfully decoded the Huffman
64//! sequence back into readable characters. This is how the decoder decodes
65//! literal values. The process is optimal, while it is best for web servers to
66//! read more bits at a time. Considering that the shortest Huffman code for an
67//! individual character is 5 bits long, it’s optimal, for the best ratio
68//! between speed and used resources, to read 4 bits at a time. More bits at a
69//! time mean faster decoding but at the same time a larger translation table
70//! and with it a higher memory footprint.
71//!
72//! [canonical Huffman]: https://en.wikipedia.org/wiki/Canonical_Huffman_code
73
74mod error;
75mod reader;
76mod speed;
77pub mod table1;
78pub mod table2;
79pub mod table3;
80pub mod table4;
81pub mod table5;
82
83pub use error::*;
84pub use speed::*;
85use reader::*;
86
87/// Decodes Huffman's `src` sequence into `dst` vector of bytes. The `speed`
88/// parameter is used to tell the encoder how many bits should be read and
89/// decoded at a time.
90///
91/// **Example:**
92///
93/// ```rust
94/// use httlib_huffman::{DecoderSpeed, decode};
95///
96/// let speed = DecoderSpeed::ThreeBits;
97/// let mut dst = Vec::new();
98/// let src = vec![135];
99/// decode(&src, &mut dst, speed).unwrap();
100/// ```
101pub fn decode(
102 src: &[u8],
103 dst: &mut Vec<u8>,
104 speed: DecoderSpeed,
105) -> Result<(), DecoderError> {
106 let mut reader = DecodeReader::new(speed as usize);
107
108 for byte in src {
109 reader.decode(*byte, dst)?;
110 }
111 reader.finalize(dst)?;
112
113 Ok(())
114}
115
116#[cfg(test)]
117mod test {
118 use super::*;
119
120 fn decode(bytes: &[u8], speed: DecoderSpeed) -> Result<Vec<u8>, DecoderError> {
121 let mut dst = Vec::new();
122 super::decode(&bytes, &mut dst, speed)?;
123 Ok(dst)
124 }
125
126 fn valid_characters() -> Vec<(&'static [u8], Vec<u8>)> {
127 vec![
128 (&[0], vec![255, 199]), // 0
129 (&[1], vec![255, 255, 177]), // 1
130 (&[2], vec![255, 255, 254, 47]), // 2
131 (&[3], vec![255, 255, 254, 63]), // 3
132 (&[4], vec![255, 255, 254, 79]), // 4
133 (&[5], vec![255, 255, 254, 95]), // 5
134 (&[6], vec![255, 255, 254, 111]), // 6
135 (&[7], vec![255, 255, 254, 127]), // 7
136 (&[8], vec![255, 255, 254, 143]), // 8
137 (&[9], vec![255, 255, 234]), // 9
138 (&[10], vec![255, 255, 255, 243]), // 10
139 (&[11], vec![255, 255, 254, 159]), // 11
140 (&[12], vec![255, 255, 254, 175]), // 12
141 (&[13], vec![255, 255, 255, 247]), // 13
142 (&[14], vec![255, 255, 254, 191]), // 14
143 (&[15], vec![255, 255, 254, 207]), // 15
144 (&[16], vec![255, 255, 254, 223]), // 16
145 (&[17], vec![255, 255, 254, 239]), // 17
146 (&[18], vec![255, 255, 254, 255]), // 18
147 (&[19], vec![255, 255, 255, 15]), // 19
148 (&[20], vec![255, 255, 255, 31]), // 20
149 (&[21], vec![255, 255, 255, 47]), // 21
150 (&[22], vec![255, 255, 255, 251]), // 22
151 (&[23], vec![255, 255, 255, 63]), // 23
152 (&[24], vec![255, 255, 255, 79]), // 24
153 (&[25], vec![255, 255, 255, 95]), // 25
154 (&[26], vec![255, 255, 255, 111]), // 26
155 (&[27], vec![255, 255, 255, 127]), // 27
156 (&[28], vec![255, 255, 255, 143]), // 28
157 (&[29], vec![255, 255, 255, 159]), // 29
158 (&[30], vec![255, 255, 255, 175]), // 30
159 (&[31], vec![255, 255, 255, 191]), // 31
160 (b" ", vec![83]), // 32
161 (b"!", vec![254, 63]), // 33
162 (b"\"", vec![254, 127]), // 34
163 (b"#", vec![255, 175]), // 35
164 (b"$", vec![255, 207]), // 36
165 (b"%", vec![87]), // 37
166 (b"&", vec![248]), // 38
167 (b"'", vec![255, 95]), // 39
168 (b"(", vec![254, 191]), // 40
169 (b")", vec![254, 255]), // 41
170 (b"*", vec![249]), // 42
171 (b"+", vec![255, 127]), // 43
172 (b",", vec![250]), // 44
173 (b"-", vec![91]), // 45
174 (b".", vec![95]), // 46
175 (b"/", vec![99]), // 47
176 (b"0", vec![7]), // 48
177 (b"1", vec![15]), // 49
178 (b"2", vec![23]), // 50
179 (b"3", vec![103]), // 51
180 (b"4", vec![107]), // 52
181 (b"5", vec![111]), // 53
182 (b"6", vec![115]), // 54
183 (b"7", vec![119]), // 55
184 (b"8", vec![123]), // 56
185 (b"9", vec![127]), // 57
186 (b":", vec![185]), // 58
187 (b";", vec![251]), // 59
188 (b"<", vec![255, 249]), // 60
189 (b"=", vec![131]), // 61
190 (b">", vec![255, 191]), // 62
191 (b"?", vec![255, 63]), // 63
192 (b"@", vec![255, 215]), // 64
193 (b"A", vec![135]), // 65
194 (b"B", vec![187]), // 66
195 (b"C", vec![189]), // 67
196 (b"D", vec![191]), // 68
197 (b"E", vec![193]), // 69
198 (b"F", vec![195]), // 70
199 (b"G", vec![197]), // 71
200 (b"H", vec![199]), // 72
201 (b"I", vec![201]), // 73
202 (b"J", vec![203]), // 74
203 (b"K", vec![205]), // 75
204 (b"L", vec![207]), // 76
205 (b"M", vec![209]), // 77
206 (b"N", vec![211]), // 78
207 (b"O", vec![213]), // 79
208 (b"P", vec![215]), // 80
209 (b"Q", vec![217]), // 81
210 (b"R", vec![219]), // 82
211 (b"S", vec![221]), // 83
212 (b"T", vec![223]), // 84
213 (b"U", vec![225]), // 85
214 (b"V", vec![227]), // 86
215 (b"W", vec![229]), // 87
216 (b"X", vec![252]), // 88
217 (b"Y", vec![231]), // 89
218 (b"Z", vec![253]), // 90
219 (b"[", vec![255, 223]), // 91
220 (b"\\", vec![255, 254, 31]), // 92
221 (b"]", vec![255, 231]), // 93
222 (b"^", vec![255, 243]), // 94
223 (b"_", vec![139]), // 95
224 (b"`", vec![255, 251]), // 96
225 (b"a", vec![31]), // 97
226 (b"b", vec![143]), // 98
227 (b"c", vec![39]), // 99
228 (b"d", vec![147]), // 100
229 (b"e", vec![47]), // 101
230 (b"f", vec![151]), // 102
231 (b"g", vec![155]), // 103
232 (b"h", vec![159]), // 104
233 (b"i", vec![55]), // 105
234 (b"j", vec![233]), // 106
235 (b"k", vec![235]), // 107
236 (b"l", vec![163]), // 108
237 (b"m", vec![167]), // 109
238 (b"n", vec![171]), // 110
239 (b"o", vec![63]), // 111
240 (b"p", vec![175]), // 112
241 (b"q", vec![237]), // 113
242 (b"r", vec![179]), // 114
243 (b"s", vec![71]), // 115
244 (b"t", vec![79]), // 116
245 (b"u", vec![183]), // 117
246 (b"v", vec![239]), // 118
247 (b"w", vec![241]), // 119
248 (b"x", vec![243]), // 120
249 (b"y", vec![245]), // 121
250 (b"z", vec![247]), // 122
251 (b"{", vec![255, 253]), // 123
252 (b"|", vec![255, 159]), // 124
253 (b"}", vec![255, 247]), // 125
254 (b"~", vec![255, 239]), // 126
255 (&[127], vec![255, 255, 255, 207]), // 127
256 (&[128], vec![255, 254, 111]), // 128
257 (&[129], vec![255, 255, 75]), // 129
258 (&[130], vec![255, 254, 127]), // 130
259 (&[131], vec![255, 254, 143]), // 131
260 (&[132], vec![255, 255, 79]), // 132
261 (&[133], vec![255, 255, 83]), // 133
262 (&[134], vec![255, 255, 87]), // 134
263 (&[135], vec![255, 255, 179]), // 135
264 (&[136], vec![255, 255, 91]), // 136
265 (&[137], vec![255, 255, 181]), // 137
266 (&[138], vec![255, 255, 183]), // 138
267 (&[139], vec![255, 255, 185]), // 139
268 (&[140], vec![255, 255, 187]), // 140
269 (&[141], vec![255, 255, 189]), // 141
270 (&[142], vec![255, 255, 235]), // 142
271 (&[143], vec![255, 255, 191]), // 143
272 (&[144], vec![255, 255, 236]), // 144
273 (&[145], vec![255, 255, 237]), // 145
274 (&[146], vec![255, 255, 95]), // 146
275 (&[147], vec![255, 255, 193]), // 147
276 (&[148], vec![255, 255, 238]), // 148
277 (&[149], vec![255, 255, 195]), // 149
278 (&[150], vec![255, 255, 197]), // 150
279 (&[151], vec![255, 255, 199]), // 151
280 (&[152], vec![255, 255, 201]), // 152
281 (&[153], vec![255, 254, 231]), // 153
282 (&[154], vec![255, 255, 99]), // 154
283 (&[155], vec![255, 255, 203]), // 155
284 (&[156], vec![255, 255, 103]), // 156
285 (&[157], vec![255, 255, 205]), // 157
286 (&[158], vec![255, 255, 207]), // 158
287 (&[159], vec![255, 255, 239]), // 159
288 (&[160], vec![255, 255, 107]), // 160
289 (&[161], vec![255, 254, 239]), // 161
290 (&[162], vec![255, 254, 159]), // 162
291 (&[163], vec![255, 255, 111]), // 163
292 (&[164], vec![255, 255, 115]), // 164
293 (&[165], vec![255, 255, 209]), // 165
294 (&[166], vec![255, 255, 211]), // 166
295 (&[167], vec![255, 254, 247]), // 167
296 (&[168], vec![255, 255, 213]), // 168
297 (&[169], vec![255, 255, 119]), // 169
298 (&[170], vec![255, 255, 123]), // 170
299 (&[171], vec![255, 255, 240]), // 171
300 (&[172], vec![255, 254, 255]), // 172
301 (&[173], vec![255, 255, 127]), // 173
302 (&[174], vec![255, 255, 215]), // 174
303 (&[175], vec![255, 255, 217]), // 175
304 (&[176], vec![255, 255, 7]), // 176
305 (&[177], vec![255, 255, 15]), // 177
306 (&[178], vec![255, 255, 131]), // 178
307 (&[179], vec![255, 255, 23]), // 179
308 (&[180], vec![255, 255, 219]), // 180
309 (&[181], vec![255, 255, 135]), // 181
310 (&[182], vec![255, 255, 221]), // 182
311 (&[183], vec![255, 255, 223]), // 183
312 (&[184], vec![255, 254, 175]), // 184
313 (&[185], vec![255, 255, 139]), // 185
314 (&[186], vec![255, 255, 143]), // 186
315 (&[187], vec![255, 255, 147]), // 187
316 (&[188], vec![255, 255, 225]), // 188
317 (&[189], vec![255, 255, 151]), // 189
318 (&[190], vec![255, 255, 155]), // 190
319 (&[191], vec![255, 255, 227]), // 191
320 (&[192], vec![255, 255, 248, 63]), // 192
321 (&[193], vec![255, 255, 248, 127]), // 193
322 (&[194], vec![255, 254, 191]), // 194
323 (&[195], vec![255, 254, 63]), // 195
324 (&[196], vec![255, 255, 159]), // 196
325 (&[197], vec![255, 255, 229]), // 197
326 (&[198], vec![255, 255, 163]), // 198
327 (&[199], vec![255, 255, 246, 127]), // 199
328 (&[200], vec![255, 255, 248, 191]), // 200
329 (&[201], vec![255, 255, 248, 255]), // 201
330 (&[202], vec![255, 255, 249, 63]), // 202
331 (&[203], vec![255, 255, 251, 223]), // 203
332 (&[204], vec![255, 255, 251, 255]), // 204
333 (&[205], vec![255, 255, 249, 127]), // 205
334 (&[206], vec![255, 255, 241]), // 206
335 (&[207], vec![255, 255, 246, 255]), // 207
336 (&[208], vec![255, 254, 95]), // 208
337 (&[209], vec![255, 255, 31]), // 209
338 (&[210], vec![255, 255, 249, 191]), // 210
339 (&[211], vec![255, 255, 252, 31]), // 211
340 (&[212], vec![255, 255, 252, 63]), // 212
341 (&[213], vec![255, 255, 249, 255]), // 213
342 (&[214], vec![255, 255, 252, 95]), // 214
343 (&[215], vec![255, 255, 242]), // 215
344 (&[216], vec![255, 255, 39]), // 216
345 (&[217], vec![255, 255, 47]), // 217
346 (&[218], vec![255, 255, 250, 63]), // 218
347 (&[219], vec![255, 255, 250, 127]), // 219
348 (&[220], vec![255, 255, 255, 223]), // 220
349 (&[221], vec![255, 255, 252, 127]), // 221
350 (&[222], vec![255, 255, 252, 159]), // 222
351 (&[223], vec![255, 255, 252, 191]), // 223
352 (&[224], vec![255, 254, 207]), // 224
353 (&[225], vec![255, 255, 243]), // 225
354 (&[226], vec![255, 254, 223]), // 226
355 (&[227], vec![255, 255, 55]), // 227
356 (&[228], vec![255, 255, 167]), // 228
357 (&[229], vec![255, 255, 63]), // 229
358 (&[230], vec![255, 255, 71]), // 230
359 (&[231], vec![255, 255, 231]), // 231
360 (&[232], vec![255, 255, 171]), // 232
361 (&[233], vec![255, 255, 175]), // 233
362 (&[234], vec![255, 255, 247, 127]), // 234
363 (&[235], vec![255, 255, 247, 255]), // 235
364 (&[236], vec![255, 255, 244]), // 236
365 (&[237], vec![255, 255, 245]), // 237
366 (&[238], vec![255, 255, 250, 191]), // 238
367 (&[239], vec![255, 255, 233]), // 239
368 (&[240], vec![255, 255, 250, 255]), // 240
369 (&[241], vec![255, 255, 252, 223]), // 241
370 (&[242], vec![255, 255, 251, 63]), // 242
371 (&[243], vec![255, 255, 251, 127]), // 243
372 (&[244], vec![255, 255, 252, 255]), // 244
373 (&[245], vec![255, 255, 253, 31]), // 245
374 (&[246], vec![255, 255, 253, 63]), // 246
375 (&[247], vec![255, 255, 253, 95]), // 247
376 (&[248], vec![255, 255, 253, 127]), // 248
377 (&[249], vec![255, 255, 255, 239]), // 249
378 (&[250], vec![255, 255, 253, 159]), // 250
379 (&[251], vec![255, 255, 253, 191]), // 251
380 (&[252], vec![255, 255, 253, 223]), // 252
381 (&[253], vec![255, 255, 253, 255]), // 253
382 (&[254], vec![255, 255, 254, 31]), // 254
383 (&[255], vec![255, 255, 251, 191]), // 255
384 ] // EOS(256) is not a valid character
385 }
386
387 fn valid_literals() -> Vec<(Vec<u8>, Vec<u8>)> {
388 // NOTES:
389 // * Padding should be discarded.
390 vec![(
391 vec![3, 4, 1, 2],
392 vec![255, 255, 254, 63, 255, 255, 228, 255, 255, 177, 255, 255, 252, 95],
393 ), (
394 b":method".to_vec(),
395 vec![185, 73, 83, 57, 228],
396 ), (
397 b":scheme".to_vec(),
398 vec![184, 130, 78, 90, 75],
399 ), (
400 b":authority".to_vec(),
401 vec![184, 59, 83, 57, 236, 50, 125, 127],
402 ), (
403 b"nibbstack.com".to_vec(),
404 vec![168, 209, 198, 132, 140, 157, 87, 33, 233],
405 ), (
406 b"GET".to_vec(),
407 vec![197, 131, 127],
408 ), (
409 b"http".to_vec(),
410 vec![157, 41, 175],
411 ), (
412 b":path".to_vec(),
413 vec![185, 88, 211, 63],
414 ), (
415 b"/images/top/sp2/cmn/logo-ns-130528.png".to_vec(),
416 vec![96, 212, 142, 98, 161, 132, 158, 182, 17, 88, 152, 37, 53, 49,65, 230, 58, 213, 33, 96, 178, 6, 196, 242, 245, 213, 55],
417 ), (
418 b"hpack-test".to_vec(),
419 vec![158, 177, 147, 170, 201, 42, 19],
420 ), (
421 b"xxxxxxx1".to_vec(),
422 vec![243, 231, 207, 159, 62, 124, 135],
423 ), (
424 b"Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:16.0) Gecko/20100101 Firefox/16.0".to_vec(),
425 vec![208, 127, 102, 162, 129, 176, 218, 224, 83, 250, 208, 50, 26, 164, 157, 19, 253, 169, 146, 164, 150, 133, 52, 12, 138, 106, 220, 167, 226, 129, 2, 239, 125, 169, 103, 123, 129, 113, 112, 127, 106, 98, 41, 58, 157, 129, 0, 32, 0, 64, 21, 48, 154, 194, 202, 127, 44, 5, 197, 193],
426 ), (
427 b"accept".to_vec(),
428 vec![25, 8, 90, 211],
429 ), (
430 b"Accept".to_vec(),
431 vec![132, 132, 45, 105],
432 ), (
433 b"text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8".to_vec(),
434 vec![73, 124, 165, 137, 211, 77, 31, 67, 174, 186, 12, 65, 164, 199, 169, 143, 51, 166, 154, 63, 223, 154, 104, 250, 29, 117, 208, 98, 13, 38, 61, 76, 121, 166, 143, 190, 208, 1, 119, 254, 190, 88, 249, 251, 237, 0, 23, 123],
435 ), (
436 b"cookie".to_vec(),
437 vec![33, 207, 212, 197],
438 ), (
439 b"B=11231252zdf&b=3&s=0b".to_vec(),
440 vec![187, 0, 66, 38, 66, 38, 197, 238, 73, 126, 35, 129, 159, 132, 64, 8, 255],
441 ), (
442 b"TE".to_vec(),
443 vec![223, 131],
444 ), (
445 b"Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi non bibendum libero. Etiam ultrices lorem ut.".to_vec(),
446 vec![206, 123, 11, 74, 134, 173, 22, 210, 164, 135, 160, 246, 40, 131, 37, 65, 210, 84, 253, 40, 67, 212, 130, 145, 37, 77, 182, 40, 57, 13, 89, 144, 67, 85, 50, 133, 160, 201, 93, 77, 7, 178, 51, 41, 81, 234, 82, 51, 70, 90, 164, 182, 149, 40, 52, 101, 176, 235, 169, 129, 38, 29, 42, 91, 66, 108, 49, 10, 133, 40, 61, 133, 165, 75, 82, 191],
447 ), (
448 b"!$%&A".to_vec(),
449 vec![0b11111110, 0b00111111, 0b11110010, 0b10101111, 0b11000100, 0b00111111],
450 ), (
451 b"\0\0\0".to_vec(),
452 vec![255, 199, 254, 63, 241],
453 ), (
454 b"\0\x01\x02\x03\x04\x05".to_vec(),
455 vec![255, 199, 255, 253, 143, 255, 255, 226, 255, 255, 254, 63, 255, 255, 228, 255, 255, 254, 95],
456 ), (
457 b"\xFF\xF8".to_vec(),
458 vec![255, 255, 251, 191, 255, 255, 95],
459 )]
460 }
461
462 fn invalid_encodings() -> Vec<Vec<u8>> {
463 vec![
464 vec![0, 23, 122],
465 vec![73, 124, 165, 137, 211, 77, 31, 67, 174, 186, 12, 65, 164, 199, 169, 143, 51, 166, 154, 63, 223, 154, 104, 250, 29, 117, 208, 98, 13, 38, 61, 76, 121, 166, 143, 190, 208, 1, 119, 254, 190, 88, 249, 251, 237, 0, 23, 122],
466 vec![0b11111111, 0b11111111], // EOS (padding > 7 bits)
467 vec![0b00011111, 0b11111111, 0b11111111, 0b11111111, 0b11100000], // a, EOS, +5
468 vec![0b11111111, 0b10011111, 0b11111111, 0b11111111, 0b11111111, 0b10000000], // |, EOS, +7
469 vec![0b11111111, 0b00111111, 0b11111111, 0b11111111, 0b11111111], // ?, EOS
470 vec![0b11111111, 0b11111111, 0b11111111, 0b11111100], // EOS, +2
471 vec![0b11111111, 0b00111111, 0b11111111, 0b11111111, 0b11111111, 0b0], // ?, EOS, +8
472 vec![0b11111111, 0b11111111, 0b11111111, 0b11111100, 0b0], // EOS, +10
473 ]
474 }
475
476 /// Should be able to decode ASCII characters encoded into Huffman formatted
477 /// sequence. The decoder should be able to decode the sequence by using any
478 /// valid decoding speed.
479 #[test]
480 fn decodes_characters() {
481 for speed in DecoderSpeed::known() {
482 for (data, code) in valid_characters() { // passes
483 assert_eq!(data, decode(&code, speed).unwrap());
484 }
485 }
486 // 256 or higher is an overflowing literal and the decoder will throw an
487 // error because it doesn't fit into the type u8.
488 }
489
490 /// Should be able to decode ASCII string literals encoded into Huffman
491 /// formatted sequence. The decoder should be able to decode the sequence by
492 /// using any valid decoding speed.
493 #[test]
494 fn decodes_literals() {
495 for speed in DecoderSpeed::known() {
496 for (data, code) in valid_literals() { // passes
497 assert_eq!(data, decode(&code, speed).unwrap());
498 }
499 for encoding in invalid_encodings() { // throws
500 assert_eq!(Err(DecoderError::InvalidInput), decode(&encoding, speed));
501 }
502 }
503 }
504}