1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.commons.compress.compressors.deflate64;
20
21 import static org.junit.jupiter.api.Assertions.assertEquals;
22 import static org.junit.jupiter.api.Assertions.assertThrows;
23 import static org.junit.jupiter.api.Assertions.fail;
24
25 import java.io.ByteArrayInputStream;
26 import java.util.Arrays;
27
28 import org.junit.jupiter.api.Test;
29
30 class HuffmanDecoderTest {
31
32 @Test
33 void testDecodeFixedHuffmanBlockWithMemoryLookup() throws Exception {
34 final byte[] data = {
35
36 0b11111111111111111111111111110011,
37 0b00000000000000000000000001001000,
38 0b11111111111111111111111111001101,
39 0b11111111111111111111111111001001,
40 0b11111111111111111111111111001001,
41 0b00000000000000000000000001010111,
42 0b00000000000000000000000000001000,
43 0b11111111111111111111111111001111,
44 0b00000000000000000000000000101111,
45 0b11111111111111111111111111001010,
46 0b00000000000000000000000001001001,
47 0b11111111111111111111111111100001,
48 0b00000000000000000000000000100010,
49 0b11111111111111111111111110000110,
50 0b00000000000000000000000000001101,
51 0b11111111111111111111111111111000
52 };
53 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
54 final byte[] result = new byte[100];
55 final int len = decoder.decode(result);
56 assertEquals(48, len);
57 assertEquals("Hello World\nHello World\nHello World\nHello World\n", new String(result, 0, len));
58 }
59 }
60
61 @Test
62 void testDecodeFixedHuffmanBlockWithMemoryLookupInExactBuffer() throws Exception {
63 final byte[] data = {
64
65 0b11111111111111111111111111110011,
66 0b00000000000000000000000001001000,
67 0b11111111111111111111111111001101,
68 0b11111111111111111111111111001001,
69 0b11111111111111111111111111001001,
70 0b00000000000000000000000001010111,
71 0b00000000000000000000000000001000,
72 0b11111111111111111111111111001111,
73 0b00000000000000000000000000101111,
74 0b11111111111111111111111111001010,
75 0b00000000000000000000000001001001,
76 0b11111111111111111111111111100001,
77 0b00000000000000000000000000100010,
78 0b11111111111111111111111110000110,
79 0b00000000000000000000000000001101,
80 0b11111111111111111111111111111000
81 };
82 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
83 final byte[] result = new byte[48];
84 int len;
85 len = decoder.decode(result);
86 assertEquals(48, len);
87 assertEquals("Hello World\nHello World\nHello World\nHello World\n", new String(result, 0, len));
88 len = decoder.decode(result);
89 assertEquals(-1, len);
90 }
91 }
92
93 @Test
94 void testDecodeFixedHuffmanBlockWithMemoryLookupInSmallBuffer() throws Exception {
95 final byte[] data = {
96
97 0b11111111111111111111111111110011,
98 0b00000000000000000000000001001000,
99 0b11111111111111111111111111001101,
100 0b11111111111111111111111111001001,
101 0b11111111111111111111111111001001,
102 0b00000000000000000000000001010111,
103 0b00000000000000000000000000001000,
104 0b11111111111111111111111111001111,
105 0b00000000000000000000000000101111,
106 0b11111111111111111111111111001010,
107 0b00000000000000000000000001001001,
108 0b11111111111111111111111111100001,
109 0b00000000000000000000000000100010,
110 0b11111111111111111111111110000110,
111 0b00000000000000000000000000001101,
112 0b11111111111111111111111111111000
113 };
114
115 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
116 final byte[] result = new byte[30];
117 int len;
118 len = decoder.decode(result);
119 assertEquals(30, len);
120 assertEquals("Hello World\nHello World\nHello ", new String(result, 0, len));
121 len = decoder.decode(result);
122 assertEquals(18, len);
123 assertEquals("World\nHello World\n", new String(result, 0, len));
124 }
125 }
126
127 @Test
128 void testDecodeSimpleFixedHuffmanBlock() throws Exception {
129 final byte[] data = {
130
131 0b11111111111111111111111111110011,
132 0b00000000000000000000000001001000,
133 0b11111111111111111111111111001101,
134 0b11111111111111111111111111001001,
135 0b11111111111111111111111111001001,
136 0b00000000000000000000000001010111,
137 0b00000000000000000000000000001000,
138 0b11111111111111111111111111001111,
139 0b00000000000000000000000000101111,
140 0b11111111111111111111111111001010,
141 0b00000000000000000000000001001001,
142 0b00000000000000000000000000000001,
143 0b11111111111111111111111111111100
144 };
145 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
146 final byte[] result = new byte[100];
147 final int len = decoder.decode(result);
148 assertEquals(11, len);
149 assertEquals("Hello World", new String(result, 0, len));
150 }
151 }
152
153 @Test
154 void testDecodeSimpleFixedHuffmanBlockToSmallBuffer() throws Exception {
155 final byte[] data = {
156
157 0b11111111111111111111111111110011,
158 0b00000000000000000000000001001000,
159 0b11111111111111111111111111001101,
160 0b11111111111111111111111111001001,
161 0b11111111111111111111111111001001,
162 0b00000000000000000000000001010111,
163 0b00000000000000000000000000001000,
164 0b11111111111111111111111111001111,
165 0b00000000000000000000000000101111,
166 0b11111111111111111111111111001010,
167 0b00000000000000000000000001001001,
168 0b00000000000000000000000000000001,
169 0b11111111111111111111111111111100
170 };
171 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
172 final byte[] result = new byte[10];
173 int len;
174 len = decoder.decode(result);
175 assertEquals(10, len);
176 assertEquals("Hello Worl", new String(result, 0, len));
177 len = decoder.decode(result);
178 assertEquals(1, len);
179 assertEquals("d", new String(result, 0, len));
180 }
181 }
182
183 @Test
184 void testDecodeUncompressedBlock() throws Exception {
185 final byte[] data = { 0b1,
186 11, 0, -12, -1,
187 'H', 'e', 'l', 'l', 'o', ' ', 'W', 'o', 'r', 'l', 'd' };
188 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
189 final byte[] result = new byte[100];
190 final int len = decoder.decode(result);
191 assertEquals(11, len);
192 assertEquals("Hello World", new String(result, 0, len));
193 }
194 }
195
196 @Test
197 void testDecodeUncompressedBlockWithInvalidLenNLenValue() throws Exception {
198 final byte[] data = { 0b1,
199 11, 0, -12, -2,
200 'H', 'e', 'l', 'l', 'o', ' ', 'W', 'o', 'r', 'l', 'd' };
201 try (HuffmanDecoder decoder = new HuffmanDecoder(new ByteArrayInputStream(data))) {
202 final byte[] result = new byte[100];
203 final IllegalStateException e = assertThrows(IllegalStateException.class, () -> {
204 final int len = decoder.decode(result);
205 fail("Should have failed but returned " + len + " entries: " + Arrays.toString(Arrays.copyOf(result, len)));
206 });
207 assertEquals("Illegal LEN / NLEN values", e.getMessage());
208 }
209 }
210 }