1 /*-
2  * Copyright (c) 2003-2007 Tim Kientzle
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
15  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
16  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17  * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
18  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
19  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
20  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
21  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25 #include "test.h"
26 __FBSDID("$FreeBSD: head/lib/libarchive/test/test_read_format_tar.c 201247 2009-12-30 05:59:21Z kientzle $");
27 
28 /*
29  * Each of these archives is a short archive with a single entry.  The
30  * corresponding verify function verifies the entry structure returned
31  * from libarchive is what it should be.  The support functions pad with
32  * lots of zeros, so we can trim trailing zero bytes from each hardcoded
33  * archive to save space.
34  *
35  * The naming here follows the tar file type flags.  E.g. '1' is a hardlink,
36  * '2' is a symlink, '5' is a dir, etc.
37  */
38 
39 /* Empty archive. */
40 static unsigned char archiveEmpty[] = {
41 	/* 512 zero bytes */
42 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
43 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
44 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
45 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
46 
47 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
48 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
49 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
50 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
51 
52 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
53 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
54 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
55 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
56 
57 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
58 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
59 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,
60 	0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0
61 };
62 
63 static void verifyEmpty(void)
64 {
65 	struct archive_entry *ae;
66 	struct archive *a;
67 
68 	assert((a = archive_read_new()) != NULL);
69 	assertA(0 == archive_read_support_compression_all(a));
70 	assertA(0 == archive_read_support_format_all(a));
71 	assertA(0 == archive_read_open_memory(a, archiveEmpty, 512));
72 	assertEqualIntA(a, ARCHIVE_EOF, archive_read_next_header(a, &ae));
73 	assertEqualInt(archive_compression(a), ARCHIVE_COMPRESSION_NONE);
74 	assertEqualString(archive_compression_name(a), "none");
75 	failure("512 zero bytes should be recognized as a tar archive.");
76 	assertEqualInt(archive_format(a), ARCHIVE_FORMAT_TAR);
77 
78 	assert(0 == archive_read_close(a));
79 #if ARCHIVE_VERSION_NUMBER < 2000000
80 	archive_read_finish(a);
81 #else
82 	assert(0 == archive_read_finish(a));
83 #endif
84 }
85 
86 /* Single entry with a hardlink. */
87 static unsigned char archive1[] = {
88 'h','a','r','d','l','i','n','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
89 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
90 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0',
91 '0','6','4','4',' ',0,'0','0','1','7','5','0',' ',0,'0','0','1','7','5','0',
92 ' ',0,'0','0','0','0','0','0','0','0','0','0','0',' ','1','0','6','4','6',
93 '0','5','2','6','6','2',' ','0','1','3','0','5','7',0,' ','1','f','i','l',
94 'e',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
95 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
96 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,'0',
97 '0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
98 't','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0',
99 '0','0','0','0','0',' ',0,'0','0','0','0','0','0',' '};
100 
101 static void verify1(struct archive_entry *ae)
102 {
103 	/* A hardlink is not a symlink. */
104 	assert(archive_entry_filetype(ae) != AE_IFLNK);
105 	/* Nor is it a directory. */
106 	assert(archive_entry_filetype(ae) != AE_IFDIR);
107 	assertEqualInt(archive_entry_mode(ae) & 0777, 0644);
108 	assertEqualInt(archive_entry_uid(ae), 1000);
109 	assertEqualInt(archive_entry_gid(ae), 1000);
110 	assertEqualString(archive_entry_uname(ae), "tim");
111 	assertEqualString(archive_entry_gname(ae), "tim");
112 	assertEqualString(archive_entry_pathname(ae), "hardlink");
113 	assertEqualString(archive_entry_hardlink(ae), "file");
114 	assert(archive_entry_symlink(ae) == NULL);
115 	assertEqualInt(archive_entry_mtime(ae), 1184388530);
116 }
117 
118 /* Verify that symlinks are read correctly. */
119 static unsigned char archive2[] = {
120 's','y','m','l','i','n','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
121 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
122 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0',
123 '0','0','7','5','5',' ','0','0','0','1','7','5','0',' ','0','0','0','1','7',
124 '5','0',' ','0','0','0','0','0','0','0','0','0','0','0',' ','1','0','6','4',
125 '6','0','5','4','1','0','1',' ','0','0','1','3','3','2','3',' ','2','f','i',
126 'l','e',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
127 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
128 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,
129 '0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
130 0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
131 '0','0','0','0','0','0','0',' ','0','0','0','0','0','0','0',' '};
132 
133 static void verify2(struct archive_entry *ae)
134 {
135 	assertEqualInt(archive_entry_filetype(ae), AE_IFLNK);
136 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
137 	assertEqualInt(archive_entry_uid(ae), 1000);
138 	assertEqualInt(archive_entry_gid(ae), 1000);
139 	assertEqualString(archive_entry_uname(ae), "tim");
140 	assertEqualString(archive_entry_gname(ae), "tim");
141 	assertEqualString(archive_entry_pathname(ae), "symlink");
142 	assertEqualString(archive_entry_symlink(ae), "file");
143 	assert(archive_entry_hardlink(ae) == NULL);
144 	assertEqualInt(archive_entry_mtime(ae), 1184389185);
145 }
146 
147 /* Character device node. */
148 static unsigned char archive3[] = {
149 'd','e','v','c','h','a','r',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
150 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
151 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0',
152 '0','0','7','5','5',' ','0','0','0','1','7','5','0',' ','0','0','0','1','7',
153 '5','0',' ','0','0','0','0','0','0','0','0','0','0','0',' ','1','0','6','4',
154 '6','0','5','4','1','0','1',' ','0','0','1','2','4','1','2',' ','3',0,0,
155 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
156 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
157 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,
158 '0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
159 0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
160 '0','0','0','0','0','0','0',' ','0','0','0','0','0','0','0',' '};
161 
162 static void verify3(struct archive_entry *ae)
163 {
164 	assertEqualInt(archive_entry_filetype(ae), AE_IFCHR);
165 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
166 	assertEqualInt(archive_entry_uid(ae), 1000);
167 	assertEqualInt(archive_entry_gid(ae), 1000);
168 	assertEqualString(archive_entry_uname(ae), "tim");
169 	assertEqualString(archive_entry_gname(ae), "tim");
170 	assertEqualString(archive_entry_pathname(ae), "devchar");
171 	assert(archive_entry_symlink(ae) == NULL);
172 	assert(archive_entry_hardlink(ae) == NULL);
173 	assertEqualInt(archive_entry_mtime(ae), 1184389185);
174 }
175 
176 /* Block device node. */
177 static unsigned char archive4[] = {
178 'd','e','v','b','l','o','c','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
179 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
180 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0',
181 '0','0','7','5','5',' ','0','0','0','1','7','5','0',' ','0','0','0','1','7',
182 '5','0',' ','0','0','0','0','0','0','0','0','0','0','0',' ','1','0','6','4',
183 '6','0','5','4','1','0','1',' ','0','0','1','2','5','7','0',' ','4',0,0,
184 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
185 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
186 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,
187 '0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
188 0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
189 '0','0','0','0','0','0','0',' ','0','0','0','0','0','0','0',' '};
190 
191 static void verify4(struct archive_entry *ae)
192 {
193 	assertEqualInt(archive_entry_filetype(ae), AE_IFBLK);
194 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
195 	assertEqualInt(archive_entry_uid(ae), 1000);
196 	assertEqualInt(archive_entry_gid(ae), 1000);
197 	assertEqualString(archive_entry_uname(ae), "tim");
198 	assertEqualString(archive_entry_gname(ae), "tim");
199 	assertEqualString(archive_entry_pathname(ae), "devblock");
200 	assert(archive_entry_symlink(ae) == NULL);
201 	assert(archive_entry_hardlink(ae) == NULL);
202 	assertEqualInt(archive_entry_mtime(ae), 1184389185);
203 }
204 
205 /* Directory. */
206 static unsigned char archive5[] = {
207 '.',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
208 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
209 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0','0',
210 '7','5','5',' ',0,'0','0','1','7','5','0',' ',0,'0','0','1','7','5','0',
211 ' ',0,'0','0','0','0','0','0','0','0','0','0','0',' ','1','0','3','3',
212 '4','0','4','1','7','3','6',' ','0','1','0','5','6','1',0,' ','5',0,0,0,
213 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
214 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
215 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,
216 '0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
217 0,0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
218 0,0,'0','0','0','0','0','0',' ',0,'0','0','0','0','0','0',' '};
219 
220 static void verify5(struct archive_entry *ae)
221 {
222 	assertEqualInt(archive_entry_filetype(ae), AE_IFDIR);
223 	assertEqualInt(archive_entry_mtime(ae), 1131430878);
224 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
225 	assertEqualInt(archive_entry_uid(ae), 1000);
226 	assertEqualInt(archive_entry_gid(ae), 1000);
227 	assertEqualString(archive_entry_uname(ae), "tim");
228 	assertEqualString(archive_entry_gname(ae), "tim");
229 }
230 
231 /* fifo */
232 static unsigned char archive6[] = {
233 'f','i','f','o',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
234 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
235 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0',
236 '0','0','7','5','5',' ','0','0','0','1','7','5','0',' ','0','0','0','1','7',
237 '5','0',' ','0','0','0','0','0','0','0','0','0','0','0',' ','1','0','6','4',
238 '6','0','5','4','1','0','1',' ','0','0','1','1','7','2','4',' ','6',0,0,
239 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
240 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
241 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',0,
242 '0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
243 0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
244 '0','0','0','0','0','0','0',' ','0','0','0','0','0','0','0',' '};
245 
246 static void verify6(struct archive_entry *ae)
247 {
248 	assertEqualInt(archive_entry_filetype(ae), AE_IFIFO);
249 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
250 	assertEqualInt(archive_entry_uid(ae), 1000);
251 	assertEqualInt(archive_entry_gid(ae), 1000);
252 	assertEqualString(archive_entry_uname(ae), "tim");
253 	assertEqualString(archive_entry_gname(ae), "tim");
254 	assertEqualString(archive_entry_pathname(ae), "fifo");
255 	assert(archive_entry_symlink(ae) == NULL);
256 	assert(archive_entry_hardlink(ae) == NULL);
257 	assertEqualInt(archive_entry_mtime(ae), 1184389185);
258 }
259 
260 /* GNU long link name */
261 static unsigned char archiveK[] = {
262 '.','/','.','/','@','L','o','n','g','L','i','n','k',0,0,0,0,0,0,0,0,0,0,0,
263 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
264 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
265 0,0,'0','0','0','0','0','0','0',0,'0','0','0','0','0','0','0',0,'0','0','0',
266 '0','0','0','0',0,'0','0','0','0','0','0','0','0','6','6','6',0,'0','0','0',
267 '0','0','0','0','0','0','0','0',0,'0','1','1','7','1','5',0,' ','K',0,0,0,
268 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
269 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
270 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u','s','t','a','r',' ',' ',
271 0,'r','o','o','t',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
272 'w','h','e','e','l',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
273 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
274 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
275 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
276 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
277 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'t',
278 'h','i','s','_','i','s','_','a','_','v','e','r','y','_','l','o','n','g','_',
279 's','y','m','l','i','n','k','_','b','o','d','y','_','a','b','c','d','e','f',
280 'g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y',
281 'z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q',
282 'r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i',
283 'j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a',
284 'b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t',
285 'u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l',
286 'm','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d',
287 'e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w',
288 'x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o',
289 'p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g',
290 'h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z',
291 '_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r',
292 's','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j',
293 'k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b',
294 'c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u',
295 'v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m',
296 'n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e',
297 'f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x',
298 'y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p',
299 'q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g','h',
300 'i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z',0,
301 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
302 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
303 's','y','m','l','i','n','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
304 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
305 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','1',
306 '2','0','7','5','5',0,'0','0','0','1','7','5','0',0,'0','0','0','1','7','5',
307 '0',0,'0','0','0','0','0','0','0','0','0','0','0',0,'1','0','6','4','6','0',
308 '5','6','7','7','0',0,'0','3','5','4','4','7',0,' ','2','t','h','i','s','_',
309 'i','s','_','a','_','v','e','r','y','_','l','o','n','g','_','s','y','m','l',
310 'i','n','k','_','b','o','d','y','_','a','b','c','d','e','f','g','h','i','j',
311 'k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b',
312 'c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u',
313 'v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l',0,
314 'u','s','t','a','r',' ',' ',0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
315 0,0,0,0,0,0,0,0,0,0,0,0,0,'t','i','m'};
316 
317 static void verifyK(struct archive_entry *ae)
318 {
319 	assertEqualInt(archive_entry_filetype(ae), AE_IFLNK);
320 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
321 	assertEqualInt(archive_entry_uid(ae), 1000);
322 	assertEqualInt(archive_entry_gid(ae), 1000);
323 	assertEqualString(archive_entry_uname(ae), "tim");
324 	assertEqualString(archive_entry_gname(ae), "tim");
325 	assertEqualString(archive_entry_pathname(ae), "symlink");
326 	assertEqualString(archive_entry_symlink(ae),
327 	    "this_is_a_very_long_symlink_body_abcdefghijklmnopqrstuvwxyz_"
328 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
329 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
330 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
331 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
332 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
333 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
334 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz");
335 	assert(archive_entry_hardlink(ae) == NULL);
336 	assertEqualInt(archive_entry_mtime(ae), 1184390648);
337 }
338 
339 /* TODO: GNU long name */
340 
341 /* TODO: Solaris ACL */
342 
343 /* Pax extended long link name */
344 static unsigned char archivexL[] = {
345 '.','/','P','a','x','H','e','a','d','e','r','s','.','8','6','9','7','5','/',
346 's','y','m','l','i','n','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
347 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
348 0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0','0','0','6','4','4',0,'0','0','0','1',
349 '7','5','0',0,'0','0','0','1','7','5','0',0,'0','0','0','0','0','0','0','0',
350 '7','5','3',0,'1','0','6','4','6','0','5','7','6','1','1',0,'0','1','3','7',
351 '1','4',0,' ','x',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
352 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
353 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'u',
354 's','t','a','r',0,'0','0',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
355 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
356 0,0,0,'0','0','0','0','0','0','0',0,'0','0','0','0','0','0','0',0,0,0,0,0,
357 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
358 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
359 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
360 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
361 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'4','5','1',' ','l','i','n','k','p','a','t',
362 'h','=','t','h','i','s','_','i','s','_','a','_','v','e','r','y','_','l','o',
363 'n','g','_','s','y','m','l','i','n','k','_','b','o','d','y','_','a','b','c',
364 'd','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v',
365 'w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n',
366 'o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f',
367 'g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y',
368 'z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q',
369 'r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i',
370 'j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a',
371 'b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t',
372 'u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l',
373 'm','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d',
374 'e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w',
375 'x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o',
376 'p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g',
377 'h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z',
378 '_','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r',
379 's','t','u','v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j',
380 'k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b',
381 'c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u',
382 'v','w','x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m',
383 'n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d','e',
384 'f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x',
385 'y','z',10,'2','0',' ','a','t','i','m','e','=','1','1','8','4','3','9','1',
386 '0','2','5',10,'2','0',' ','c','t','i','m','e','=','1','1','8','4','3','9',
387 '0','6','4','8',10,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'s','y','m',
388 'l','i','n','k',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
389 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
390 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,'0','0','0','0','7',
391 '5','5',0,'0','0','0','1','7','5','0',0,'0','0','0','1','7','5','0',0,'0',
392 '0','0','0','0','0','0','0','0','0','0',0,'1','0','6','4','6','0','5','6',
393 '7','7','0',0,'0','3','7','1','2','1',0,' ','2','t','h','i','s','_','i','s',
394 '_','a','_','v','e','r','y','_','l','o','n','g','_','s','y','m','l','i','n',
395 'k','_','b','o','d','y','_','a','b','c','d','e','f','g','h','i','j','k','l',
396 'm','n','o','p','q','r','s','t','u','v','w','x','y','z','_','a','b','c','d',
397 'e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w',
398 'x','y','z','_','a','b','c','d','e','f','g','h','i','j','k','l','m','u','s',
399 't','a','r',0,'0','0','t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
400 0,0,0,0,0,0,0,0,0,'t','i','m',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
401 0,0,0,0,0,0,0,'0','0','0','0','0','0','0',0,'0','0','0','0','0','0','0'};
402 
403 static void verifyxL(struct archive_entry *ae)
404 {
405 	assertEqualInt(archive_entry_filetype(ae), AE_IFLNK);
406 	assertEqualInt(archive_entry_mode(ae) & 0777, 0755);
407 	assertEqualInt(archive_entry_uid(ae), 1000);
408 	assertEqualInt(archive_entry_gid(ae), 1000);
409 	assertEqualString(archive_entry_uname(ae), "tim");
410 	assertEqualString(archive_entry_gname(ae), "tim");
411 	assertEqualString(archive_entry_pathname(ae), "symlink");
412 	assertEqualString(archive_entry_symlink(ae),
413 	    "this_is_a_very_long_symlink_body_abcdefghijklmnopqrstuvwxyz_"
414 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
415 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
416 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
417 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
418 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
419 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz_"
420 	    "abcdefghijklmnopqrstuvwxyz_abcdefghijklmnopqrstuvwxyz");
421 	assert(archive_entry_hardlink(ae) == NULL);
422 	assertEqualInt(archive_entry_mtime(ae), 1184390648);
423 }
424 
425 
426 /* TODO: Any other types of headers? */
427 
428 static void verify(unsigned char *d, size_t s,
429     void (*f)(struct archive_entry *),
430     int compression, int format)
431 {
432 	struct archive_entry *ae;
433 	struct archive *a;
434 	unsigned char *buff = malloc(100000);
435 
436 	memcpy(buff, d, s);
437 	memset(buff + s, 0, 2048);
438 
439 	assert((a = archive_read_new()) != NULL);
440 	assertA(0 == archive_read_support_compression_all(a));
441 	assertA(0 == archive_read_support_format_all(a));
442 	assertA(0 == archive_read_open_memory(a, buff, s + 1024));
443 	assertA(0 == archive_read_next_header(a, &ae));
444 	assertEqualInt(archive_compression(a), compression);
445 	assertEqualInt(archive_format(a), format);
446 
447 	/* Verify the only entry. */
448 	f(ae);
449 
450 	assert(0 == archive_read_close(a));
451 #if ARCHIVE_VERSION_NUMBER < 2000000
452 	archive_read_finish(a);
453 #else
454 	assert(0 == archive_read_finish(a));
455 #endif
456 	free(buff);
457 }
458 
459 DEFINE_TEST(test_read_format_tar)
460 {
461 	verifyEmpty();
462 	verify(archive1, sizeof(archive1), verify1,
463 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
464 	verify(archive2, sizeof(archive2), verify2,
465 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
466 	verify(archive3, sizeof(archive3), verify3,
467 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
468 	verify(archive4, sizeof(archive4), verify4,
469 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
470 	verify(archive5, sizeof(archive5), verify5,
471 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
472 	verify(archive6, sizeof(archive6), verify6,
473 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_USTAR);
474 	verify(archiveK, sizeof(archiveK), verifyK,
475 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_GNUTAR);
476 	verify(archivexL, sizeof(archivexL), verifyxL,
477 	    ARCHIVE_COMPRESSION_NONE, ARCHIVE_FORMAT_TAR_PAX_INTERCHANGE);
478 }
479 
480 
481