]> CyberLeo.Net >> Repos - FreeBSD/stable/10.git/blob - contrib/libarchive/libarchive/test/test_archive_read_multiple_data_objects.c
MFC r368207,368607:
[FreeBSD/stable/10.git] / contrib / libarchive / libarchive / test / test_archive_read_multiple_data_objects.c
1 /*-
2  * Copyright (c) 2011 Tim Kientzle
3  * Copyright (c) 2011-2012 Andres Mejia
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
16  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
17  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
18  * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
19  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
20  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
21  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
22  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
24  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25  */
26
27 #include "test.h"
28 __FBSDID("$FreeBSD$");
29
30 #if defined(_WIN32) && !defined(__CYGWIN__)
31 #define open _open
32 #define close _close
33 #define read _read
34 #if !defined(__BORLANDC__)
35 #ifdef lseek
36 #undef lseek
37 #endif
38 #define lseek(f, o, w) _lseek(f, (long)(o), (int)(w))
39 #endif
40 #endif
41
42 static void
43 test_splitted_file(void)
44 {
45   char buff[64];
46   static const char *reffiles[] =
47   {
48     "test_read_splitted_rar_aa",
49     "test_read_splitted_rar_ab",
50     "test_read_splitted_rar_ac",
51     "test_read_splitted_rar_ad",
52     NULL
53   };
54   const char test_txt[] = "test text document\r\n";
55   int size = sizeof(test_txt)-1;
56   struct archive_entry *ae;
57   struct archive *a;
58
59   extract_reference_files(reffiles);
60   assert((a = archive_read_new()) != NULL);
61   assertA(0 == archive_read_support_filter_all(a));
62   assertA(0 == archive_read_support_format_all(a));
63   assertA(0 == archive_read_open_filenames(a, reffiles, 10240));
64
65   /* First header. */
66   assertA(0 == archive_read_next_header(a, &ae));
67   assertEqualString("test.txt", archive_entry_pathname(ae));
68   assertA((int)archive_entry_mtime(ae));
69   assertA((int)archive_entry_ctime(ae));
70   assertA((int)archive_entry_atime(ae));
71   assertEqualInt(20, archive_entry_size(ae));
72   assertEqualInt(33188, archive_entry_mode(ae));
73   assertA(size == archive_read_data(a, buff, size));
74   assertEqualMem(buff, test_txt, size);
75
76   /* Second header. */
77   assertA(0 == archive_read_next_header(a, &ae));
78   assertEqualString("testlink", archive_entry_pathname(ae));
79   assertA((int)archive_entry_mtime(ae));
80   assertA((int)archive_entry_ctime(ae));
81   assertA((int)archive_entry_atime(ae));
82   assertEqualInt(0, archive_entry_size(ae));
83   assertEqualInt(41471, archive_entry_mode(ae));
84   assertEqualString("test.txt", archive_entry_symlink(ae));
85   assertEqualIntA(a, 0, archive_read_data(a, buff, sizeof(buff)));
86
87   /* Third header. */
88   assertA(0 == archive_read_next_header(a, &ae));
89   assertEqualString("testdir/test.txt", archive_entry_pathname(ae));
90   assertA((int)archive_entry_mtime(ae));
91   assertA((int)archive_entry_ctime(ae));
92   assertA((int)archive_entry_atime(ae));
93   assertEqualInt(20, archive_entry_size(ae));
94   assertEqualInt(33188, archive_entry_mode(ae));
95   assertA(size == archive_read_data(a, buff, size));
96   assertEqualMem(buff, test_txt, size);
97
98   /* Fourth header. */
99   assertA(0 == archive_read_next_header(a, &ae));
100   assertEqualString("testdir", archive_entry_pathname(ae));
101   assertA((int)archive_entry_mtime(ae));
102   assertA((int)archive_entry_ctime(ae));
103   assertA((int)archive_entry_atime(ae));
104   assertEqualInt(0, archive_entry_size(ae));
105   assertEqualInt(16877, archive_entry_mode(ae));
106
107   /* Fifth header. */
108   assertA(0 == archive_read_next_header(a, &ae));
109   assertEqualString("testemptydir", archive_entry_pathname(ae));
110   assertA((int)archive_entry_mtime(ae));
111   assertA((int)archive_entry_ctime(ae));
112   assertA((int)archive_entry_atime(ae));
113   assertEqualInt(0, archive_entry_size(ae));
114   assertEqualInt(16877, archive_entry_mode(ae));
115
116   /* Test EOF */
117   assertA(1 == archive_read_next_header(a, &ae));
118   assertEqualInt(5, archive_file_count(a));
119   assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
120   assertEqualInt(ARCHIVE_OK, archive_read_free(a));
121 }
122
123 static void
124 test_large_splitted_file(void)
125 {
126   static const char *reffiles[] =
127   {
128     "test_read_large_splitted_rar_aa",
129     "test_read_large_splitted_rar_ab",
130     "test_read_large_splitted_rar_ac",
131     "test_read_large_splitted_rar_ad",
132     "test_read_large_splitted_rar_ae",
133     NULL
134   };
135   const char test_txt[] = "gin-bottom: 0in\"><BR>\n</P>\n</BODY>\n</HTML>";
136   int size = 241647978, offset = 0;
137   char buff[64];
138   struct archive_entry *ae;
139   struct archive *a;
140
141   extract_reference_files(reffiles);
142   assert((a = archive_read_new()) != NULL);
143   assertA(0 == archive_read_support_filter_all(a));
144   assertA(0 == archive_read_support_format_all(a));
145   assertA(0 == archive_read_open_filenames(a, reffiles, 10240));
146
147   /* First header. */
148   assertA(0 == archive_read_next_header(a, &ae));
149   assertEqualString("ppmd_lzss_conversion_test.txt",
150                     archive_entry_pathname(ae));
151   assertA((int)archive_entry_mtime(ae));
152   assertA((int)archive_entry_ctime(ae));
153   assertA((int)archive_entry_atime(ae));
154   assertEqualInt(size, archive_entry_size(ae));
155   assertEqualInt(33188, archive_entry_mode(ae));
156   while (offset + (int)sizeof(buff) < size)
157   {
158     assertA(sizeof(buff) == archive_read_data(a, buff, sizeof(buff)));
159     offset += sizeof(buff);
160   }
161   assertA(size - offset == archive_read_data(a, buff, size - offset));
162   assertEqualMem(buff, test_txt, size - offset);
163
164   /* Test EOF */
165   assertA(1 == archive_read_next_header(a, &ae));
166   assertEqualInt(1, archive_file_count(a));
167   assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
168   assertEqualInt(ARCHIVE_OK, archive_read_free(a));
169 }
170
171 #define BLOCK_SIZE 10240
172 struct mydata {
173   char *filename;
174   void *buffer;
175   int fd;
176 };
177
178 static int
179 file_open(struct archive *a, void *data)
180 {
181   struct mydata *mydata = (struct mydata *)data;
182   (void)a;
183   if (mydata->fd < 0)
184   {
185     mydata->fd = open(mydata->filename, O_RDONLY | O_BINARY);
186     if (mydata->fd >= 0)
187     {
188       if ((mydata->buffer = (void*)calloc(1, BLOCK_SIZE)) == NULL)
189         return (ARCHIVE_FAILED);
190     }
191   }
192   return (ARCHIVE_OK);
193 }
194 static ssize_t
195 file_read(struct archive *a, void *data, const void **buff)
196 {
197   struct mydata *mydata = (struct mydata *)data;
198   (void)a;
199   *buff = mydata->buffer;
200   return read(mydata->fd, mydata->buffer, BLOCK_SIZE);
201 }
202 static int64_t
203 file_skip(struct archive *a, void *data, int64_t request)
204 {
205   struct mydata *mydata = (struct mydata *)data;
206   int64_t result = lseek(mydata->fd, SEEK_CUR, request);
207   if (result >= 0)
208     return result;
209   archive_set_error(a, errno, "Error seeking in '%s'", mydata->filename);
210   return -1;
211 }
212 static int
213 file_switch(struct archive *a, void *data1, void *data2)
214 {
215   struct mydata *mydata1 = (struct mydata *)data1;
216   struct mydata *mydata2 = (struct mydata *)data2;
217   int r = (ARCHIVE_OK);
218
219   (void)a;
220   if (mydata1 && mydata1->fd >= 0)
221   {
222     close(mydata1->fd);
223     free(mydata1->buffer);
224     mydata1->buffer = NULL;
225     mydata1->fd = -1;
226   }
227   if (mydata2)
228   {
229     r = file_open(a, mydata2);
230   }
231   return (r);
232 }
233 static int
234 file_close(struct archive *a, void *data)
235 {
236   struct mydata *mydata = (struct mydata *)data;
237   if (mydata == NULL)
238     return (ARCHIVE_FATAL);
239   file_switch(a, mydata, NULL);
240   free(mydata->filename);
241   free(mydata);
242   return (ARCHIVE_OK);
243 }
244 static int64_t
245 file_seek(struct archive *a, void *data, int64_t request, int whence)
246 {
247   struct mydata *mine = (struct mydata *)data;
248   int64_t r;
249
250   (void)a;
251   r = lseek(mine->fd, request, whence);
252   if (r >= 0)
253     return r;
254   return (ARCHIVE_FATAL);
255 }
256
257 static void
258 test_customized_multiple_data_objects(void)
259 {
260   char buff[64];
261   static const char *reffiles[] =
262   {
263     "test_read_splitted_rar_aa",
264     "test_read_splitted_rar_ab",
265     "test_read_splitted_rar_ac",
266     "test_read_splitted_rar_ad",
267     NULL
268   };
269   const char test_txt[] = "test text document\r\n";
270   int size = sizeof(test_txt)-1;
271   struct archive_entry *ae;
272   struct archive *a;
273   struct mydata *mydata;
274   const char *filename = *reffiles;
275   int i;
276
277   extract_reference_files(reffiles);
278   assert((a = archive_read_new()) != NULL);
279   assertA(0 == archive_read_support_filter_all(a));
280   assertA(0 == archive_read_support_format_all(a));
281
282   for (i = 0; filename != NULL;)
283   {
284     assert((mydata = (struct mydata *)calloc(1, sizeof(*mydata))) != NULL);
285     if (mydata == NULL) {
286       assertEqualInt(ARCHIVE_OK, archive_read_free(a));
287       return;
288     }
289     assert((mydata->filename =
290       (char *)calloc(1, strlen(filename) + 1)) != NULL);
291     if (mydata->filename == NULL) {
292       free(mydata);
293       assertEqualInt(ARCHIVE_OK, archive_read_free(a));
294       return;
295     }
296     strcpy(mydata->filename, filename);
297     mydata->fd = -1;
298     filename = reffiles[++i];
299     assertA(0 == archive_read_append_callback_data(a, mydata));
300   }
301         assertA(0 == archive_read_set_open_callback(a, file_open));
302         assertA(0 == archive_read_set_read_callback(a, file_read));
303         assertA(0 == archive_read_set_skip_callback(a, file_skip));
304         assertA(0 == archive_read_set_close_callback(a, file_close));
305         assertA(0 == archive_read_set_switch_callback(a, file_switch));
306   assertA(0 == archive_read_set_seek_callback(a, file_seek));
307   assertA(0 == archive_read_open1(a));
308
309   /* First header. */
310   assertA(0 == archive_read_next_header(a, &ae));
311   assertEqualString("test.txt", archive_entry_pathname(ae));
312   assertA((int)archive_entry_mtime(ae));
313   assertA((int)archive_entry_ctime(ae));
314   assertA((int)archive_entry_atime(ae));
315   assertEqualInt(20, archive_entry_size(ae));
316   assertEqualInt(33188, archive_entry_mode(ae));
317   assertA(size == archive_read_data(a, buff, size));
318   assertEqualMem(buff, test_txt, size);
319
320   /* Second header. */
321   assertA(0 == archive_read_next_header(a, &ae));
322   assertEqualString("testlink", archive_entry_pathname(ae));
323   assertA((int)archive_entry_mtime(ae));
324   assertA((int)archive_entry_ctime(ae));
325   assertA((int)archive_entry_atime(ae));
326   assertEqualInt(0, archive_entry_size(ae));
327   assertEqualInt(41471, archive_entry_mode(ae));
328   assertEqualString("test.txt", archive_entry_symlink(ae));
329   assertEqualIntA(a, 0, archive_read_data(a, buff, sizeof(buff)));
330
331   /* Third header. */
332   assertA(0 == archive_read_next_header(a, &ae));
333   assertEqualString("testdir/test.txt", archive_entry_pathname(ae));
334   assertA((int)archive_entry_mtime(ae));
335   assertA((int)archive_entry_ctime(ae));
336   assertA((int)archive_entry_atime(ae));
337   assertEqualInt(20, archive_entry_size(ae));
338   assertEqualInt(33188, archive_entry_mode(ae));
339   assertA(size == archive_read_data(a, buff, size));
340   assertEqualMem(buff, test_txt, size);
341
342   /* Fourth header. */
343   assertA(0 == archive_read_next_header(a, &ae));
344   assertEqualString("testdir", archive_entry_pathname(ae));
345   assertA((int)archive_entry_mtime(ae));
346   assertA((int)archive_entry_ctime(ae));
347   assertA((int)archive_entry_atime(ae));
348   assertEqualInt(0, archive_entry_size(ae));
349   assertEqualInt(16877, archive_entry_mode(ae));
350
351   /* Fifth header. */
352   assertA(0 == archive_read_next_header(a, &ae));
353   assertEqualString("testemptydir", archive_entry_pathname(ae));
354   assertA((int)archive_entry_mtime(ae));
355   assertA((int)archive_entry_ctime(ae));
356   assertA((int)archive_entry_atime(ae));
357   assertEqualInt(0, archive_entry_size(ae));
358   assertEqualInt(16877, archive_entry_mode(ae));
359
360   /* Test EOF */
361   assertA(1 == archive_read_next_header(a, &ae));
362   assertEqualInt(5, archive_file_count(a));
363   assertEqualIntA(a, ARCHIVE_OK, archive_read_close(a));
364   assertEqualInt(ARCHIVE_OK, archive_read_free(a));
365 }
366
367 DEFINE_TEST(test_archive_read_multiple_data_objects)
368 {
369   test_splitted_file();
370   test_large_splitted_file();
371   test_customized_multiple_data_objects();
372 }