]> icculus.org git repositories - icculus/xz.git/blob - tests/test_block_header.c
Update the code to mostly match the new simpler file format
[icculus/xz.git] / tests / test_block_header.c
1 ///////////////////////////////////////////////////////////////////////////////
2 //
3 /// \file       test_block_header.c
4 /// \brief      Tests Block Header coders
5 //
6 //  Copyright (C) 2007 Lasse Collin
7 //
8 //  This library is free software; you can redistribute it and/or
9 //  modify it under the terms of the GNU Lesser General Public
10 //  License as published by the Free Software Foundation; either
11 //  version 2.1 of the License, or (at your option) any later version.
12 //
13 //  This library is distributed in the hope that it will be useful,
14 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
15 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16 //  Lesser General Public License for more details.
17 //
18 ///////////////////////////////////////////////////////////////////////////////
19
20 #include "tests.h"
21
22
23 static void
24 test4(void)
25 {
26         known_options = (lzma_options_block){
27                 .has_crc32 = false,
28                 .has_eopm = true,
29                 .is_metadata = false,
30                 .compressed_size = 0,
31                 .uncompressed_size = 0,
32                 .compressed_reserve = LZMA_VLI_BYTES_MAX,
33                 .uncompressed_reserve = LZMA_VLI_BYTES_MAX,
34                 .padding = 0,
35         };
36         memcpy(known_options.filters, filters_powerpc,
37                         sizeof(filters_powerpc));
38         expect(!code(21));
39
40         // Reserved bits
41         buffer[0] ^= 0x40;
42         expect(!decode_ret(1, LZMA_HEADER_ERROR));
43         buffer[0] ^= 0x40;
44
45         buffer[1] ^= 0x40;
46         expect(decode_ret(21, LZMA_HEADER_ERROR));
47         buffer[1] ^= 0x40;
48
49
50 }
51 */
52
53 static uint8_t buf[LZMA_BLOCK_HEADER_SIZE_MAX];
54 static lzma_options_block known_options;
55 static lzma_options_block decoded_options;
56
57 static lzma_options_filter filters_none[1] = {
58         {
59                 .id = LZMA_VLI_VALUE_UNKNOWN,
60         },
61 };
62
63
64 static lzma_options_filter filters_one[2] = {
65         {
66                 .id = LZMA_FILTER_LZMA,
67                 .options = (void *)(&lzma_preset_lzma[0]),
68         }, {
69                 .id = LZMA_VLI_VALUE_UNKNOWN,
70         }
71 };
72
73
74 static lzma_options_filter filters_four[5] = {
75         {
76                 .id = LZMA_FILTER_X86,
77                 .options = NULL,
78         }, {
79                 .id = LZMA_FILTER_X86,
80                 .options = NULL,
81         }, {
82                 .id = LZMA_FILTER_X86,
83                 .options = NULL,
84         }, {
85                 .id = LZMA_FILTER_LZMA,
86                 .options = (void *)(&lzma_preset_lzma[0]),
87         }, {
88                 .id = LZMA_VLI_VALUE_UNKNOWN,
89         }
90 };
91
92
93 static lzma_options_filter filters_five[6] = {
94         {
95                 .id = LZMA_FILTER_X86,
96                 .options = NULL,
97         }, {
98                 .id = LZMA_FILTER_X86,
99                 .options = NULL,
100         }, {
101                 .id = LZMA_FILTER_X86,
102                 .options = NULL,
103         }, {
104                 .id = LZMA_FILTER_X86,
105                 .options = NULL,
106         }, {
107                 .id = LZMA_FILTER_LZMA,
108                 .options = (void *)(&lzma_preset_lzma[0]),
109         }, {
110                 .id = LZMA_VLI_VALUE_UNKNOWN,
111         }
112 };
113
114
115 static void
116 code(void)
117 {
118         expect(lzma_block_header_encode(&known_options, buf) == LZMA_OK);
119
120         lzma_options_filter filters[LZMA_BLOCK_FILTERS_MAX + 1];
121         memcrap(filters, sizeof(filters));
122         memcrap(&decoded_options, sizeof(decoded_options));
123
124         decoded_options.header_size = known_options.header_size;
125         decoded_options.check = known_options.check;
126         decoded_options.filters = filters;
127         expect(lzma_block_header_decode(&decoded_options, NULL, buf)
128                         == LZMA_OK);
129
130         expect(known_options.compressed_size
131                         == decoded_options.compressed_size);
132         expect(known_options.uncompressed_size
133                         == decoded_options.uncompressed_size);
134
135         for (size_t i = 0; known_options.filters[i].id
136                         != LZMA_VLI_VALUE_UNKNOWN; ++i)
137                 expect(known_options.filters[i].id == filters[i].id);
138
139         for (size_t i = 0; i < LZMA_BLOCK_FILTERS_MAX; ++i)
140                 free(decoded_options.filters[i].options);
141 }
142
143
144 static void
145 test1(void)
146 {
147         known_options = (lzma_options_block){
148                 .check = LZMA_CHECK_NONE,
149                 .compressed_size = LZMA_VLI_VALUE_UNKNOWN,
150                 .uncompressed_size = LZMA_VLI_VALUE_UNKNOWN,
151                 .filters = NULL,
152         };
153
154         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
155
156         known_options.filters = filters_none;
157         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
158
159         known_options.filters = filters_five;
160         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
161
162         known_options.filters = filters_one;
163         expect(lzma_block_header_size(&known_options) == LZMA_OK);
164
165         known_options.check = 999; // Some invalid value, which gets ignored.
166         expect(lzma_block_header_size(&known_options) == LZMA_OK);
167
168         known_options.compressed_size = 5; // Not a multiple of four.
169         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
170
171         known_options.compressed_size = 0; // Cannot be zero.
172         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
173
174         known_options.compressed_size = LZMA_VLI_VALUE_UNKNOWN;
175         known_options.uncompressed_size = 0;
176         expect(lzma_block_header_size(&known_options) == LZMA_OK);
177
178         known_options.uncompressed_size = LZMA_VLI_VALUE_MAX + 1;
179         expect(lzma_block_header_size(&known_options) == LZMA_PROG_ERROR);
180 }
181
182
183 static void
184 test2(void)
185 {
186         known_options = (lzma_options_block){
187                 .check = LZMA_CHECK_CRC32,
188                 .compressed_size = LZMA_VLI_VALUE_UNKNOWN,
189                 .uncompressed_size = LZMA_VLI_VALUE_UNKNOWN,
190                 .filters = filters_four,
191         };
192
193         expect(lzma_block_header_size(&known_options) == LZMA_OK);
194         code();
195
196         known_options.compressed_size = 123456;
197         known_options.uncompressed_size = 234567;
198         expect(lzma_block_header_size(&known_options) == LZMA_OK);
199         code();
200
201         // We can make the sizes smaller while keeping the header size
202         // the same.
203         known_options.compressed_size = 12;
204         known_options.uncompressed_size = 23;
205         code();
206 }
207
208
209 static void
210 test3(void)
211 {
212         known_options = (lzma_options_block){
213                 .check = LZMA_CHECK_CRC32,
214                 .compressed_size = LZMA_VLI_VALUE_UNKNOWN,
215                 .uncompressed_size = LZMA_VLI_VALUE_UNKNOWN,
216                 .filters = filters_one,
217         };
218
219         expect(lzma_block_header_size(&known_options) == LZMA_OK);
220         known_options.header_size += 4;
221         expect(lzma_block_header_encode(&known_options, buf) == LZMA_OK);
222
223         lzma_options_filter filters[LZMA_BLOCK_FILTERS_MAX + 1];
224         decoded_options.header_size = known_options.header_size;
225         decoded_options.check = known_options.check;
226         decoded_options.filters = filters;
227
228         // Wrong size
229         ++buf[0];
230         expect(lzma_block_header_decode(&decoded_options, NULL, buf)
231                         == LZMA_PROG_ERROR);
232         --buf[0];
233
234         // Wrong CRC32
235         buf[known_options.header_size - 1] ^= 1;
236         expect(lzma_block_header_decode(&decoded_options, NULL, buf)
237                         == LZMA_DATA_ERROR);
238         buf[known_options.header_size - 1] ^= 1;
239
240         // Unsupported filter
241         // NOTE: This may need updating when new IDs become supported.
242         buf[2] ^= 0x1F;
243         integer_write_32(buf + known_options.header_size - 4,
244                         lzma_crc32(buf, known_options.header_size - 4, 0));
245         expect(lzma_block_header_decode(&decoded_options, NULL, buf)
246                         == LZMA_HEADER_ERROR);
247         buf[2] ^= 0x1F;
248
249         // Non-nul Padding
250         buf[known_options.header_size - 4 - 1] ^= 1;
251         integer_write_32(buf + known_options.header_size - 4,
252                         lzma_crc32(buf, known_options.header_size - 4, 0));
253         expect(lzma_block_header_decode(&decoded_options, NULL, buf)
254                         == LZMA_HEADER_ERROR);
255         buf[known_options.header_size - 4 - 1] ^= 1;
256 }
257
258
259 int
260 main(void)
261 {
262         lzma_init();
263
264         test1();
265         test2();
266         test3();
267
268         return 0;
269 }