1 /*-
2  * Copyright (c) 2008 Joerg Sonnenberger
3  * Copyright (c) 2009-2012 Michihiro NAKAJIMA
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 "archive_platform.h"
28 __FBSDID("$FreeBSD: head/lib/libarchive/archive_write_set_format_mtree.c 201171 2009-12-29 06:39:07Z kientzle $");
29 
30 #ifdef HAVE_SYS_TYPES_H
31 #include <sys/types.h>
32 #endif
33 #include <errno.h>
34 #include <stdlib.h>
35 #include <string.h>
36 
37 #include "archive.h"
38 #include "archive_crypto_private.h"
39 #include "archive_entry.h"
40 #include "archive_private.h"
41 #include "archive_rb.h"
42 #include "archive_string.h"
43 #include "archive_write_private.h"
44 
45 #define INDENTNAMELEN	15
46 #define MAXLINELEN	80
47 #define SET_KEYS	\
48 	(F_FLAGS | F_GID | F_GNAME | F_MODE | F_TYPE | F_UID | F_UNAME)
49 
50 struct attr_counter {
51 	struct attr_counter *prev;
52 	struct attr_counter *next;
53 	struct mtree_entry *m_entry;
54 	int count;
55 };
56 
57 struct att_counter_set {
58 	struct attr_counter *uid_list;
59 	struct attr_counter *gid_list;
60 	struct attr_counter *mode_list;
61 	struct attr_counter *flags_list;
62 };
63 
64 struct mtree_chain {
65 	struct mtree_entry *first;
66 	struct mtree_entry **last;
67 };
68 
69 /*
70  * The Data only for a directory file.
71  */
72 struct dir_info {
73 	struct archive_rb_tree rbtree;
74 	struct mtree_chain children;
75 	struct mtree_entry *chnext;
76 	int virtual;
77 };
78 
79 /*
80  * The Data only for a regular file.
81  */
82 struct reg_info {
83 	int compute_sum;
84 	uint32_t crc;
85 #ifdef ARCHIVE_HAS_MD5
86 	unsigned char buf_md5[16];
87 #endif
88 #ifdef ARCHIVE_HAS_RMD160
89 	unsigned char buf_rmd160[20];
90 #endif
91 #ifdef ARCHIVE_HAS_SHA1
92 	unsigned char buf_sha1[20];
93 #endif
94 #ifdef ARCHIVE_HAS_SHA256
95 	unsigned char buf_sha256[32];
96 #endif
97 #ifdef ARCHIVE_HAS_SHA384
98 	unsigned char buf_sha384[48];
99 #endif
100 #ifdef ARCHIVE_HAS_SHA512
101 	unsigned char buf_sha512[64];
102 #endif
103 };
104 
105 struct mtree_entry {
106 	struct archive_rb_node rbnode;
107 	struct mtree_entry *next;
108 	struct mtree_entry *parent;
109 	struct dir_info *dir_info;
110 	struct reg_info *reg_info;
111 
112 	struct archive_string parentdir;
113 	struct archive_string basename;
114 	struct archive_string pathname;
115 	struct archive_string symlink;
116 	struct archive_string uname;
117 	struct archive_string gname;
118 	struct archive_string fflags_text;
119 	unsigned int nlink;
120 	mode_t filetype;
121 	mode_t mode;
122 	int64_t size;
123 	int64_t uid;
124 	int64_t gid;
125 	time_t mtime;
126 	long mtime_nsec;
127 	unsigned long fflags_set;
128 	unsigned long fflags_clear;
129 	dev_t rdevmajor;
130 	dev_t rdevminor;
131 };
132 
133 struct mtree_writer {
134 	struct mtree_entry *mtree_entry;
135 	struct mtree_entry *root;
136 	struct mtree_entry *cur_dirent;
137 	struct archive_string cur_dirstr;
138 	struct mtree_chain file_list;
139 
140 	struct archive_string ebuf;
141 	struct archive_string buf;
142 	int first;
143 	uint64_t entry_bytes_remaining;
144 
145 	/*
146 	 * Set global value.
147 	 */
148 	struct {
149 		int		processing;
150 		mode_t		type;
151 		int		keys;
152 		int64_t		uid;
153 		int64_t		gid;
154 		mode_t		mode;
155 		unsigned long	fflags_set;
156 		unsigned long	fflags_clear;
157 	} set;
158 	struct att_counter_set	acs;
159 	int classic;
160 	int depth;
161 
162 	/* check sum */
163 	int compute_sum;
164 	uint32_t crc;
165 	uint64_t crc_len;
166 #ifdef ARCHIVE_HAS_MD5
167 	archive_md5_ctx md5ctx;
168 #endif
169 #ifdef ARCHIVE_HAS_RMD160
170 	archive_rmd160_ctx rmd160ctx;
171 #endif
172 #ifdef ARCHIVE_HAS_SHA1
173 	archive_sha1_ctx sha1ctx;
174 #endif
175 #ifdef ARCHIVE_HAS_SHA256
176 	archive_sha256_ctx sha256ctx;
177 #endif
178 #ifdef ARCHIVE_HAS_SHA384
179 	archive_sha384_ctx sha384ctx;
180 #endif
181 #ifdef ARCHIVE_HAS_SHA512
182 	archive_sha512_ctx sha512ctx;
183 #endif
184 	/* Keyword options */
185 	int keys;
186 #define	F_CKSUM		0x00000001		/* check sum */
187 #define	F_DEV		0x00000002		/* device type */
188 #define	F_DONE		0x00000004		/* directory done */
189 #define	F_FLAGS		0x00000008		/* file flags */
190 #define	F_GID		0x00000010		/* gid */
191 #define	F_GNAME		0x00000020		/* group name */
192 #define	F_IGN		0x00000040		/* ignore */
193 #define	F_MAGIC		0x00000080		/* name has magic chars */
194 #define	F_MD5		0x00000100		/* MD5 digest */
195 #define	F_MODE		0x00000200		/* mode */
196 #define	F_NLINK		0x00000400		/* number of links */
197 #define	F_NOCHANGE 	0x00000800		/* If owner/mode "wrong", do
198 						 * not change */
199 #define	F_OPT		0x00001000		/* existence optional */
200 #define	F_RMD160 	0x00002000		/* RIPEMD160 digest */
201 #define	F_SHA1		0x00004000		/* SHA-1 digest */
202 #define	F_SIZE		0x00008000		/* size */
203 #define	F_SLINK		0x00010000		/* symbolic link */
204 #define	F_TAGS		0x00020000		/* tags */
205 #define	F_TIME		0x00040000		/* modification time */
206 #define	F_TYPE		0x00080000		/* file type */
207 #define	F_UID		0x00100000		/* uid */
208 #define	F_UNAME		0x00200000		/* user name */
209 #define	F_VISIT		0x00400000		/* file visited */
210 #define	F_SHA256	0x00800000		/* SHA-256 digest */
211 #define	F_SHA384	0x01000000		/* SHA-384 digest */
212 #define	F_SHA512	0x02000000		/* SHA-512 digest */
213 
214 	/* Options */
215 	int dironly;		/* If it is set, ignore all files except
216 				 * directory files, like mtree(8) -d option. */
217 	int indent;		/* If it is set, indent output data. */
218 	int output_global_set;	/* If it is set, use /set keyword to set
219 				 * global values. When generating mtree
220 				 * classic format, it is set by default. */
221 };
222 
223 #define DEFAULT_KEYS	(F_DEV | F_FLAGS | F_GID | F_GNAME | F_SLINK | F_MODE\
224 			 | F_NLINK | F_SIZE | F_TIME | F_TYPE | F_UID\
225 			 | F_UNAME)
226 #define attr_counter_set_reset	attr_counter_set_free
227 
228 static void attr_counter_free(struct attr_counter **);
229 static int attr_counter_inc(struct attr_counter **, struct attr_counter *,
230 	struct attr_counter *, struct mtree_entry *);
231 static struct attr_counter * attr_counter_new(struct mtree_entry *,
232 	struct attr_counter *);
233 static int attr_counter_set_collect(struct mtree_writer *,
234 	struct mtree_entry *);
235 static void attr_counter_set_free(struct mtree_writer *);
236 static int get_global_set_keys(struct mtree_writer *, struct mtree_entry *);
237 static int mtree_entry_add_child_tail(struct mtree_entry *,
238 	struct mtree_entry *);
239 static int mtree_entry_create_virtual_dir(struct archive_write *, const char *,
240 	struct mtree_entry **);
241 static int mtree_entry_cmp_node(const struct archive_rb_node *,
242 	const struct archive_rb_node *);
243 static int mtree_entry_cmp_key(const struct archive_rb_node *, const void *);
244 static int mtree_entry_exchange_same_entry(struct archive_write *,
245     struct mtree_entry *, struct mtree_entry *);
246 static void mtree_entry_free(struct mtree_entry *);
247 static int mtree_entry_new(struct archive_write *, struct archive_entry *,
248 	struct mtree_entry **);
249 static void mtree_entry_register_free(struct mtree_writer *);
250 static void mtree_entry_register_init(struct mtree_writer *);
251 static int mtree_entry_setup_filenames(struct archive_write *,
252 	struct mtree_entry *, struct archive_entry *);
253 static int mtree_entry_tree_add(struct archive_write *, struct mtree_entry **);
254 static void sum_init(struct mtree_writer *);
255 static void sum_update(struct mtree_writer *, const void *, size_t);
256 static void sum_final(struct mtree_writer *, struct reg_info *);
257 static void sum_write(struct archive_string *, struct reg_info *);
258 static int write_mtree_entry(struct archive_write *, struct mtree_entry *);
259 static int write_dot_dot_entry(struct archive_write *, struct mtree_entry *);
260 
261 #define	COMPUTE_CRC(var, ch)	(var) = (var) << 8 ^ crctab[(var) >> 24 ^ (ch)]
262 static const uint32_t crctab[] = {
263 	0x0,
264 	0x04c11db7, 0x09823b6e, 0x0d4326d9, 0x130476dc, 0x17c56b6b,
265 	0x1a864db2, 0x1e475005, 0x2608edb8, 0x22c9f00f, 0x2f8ad6d6,
266 	0x2b4bcb61, 0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd,
267 	0x4c11db70, 0x48d0c6c7, 0x4593e01e, 0x4152fda9, 0x5f15adac,
268 	0x5bd4b01b, 0x569796c2, 0x52568b75, 0x6a1936c8, 0x6ed82b7f,
269 	0x639b0da6, 0x675a1011, 0x791d4014, 0x7ddc5da3, 0x709f7b7a,
270 	0x745e66cd, 0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039,
271 	0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5, 0xbe2b5b58,
272 	0xbaea46ef, 0xb7a96036, 0xb3687d81, 0xad2f2d84, 0xa9ee3033,
273 	0xa4ad16ea, 0xa06c0b5d, 0xd4326d90, 0xd0f37027, 0xddb056fe,
274 	0xd9714b49, 0xc7361b4c, 0xc3f706fb, 0xceb42022, 0xca753d95,
275 	0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1, 0xe13ef6f4,
276 	0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d, 0x34867077, 0x30476dc0,
277 	0x3d044b19, 0x39c556ae, 0x278206ab, 0x23431b1c, 0x2e003dc5,
278 	0x2ac12072, 0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16,
279 	0x018aeb13, 0x054bf6a4, 0x0808d07d, 0x0cc9cdca, 0x7897ab07,
280 	0x7c56b6b0, 0x71159069, 0x75d48dde, 0x6b93dddb, 0x6f52c06c,
281 	0x6211e6b5, 0x66d0fb02, 0x5e9f46bf, 0x5a5e5b08, 0x571d7dd1,
282 	0x53dc6066, 0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba,
283 	0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e, 0xbfa1b04b,
284 	0xbb60adfc, 0xb6238b25, 0xb2e29692, 0x8aad2b2f, 0x8e6c3698,
285 	0x832f1041, 0x87ee0df6, 0x99a95df3, 0x9d684044, 0x902b669d,
286 	0x94ea7b2a, 0xe0b41de7, 0xe4750050, 0xe9362689, 0xedf73b3e,
287 	0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2, 0xc6bcf05f,
288 	0xc27dede8, 0xcf3ecb31, 0xcbffd686, 0xd5b88683, 0xd1799b34,
289 	0xdc3abded, 0xd8fba05a, 0x690ce0ee, 0x6dcdfd59, 0x608edb80,
290 	0x644fc637, 0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb,
291 	0x4f040d56, 0x4bc510e1, 0x46863638, 0x42472b8f, 0x5c007b8a,
292 	0x58c1663d, 0x558240e4, 0x51435d53, 0x251d3b9e, 0x21dc2629,
293 	0x2c9f00f0, 0x285e1d47, 0x36194d42, 0x32d850f5, 0x3f9b762c,
294 	0x3b5a6b9b, 0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff,
295 	0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623, 0xf12f560e,
296 	0xf5ee4bb9, 0xf8ad6d60, 0xfc6c70d7, 0xe22b20d2, 0xe6ea3d65,
297 	0xeba91bbc, 0xef68060b, 0xd727bbb6, 0xd3e6a601, 0xdea580d8,
298 	0xda649d6f, 0xc423cd6a, 0xc0e2d0dd, 0xcda1f604, 0xc960ebb3,
299 	0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7, 0xae3afba2,
300 	0xaafbe615, 0xa7b8c0cc, 0xa379dd7b, 0x9b3660c6, 0x9ff77d71,
301 	0x92b45ba8, 0x9675461f, 0x8832161a, 0x8cf30bad, 0x81b02d74,
302 	0x857130c3, 0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640,
303 	0x4e8ee645, 0x4a4ffbf2, 0x470cdd2b, 0x43cdc09c, 0x7b827d21,
304 	0x7f436096, 0x7200464f, 0x76c15bf8, 0x68860bfd, 0x6c47164a,
305 	0x61043093, 0x65c52d24, 0x119b4be9, 0x155a565e, 0x18197087,
306 	0x1cd86d30, 0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec,
307 	0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088, 0x2497d08d,
308 	0x2056cd3a, 0x2d15ebe3, 0x29d4f654, 0xc5a92679, 0xc1683bce,
309 	0xcc2b1d17, 0xc8ea00a0, 0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb,
310 	0xdbee767c, 0xe3a1cbc1, 0xe760d676, 0xea23f0af, 0xeee2ed18,
311 	0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4, 0x89b8fd09,
312 	0x8d79e0be, 0x803ac667, 0x84fbdbd0, 0x9abc8bd5, 0x9e7d9662,
313 	0x933eb0bb, 0x97ffad0c, 0xafb010b1, 0xab710d06, 0xa6322bdf,
314 	0xa2f33668, 0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4
315 };
316 
317 static const unsigned char safe_char[256] = {
318 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 00 - 0F */
319 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 10 - 1F */
320 	/* !"$%&'()*+,-./  EXCLUSION:0x20( ) 0x23(#) */
321 	0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* 20 - 2F */
322 	/* 0123456789:;<>?  EXCLUSION:0x3d(=) */
323 	1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, /* 30 - 3F */
324 	/* @ABCDEFGHIJKLMNO */
325 	1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* 40 - 4F */
326 	/* PQRSTUVWXYZ[]^_ EXCLUSION:0x5c(\)  */
327 	1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, /* 50 - 5F */
328 	/* `abcdefghijklmno */
329 	1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* 60 - 6F */
330 	/* pqrstuvwxyz{|}~ */
331 	1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, /* 70 - 7F */
332 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 80 - 8F */
333 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 90 - 9F */
334 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* A0 - AF */
335 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* B0 - BF */
336 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* C0 - CF */
337 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* D0 - DF */
338 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* E0 - EF */
339 	0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* F0 - FF */
340 };
341 
342 static void
343 mtree_quote(struct archive_string *s, const char *str)
344 {
345 	const char *start;
346 	char buf[4];
347 	unsigned char c;
348 
349 	for (start = str; *str != '\0'; ++str) {
350 		if (safe_char[*(const unsigned char *)str])
351 			continue;
352 		if (start != str)
353 			archive_strncat(s, start, str - start);
354 		c = (unsigned char)*str;
355 		buf[0] = '\\';
356 		buf[1] = (c / 64) + '0';
357 		buf[2] = (c / 8 % 8) + '0';
358 		buf[3] = (c % 8) + '0';
359 		archive_strncat(s, buf, 4);
360 		start = str + 1;
361 	}
362 
363 	if (start != str)
364 		archive_strncat(s, start, str - start);
365 }
366 
367 /*
368  * Indent a line as mtree utility to be readable for people.
369  */
370 static void
371 mtree_indent(struct mtree_writer *mtree)
372 {
373 	int i, fn, nd, pd;
374 	const char *r, *s, *x;
375 
376 	if (mtree->classic) {
377 		if (mtree->indent) {
378 			nd = 0;
379 			pd = mtree->depth * 4;
380 		} else {
381 			nd = mtree->depth?4:0;
382 			pd = 0;
383 		}
384 	} else
385 		nd = pd = 0;
386 	fn = 1;
387 	s = r = mtree->ebuf.s;
388 	x = NULL;
389 	while (*r == ' ')
390 		r++;
391 	while ((r = strchr(r, ' ')) != NULL) {
392 		if (fn) {
393 			fn = 0;
394 			for (i = 0; i < nd + pd; i++)
395 				archive_strappend_char(&mtree->buf, ' ');
396 			archive_strncat(&mtree->buf, s, r - s);
397 			if (nd + (r -s) > INDENTNAMELEN) {
398 				archive_strncat(&mtree->buf, " \\\n", 3);
399 				for (i = 0; i < (INDENTNAMELEN + 1 + pd); i++)
400 					archive_strappend_char(&mtree->buf, ' ');
401 			} else {
402 				for (i = (int)(r -s + nd);
403 				    i < (INDENTNAMELEN + 1); i++)
404 					archive_strappend_char(&mtree->buf, ' ');
405 			}
406 			s = ++r;
407 			x = NULL;
408 			continue;
409 		}
410 		if (pd + (r - s) <= MAXLINELEN - 3 - INDENTNAMELEN)
411 			x = r++;
412 		else {
413 			if (x == NULL)
414 				x = r;
415 			archive_strncat(&mtree->buf, s, x - s);
416 			archive_strncat(&mtree->buf, " \\\n", 3);
417 			for (i = 0; i < (INDENTNAMELEN + 1 + pd); i++)
418 				archive_strappend_char(&mtree->buf, ' ');
419 			s = r = ++x;
420 			x = NULL;
421 		}
422 	}
423 	if (fn) {
424 		for (i = 0; i < nd + pd; i++)
425 			archive_strappend_char(&mtree->buf, ' ');
426 		archive_strcat(&mtree->buf, s);
427 		s += strlen(s);
428 	}
429 	if (x != NULL && pd + strlen(s) > MAXLINELEN - 3 - INDENTNAMELEN) {
430 		/* Last keyword is longer. */
431 		archive_strncat(&mtree->buf, s, x - s);
432 		archive_strncat(&mtree->buf, " \\\n", 3);
433 		for (i = 0; i < (INDENTNAMELEN + 1 + pd); i++)
434 			archive_strappend_char(&mtree->buf, ' ');
435 		s = ++x;
436 	}
437 	archive_strcat(&mtree->buf, s);
438 	archive_string_empty(&mtree->ebuf);
439 }
440 
441 /*
442  * Write /set keyword.
443  * Set most used value of uid,gid,mode and fflags, which are
444  * collected by attr_counter_set_collect() function.
445  */
446 static void
447 write_global(struct mtree_writer *mtree)
448 {
449 	struct archive_string setstr;
450 	struct archive_string unsetstr;
451 	struct att_counter_set *acs;
452 	int keys, oldkeys, effkeys;
453 
454 	archive_string_init(&setstr);
455 	archive_string_init(&unsetstr);
456 	keys = mtree->keys & SET_KEYS;
457 	oldkeys = mtree->set.keys;
458 	effkeys = keys;
459 	acs = &mtree->acs;
460 	if (mtree->set.processing) {
461 		/*
462 		 * Check if the global data needs updating.
463 		 */
464 		effkeys &= ~F_TYPE;
465 		if (acs->uid_list == NULL)
466 			effkeys &= ~(F_UNAME | F_UID);
467 		else if (oldkeys & (F_UNAME | F_UID)) {
468 			if (acs->uid_list->count < 2 ||
469 			    mtree->set.uid == acs->uid_list->m_entry->uid)
470 				effkeys &= ~(F_UNAME | F_UID);
471 		}
472 		if (acs->gid_list == NULL)
473 			effkeys &= ~(F_GNAME | F_GID);
474 		else if (oldkeys & (F_GNAME | F_GID)) {
475 			if (acs->gid_list->count < 2 ||
476 			    mtree->set.gid == acs->gid_list->m_entry->gid)
477 				effkeys &= ~(F_GNAME | F_GID);
478 		}
479 		if (acs->mode_list == NULL)
480 			effkeys &= ~F_MODE;
481 		else if (oldkeys & F_MODE) {
482 			if (acs->mode_list->count < 2 ||
483 			    mtree->set.mode == acs->mode_list->m_entry->mode)
484 				effkeys &= ~F_MODE;
485 		}
486 		if (acs->flags_list == NULL)
487 			effkeys &= ~F_FLAGS;
488 		else if ((oldkeys & F_FLAGS) != 0) {
489 			if (acs->flags_list->count < 2 ||
490 			    (acs->flags_list->m_entry->fflags_set ==
491 				mtree->set.fflags_set &&
492 			     acs->flags_list->m_entry->fflags_clear ==
493 				mtree->set.fflags_clear))
494 				effkeys &= ~F_FLAGS;
495 		}
496 	} else {
497 		if (acs->uid_list == NULL)
498 			keys &= ~(F_UNAME | F_UID);
499 		if (acs->gid_list == NULL)
500 			keys &= ~(F_GNAME | F_GID);
501 		if (acs->mode_list == NULL)
502 			keys &= ~F_MODE;
503 		if (acs->flags_list == NULL)
504 			keys &= ~F_FLAGS;
505 	}
506 	if ((keys & effkeys & F_TYPE) != 0) {
507 		if (mtree->dironly) {
508 			archive_strcat(&setstr, " type=dir");
509 			mtree->set.type = AE_IFDIR;
510 		} else {
511 			archive_strcat(&setstr, " type=file");
512 			mtree->set.type = AE_IFREG;
513 		}
514 	}
515 	if ((keys & effkeys & F_UNAME) != 0) {
516 		if (archive_strlen(&(acs->uid_list->m_entry->uname)) > 0) {
517 			archive_strcat(&setstr, " uname=");
518 			mtree_quote(&setstr, acs->uid_list->m_entry->uname.s);
519 		} else {
520 			keys &= ~F_UNAME;
521 			if ((oldkeys & F_UNAME) != 0)
522 				archive_strcat(&unsetstr, " uname");
523 		}
524 	}
525 	if ((keys & effkeys & F_UID) != 0) {
526 		mtree->set.uid = acs->uid_list->m_entry->uid;
527 		archive_string_sprintf(&setstr, " uid=%jd",
528 		    (intmax_t)mtree->set.uid);
529 	}
530 	if ((keys & effkeys & F_GNAME) != 0) {
531 		if (archive_strlen(&(acs->gid_list->m_entry->gname)) > 0) {
532 			archive_strcat(&setstr, " gname=");
533 			mtree_quote(&setstr, acs->gid_list->m_entry->gname.s);
534 		} else {
535 			keys &= ~F_GNAME;
536 			if ((oldkeys & F_GNAME) != 0)
537 				archive_strcat(&unsetstr, " gname");
538 		}
539 	}
540 	if ((keys & effkeys & F_GID) != 0) {
541 		mtree->set.gid = acs->gid_list->m_entry->gid;
542 		archive_string_sprintf(&setstr, " gid=%jd",
543 		    (intmax_t)mtree->set.gid);
544 	}
545 	if ((keys & effkeys & F_MODE) != 0) {
546 		mtree->set.mode = acs->mode_list->m_entry->mode;
547 		archive_string_sprintf(&setstr, " mode=%o",
548 		    (unsigned int)mtree->set.mode);
549 	}
550 	if ((keys & effkeys & F_FLAGS) != 0) {
551 		if (archive_strlen(
552 		    &(acs->flags_list->m_entry->fflags_text)) > 0) {
553 			archive_strcat(&setstr, " flags=");
554 			mtree_quote(&setstr,
555 			    acs->flags_list->m_entry->fflags_text.s);
556 			mtree->set.fflags_set =
557 			    acs->flags_list->m_entry->fflags_set;
558 			mtree->set.fflags_clear =
559 			    acs->flags_list->m_entry->fflags_clear;
560 		} else {
561 			keys &= ~F_FLAGS;
562 			if ((oldkeys & F_FLAGS) != 0)
563 				archive_strcat(&unsetstr, " flags");
564 		}
565 	}
566 	if (unsetstr.length > 0)
567 		archive_string_sprintf(&mtree->buf, "/unset%s\n", unsetstr.s);
568 	archive_string_free(&unsetstr);
569 	if (setstr.length > 0)
570 		archive_string_sprintf(&mtree->buf, "/set%s\n", setstr.s);
571 	archive_string_free(&setstr);
572 	mtree->set.keys = keys;
573 	mtree->set.processing = 1;
574 }
575 
576 static struct attr_counter *
577 attr_counter_new(struct mtree_entry *me, struct attr_counter *prev)
578 {
579 	struct attr_counter *ac;
580 
581 	ac = malloc(sizeof(*ac));
582 	if (ac != NULL) {
583 		ac->prev = prev;
584 		ac->next = NULL;
585 		ac->count = 1;
586 		ac->m_entry = me;
587 	}
588 	return (ac);
589 }
590 
591 static void
592 attr_counter_free(struct attr_counter **top)
593 {
594 	struct attr_counter *ac, *tac;
595 
596 	if (*top == NULL)
597 		return;
598 	ac = *top;
599         while (ac != NULL) {
600 		tac = ac->next;
601 		free(ac);
602 		ac = tac;
603 	}
604 	*top = NULL;
605 }
606 
607 static int
608 attr_counter_inc(struct attr_counter **top, struct attr_counter *ac,
609     struct attr_counter *last, struct mtree_entry *me)
610 {
611 	struct attr_counter *pac;
612 
613 	if (ac != NULL) {
614 		ac->count++;
615 		if (*top == ac || ac->prev->count >= ac->count)
616 			return (0);
617 		for (pac = ac->prev; pac; pac = pac->prev) {
618 			if (pac->count >= ac->count)
619 				break;
620 		}
621 		ac->prev->next = ac->next;
622 		if (ac->next != NULL)
623 			ac->next->prev = ac->prev;
624 		if (pac != NULL) {
625 			ac->prev = pac;
626 			ac->next = pac->next;
627 			pac->next = ac;
628 			if (ac->next != NULL)
629 				ac->next->prev = ac;
630 		} else {
631 			ac->prev = NULL;
632 			ac->next = *top;
633 			*top = ac;
634 			ac->next->prev = ac;
635 		}
636 	} else {
637 		ac = attr_counter_new(me, last);
638 		if (ac == NULL)
639 			return (-1);
640 		last->next = ac;
641 	}
642 	return (0);
643 }
644 
645 /*
646  * Tabulate uid,gid,mode and fflags of a entry in order to be used for /set.
647  */
648 static int
649 attr_counter_set_collect(struct mtree_writer *mtree, struct mtree_entry *me)
650 {
651 	struct attr_counter *ac, *last;
652 	struct att_counter_set *acs = &mtree->acs;
653 	int keys = mtree->keys;
654 
655 	if (keys & (F_UNAME | F_UID)) {
656 		if (acs->uid_list == NULL) {
657 			acs->uid_list = attr_counter_new(me, NULL);
658 			if (acs->uid_list == NULL)
659 				return (-1);
660 		} else {
661 			last = NULL;
662 			for (ac = acs->uid_list; ac; ac = ac->next) {
663 				if (ac->m_entry->uid == me->uid)
664 					break;
665 				last = ac;
666 			}
667 			if (attr_counter_inc(&acs->uid_list, ac, last, me) < 0)
668 				return (-1);
669 		}
670 	}
671 	if (keys & (F_GNAME | F_GID)) {
672 		if (acs->gid_list == NULL) {
673 			acs->gid_list = attr_counter_new(me, NULL);
674 			if (acs->gid_list == NULL)
675 				return (-1);
676 		} else {
677 			last = NULL;
678 			for (ac = acs->gid_list; ac; ac = ac->next) {
679 				if (ac->m_entry->gid == me->gid)
680 					break;
681 				last = ac;
682 			}
683 			if (attr_counter_inc(&acs->gid_list, ac, last, me) < 0)
684 				return (-1);
685 		}
686 	}
687 	if (keys & F_MODE) {
688 		if (acs->mode_list == NULL) {
689 			acs->mode_list = attr_counter_new(me, NULL);
690 			if (acs->mode_list == NULL)
691 				return (-1);
692 		} else {
693 			last = NULL;
694 			for (ac = acs->mode_list; ac; ac = ac->next) {
695 				if (ac->m_entry->mode == me->mode)
696 					break;
697 				last = ac;
698 			}
699 			if (attr_counter_inc(&acs->mode_list, ac, last, me) < 0)
700 				return (-1);
701 		}
702 	}
703 	if (keys & F_FLAGS) {
704 		if (acs->flags_list == NULL) {
705 			acs->flags_list = attr_counter_new(me, NULL);
706 			if (acs->flags_list == NULL)
707 				return (-1);
708 		} else {
709 			last = NULL;
710 			for (ac = acs->flags_list; ac; ac = ac->next) {
711 				if (ac->m_entry->fflags_set == me->fflags_set &&
712 				    ac->m_entry->fflags_clear ==
713 							me->fflags_clear)
714 					break;
715 				last = ac;
716 			}
717 			if (attr_counter_inc(&acs->flags_list, ac, last, me) < 0)
718 				return (-1);
719 		}
720 	}
721 
722 	return (0);
723 }
724 
725 static void
726 attr_counter_set_free(struct mtree_writer *mtree)
727 {
728 	struct att_counter_set *acs = &mtree->acs;
729 
730 	attr_counter_free(&acs->uid_list);
731 	attr_counter_free(&acs->gid_list);
732 	attr_counter_free(&acs->mode_list);
733 	attr_counter_free(&acs->flags_list);
734 }
735 
736 static int
737 get_global_set_keys(struct mtree_writer *mtree, struct mtree_entry *me)
738 {
739 	int keys;
740 
741 	keys = mtree->keys;
742 
743 	/*
744 	 * If a keyword has been set by /set, we do not need to
745 	 * output it.
746 	 */
747 	if (mtree->set.keys == 0)
748 		return (keys);/* /set is not used. */
749 
750 	if ((mtree->set.keys & (F_GNAME | F_GID)) != 0 &&
751 	     mtree->set.gid == me->gid)
752 		keys &= ~(F_GNAME | F_GID);
753 	if ((mtree->set.keys & (F_UNAME | F_UID)) != 0 &&
754 	     mtree->set.uid == me->uid)
755 		keys &= ~(F_UNAME | F_UID);
756 	if (mtree->set.keys & F_FLAGS) {
757 		if (mtree->set.fflags_set == me->fflags_set &&
758 		    mtree->set.fflags_clear == me->fflags_clear)
759 			keys &= ~F_FLAGS;
760 	}
761 	if ((mtree->set.keys & F_MODE) != 0 && mtree->set.mode == me->mode)
762 		keys &= ~F_MODE;
763 
764 	switch (me->filetype) {
765 	case AE_IFLNK: case AE_IFSOCK: case AE_IFCHR:
766 	case AE_IFBLK: case AE_IFIFO:
767 		break;
768 	case AE_IFDIR:
769 		if ((mtree->set.keys & F_TYPE) != 0 &&
770 		    mtree->set.type == AE_IFDIR)
771 			keys &= ~F_TYPE;
772 		break;
773 	case AE_IFREG:
774 	default:	/* Handle unknown file types as regular files. */
775 		if ((mtree->set.keys & F_TYPE) != 0 &&
776 		    mtree->set.type == AE_IFREG)
777 			keys &= ~F_TYPE;
778 		break;
779 	}
780 
781 	return (keys);
782 }
783 
784 static int
785 mtree_entry_new(struct archive_write *a, struct archive_entry *entry,
786     struct mtree_entry **m_entry)
787 {
788 	struct mtree_entry *me;
789 	const char *s;
790 	int r;
791 	static const struct archive_rb_tree_ops rb_ops = {
792 		mtree_entry_cmp_node, mtree_entry_cmp_key
793 	};
794 
795 	me = calloc(1, sizeof(*me));
796 	if (me == NULL) {
797 		archive_set_error(&a->archive, ENOMEM,
798 		    "Can't allocate memory for a mtree entry");
799 		*m_entry = NULL;
800 		return (ARCHIVE_FATAL);
801 	}
802 
803 	r = mtree_entry_setup_filenames(a, me, entry);
804 	if (r < ARCHIVE_WARN) {
805 		mtree_entry_free(me);
806 		*m_entry = NULL;
807 		return (r);
808 	}
809 
810 	if ((s = archive_entry_symlink(entry)) != NULL)
811 		archive_strcpy(&me->symlink, s);
812 	me->nlink = archive_entry_nlink(entry);
813 	me->filetype = archive_entry_filetype(entry);
814 	me->mode = archive_entry_mode(entry) & 07777;
815 	me->uid = archive_entry_uid(entry);
816 	me->gid = archive_entry_gid(entry);
817 	if ((s = archive_entry_uname(entry)) != NULL)
818 		archive_strcpy(&me->uname, s);
819 	if ((s = archive_entry_gname(entry)) != NULL)
820 		archive_strcpy(&me->gname, s);
821 	if ((s = archive_entry_fflags_text(entry)) != NULL)
822 		archive_strcpy(&me->fflags_text, s);
823 	archive_entry_fflags(entry, &me->fflags_set, &me->fflags_clear);
824 	me->mtime = archive_entry_mtime(entry);
825 	me->mtime_nsec = archive_entry_mtime_nsec(entry);
826 	me->rdevmajor =	archive_entry_rdevmajor(entry);
827 	me->rdevminor = archive_entry_rdevminor(entry);
828 	me->size = archive_entry_size(entry);
829 	if (me->filetype == AE_IFDIR) {
830 		me->dir_info = calloc(1, sizeof(*me->dir_info));
831 		if (me->dir_info == NULL) {
832 			mtree_entry_free(me);
833 			archive_set_error(&a->archive, ENOMEM,
834 			    "Can't allocate memory for a mtree entry");
835 			*m_entry = NULL;
836 			return (ARCHIVE_FATAL);
837 		}
838 		__archive_rb_tree_init(&me->dir_info->rbtree, &rb_ops);
839 		me->dir_info->children.first = NULL;
840 		me->dir_info->children.last = &(me->dir_info->children.first);
841 		me->dir_info->chnext = NULL;
842 	} else if (me->filetype == AE_IFREG) {
843 		me->reg_info = calloc(1, sizeof(*me->reg_info));
844 		if (me->reg_info == NULL) {
845 			mtree_entry_free(me);
846 			archive_set_error(&a->archive, ENOMEM,
847 			    "Can't allocate memory for a mtree entry");
848 			*m_entry = NULL;
849 			return (ARCHIVE_FATAL);
850 		}
851 		me->reg_info->compute_sum = 0;
852 	}
853 
854 	*m_entry = me;
855 	return (ARCHIVE_OK);
856 }
857 
858 static void
859 mtree_entry_free(struct mtree_entry *me)
860 {
861 	archive_string_free(&me->parentdir);
862 	archive_string_free(&me->basename);
863 	archive_string_free(&me->pathname);
864 	archive_string_free(&me->symlink);
865 	archive_string_free(&me->uname);
866 	archive_string_free(&me->gname);
867 	archive_string_free(&me->fflags_text);
868 	free(me->dir_info);
869 	free(me->reg_info);
870 	free(me);
871 }
872 
873 static int
874 archive_write_mtree_header(struct archive_write *a,
875     struct archive_entry *entry)
876 {
877 	struct mtree_writer *mtree= a->format_data;
878 	struct mtree_entry *mtree_entry;
879 	int r, r2;
880 
881 	if (mtree->first) {
882 		mtree->first = 0;
883 		archive_strcat(&mtree->buf, "#mtree\n");
884 		if ((mtree->keys & SET_KEYS) == 0)
885 			mtree->output_global_set = 0;/* Disalbed. */
886 	}
887 
888 	mtree->entry_bytes_remaining = archive_entry_size(entry);
889 
890 	/* While directory only mode, we do not handle non directory files. */
891 	if (mtree->dironly && archive_entry_filetype(entry) != AE_IFDIR)
892 		return (ARCHIVE_OK);
893 
894 	r2 = mtree_entry_new(a, entry, &mtree_entry);
895 	if (r2 < ARCHIVE_WARN)
896 		return (r2);
897 	r = mtree_entry_tree_add(a, &mtree_entry);
898 	if (r < ARCHIVE_WARN) {
899 		mtree_entry_free(mtree_entry);
900 		return (r);
901 	}
902 	mtree->mtree_entry = mtree_entry;
903 
904 	/* If the current file is a regular file, we have to
905 	 * compute the sum of its content.
906 	 * Initialize a bunch of sum check context. */
907 	if (mtree_entry->reg_info)
908 		sum_init(mtree);
909 
910 	return (r2);
911 }
912 
913 static int
914 write_mtree_entry(struct archive_write *a, struct mtree_entry *me)
915 {
916 	struct mtree_writer *mtree = a->format_data;
917 	struct archive_string *str;
918 	int keys, ret;
919 
920 	if (me->dir_info) {
921 		if (mtree->classic) {
922 			/*
923 			 * Output a comment line to describe the full
924 			 * pathname of the entry as mtree utility does
925 			 * while generating classic format.
926 			 */
927 			if (!mtree->dironly)
928 				archive_strappend_char(&mtree->buf, '\n');
929 			if (me->parentdir.s)
930 				archive_string_sprintf(&mtree->buf,
931 				    "# %s/%s\n",
932 				    me->parentdir.s, me->basename.s);
933 			else
934 				archive_string_sprintf(&mtree->buf,
935 				    "# %s\n",
936 				    me->basename.s);
937 		}
938 		if (mtree->output_global_set)
939 			write_global(mtree);
940 	}
941 	archive_string_empty(&mtree->ebuf);
942 	str = (mtree->indent || mtree->classic)? &mtree->ebuf : &mtree->buf;
943 
944 	if (!mtree->classic && me->parentdir.s) {
945 		/*
946 		 * If generating format is not classic one(v1), output
947 		 * a full pathname.
948 		 */
949 		mtree_quote(str, me->parentdir.s);
950 		archive_strappend_char(str, '/');
951 	}
952 	mtree_quote(str, me->basename.s);
953 
954 	keys = get_global_set_keys(mtree, me);
955 	if ((keys & F_NLINK) != 0 &&
956 	    me->nlink != 1 && me->filetype != AE_IFDIR)
957 		archive_string_sprintf(str, " nlink=%u", me->nlink);
958 
959 	if ((keys & F_GNAME) != 0 && archive_strlen(&me->gname) > 0) {
960 		archive_strcat(str, " gname=");
961 		mtree_quote(str, me->gname.s);
962 	}
963 	if ((keys & F_UNAME) != 0 && archive_strlen(&me->uname) > 0) {
964 		archive_strcat(str, " uname=");
965 		mtree_quote(str, me->uname.s);
966 	}
967 	if ((keys & F_FLAGS) != 0) {
968 		if (archive_strlen(&me->fflags_text) > 0) {
969 			archive_strcat(str, " flags=");
970 			mtree_quote(str, me->fflags_text.s);
971 		} else if (mtree->set.processing &&
972 		    (mtree->set.keys & F_FLAGS) != 0)
973 			/* Overwrite the global parameter. */
974 			archive_strcat(str, " flags=none");
975 	}
976 	if ((keys & F_TIME) != 0)
977 		archive_string_sprintf(str, " time=%jd.%jd",
978 		    (intmax_t)me->mtime, (intmax_t)me->mtime_nsec);
979 	if ((keys & F_MODE) != 0)
980 		archive_string_sprintf(str, " mode=%o", (unsigned int)me->mode);
981 	if ((keys & F_GID) != 0)
982 		archive_string_sprintf(str, " gid=%jd", (intmax_t)me->gid);
983 	if ((keys & F_UID) != 0)
984 		archive_string_sprintf(str, " uid=%jd", (intmax_t)me->uid);
985 
986 	switch (me->filetype) {
987 	case AE_IFLNK:
988 		if ((keys & F_TYPE) != 0)
989 			archive_strcat(str, " type=link");
990 		if ((keys & F_SLINK) != 0) {
991 			archive_strcat(str, " link=");
992 			mtree_quote(str, me->symlink.s);
993 		}
994 		break;
995 	case AE_IFSOCK:
996 		if ((keys & F_TYPE) != 0)
997 			archive_strcat(str, " type=socket");
998 		break;
999 	case AE_IFCHR:
1000 		if ((keys & F_TYPE) != 0)
1001 			archive_strcat(str, " type=char");
1002 		if ((keys & F_DEV) != 0) {
1003 			archive_string_sprintf(str,
1004 			    " device=native,%ju,%ju",
1005 			    (uintmax_t)me->rdevmajor,
1006 			    (uintmax_t)me->rdevminor);
1007 		}
1008 		break;
1009 	case AE_IFBLK:
1010 		if ((keys & F_TYPE) != 0)
1011 			archive_strcat(str, " type=block");
1012 		if ((keys & F_DEV) != 0) {
1013 			archive_string_sprintf(str,
1014 			    " device=native,%ju,%ju",
1015 			    (uintmax_t)me->rdevmajor,
1016 			    (uintmax_t)me->rdevminor);
1017 		}
1018 		break;
1019 	case AE_IFDIR:
1020 		if ((keys & F_TYPE) != 0)
1021 			archive_strcat(str, " type=dir");
1022 		break;
1023 	case AE_IFIFO:
1024 		if ((keys & F_TYPE) != 0)
1025 			archive_strcat(str, " type=fifo");
1026 		break;
1027 	case AE_IFREG:
1028 	default:	/* Handle unknown file types as regular files. */
1029 		if ((keys & F_TYPE) != 0)
1030 			archive_strcat(str, " type=file");
1031 		if ((keys & F_SIZE) != 0)
1032 			archive_string_sprintf(str, " size=%jd",
1033 			    (intmax_t)me->size);
1034 		break;
1035 	}
1036 
1037 	/* Write a bunch of sum. */
1038 	if (me->reg_info)
1039 		sum_write(str, me->reg_info);
1040 
1041 	archive_strappend_char(str, '\n');
1042 	if (mtree->indent || mtree->classic)
1043 		mtree_indent(mtree);
1044 
1045 	if (mtree->buf.length > 32768) {
1046 		ret = __archive_write_output(
1047 			a, mtree->buf.s, mtree->buf.length);
1048 		archive_string_empty(&mtree->buf);
1049 	} else
1050 		ret = ARCHIVE_OK;
1051 	return (ret);
1052 }
1053 
1054 static int
1055 write_dot_dot_entry(struct archive_write *a, struct mtree_entry *n)
1056 {
1057 	struct mtree_writer *mtree = a->format_data;
1058 	int ret;
1059 
1060 	if (n->parentdir.s) {
1061 		if (mtree->indent) {
1062 			int i, pd = mtree->depth * 4;
1063 			for (i = 0; i < pd; i++)
1064 				archive_strappend_char(&mtree->buf, ' ');
1065 		}
1066 		archive_string_sprintf(&mtree->buf, "# %s/%s\n",
1067 			n->parentdir.s, n->basename.s);
1068 	}
1069 
1070 	if (mtree->indent) {
1071 		archive_string_empty(&mtree->ebuf);
1072 		archive_strncat(&mtree->ebuf, "..\n\n", (mtree->dironly)?3:4);
1073 		mtree_indent(mtree);
1074 	} else
1075 		archive_strncat(&mtree->buf, "..\n\n", (mtree->dironly)?3:4);
1076 
1077 	if (mtree->buf.length > 32768) {
1078 		ret = __archive_write_output(
1079 			a, mtree->buf.s, mtree->buf.length);
1080 		archive_string_empty(&mtree->buf);
1081 	} else
1082 		ret = ARCHIVE_OK;
1083 	return (ret);
1084 }
1085 
1086 /*
1087  * Write mtree entries saved at attr_counter_set_collect() function.
1088  */
1089 static int
1090 write_mtree_entry_tree(struct archive_write *a)
1091 {
1092 	struct mtree_writer *mtree = a->format_data;
1093 	struct mtree_entry *np = mtree->root;
1094 	struct archive_rb_node *n;
1095 	int ret;
1096 
1097 	do {
1098 		if (mtree->output_global_set) {
1099 			/*
1100 			 * Collect attribute infomation to know which value
1101 			 * is frequently used among the children.
1102 			 */
1103 			attr_counter_set_reset(mtree);
1104 			ARCHIVE_RB_TREE_FOREACH(n, &(np->dir_info->rbtree)) {
1105 				struct mtree_entry *e = (struct mtree_entry *)n;
1106 				if (attr_counter_set_collect(mtree, e) < 0) {
1107 					archive_set_error(&a->archive, ENOMEM,
1108 					    "Can't allocate memory");
1109 					return (ARCHIVE_FATAL);
1110 				}
1111 			}
1112 		}
1113 		if (!np->dir_info->virtual || mtree->classic) {
1114 			ret = write_mtree_entry(a, np);
1115 			if (ret != ARCHIVE_OK)
1116 				return (ARCHIVE_FATAL);
1117 		} else {
1118 			/* Whenever output_global_set is enabled
1119 			 * output global value(/set keywords)
1120 			 * even if the directory entry is not allowd
1121 			 * to be written because the global values
1122 			 * can be used for the children. */
1123 			if (mtree->output_global_set)
1124 				write_global(mtree);
1125 		}
1126 		/*
1127 		 * Output the attribute of all files except directory files.
1128 		 */
1129 		mtree->depth++;
1130 		ARCHIVE_RB_TREE_FOREACH(n, &(np->dir_info->rbtree)) {
1131 			struct mtree_entry *e = (struct mtree_entry *)n;
1132 
1133 			if (e->dir_info)
1134 				mtree_entry_add_child_tail(np, e);
1135 			else {
1136 				ret = write_mtree_entry(a, e);
1137 				if (ret != ARCHIVE_OK)
1138 					return (ARCHIVE_FATAL);
1139 			}
1140 		}
1141 		mtree->depth--;
1142 
1143 		if (np->dir_info->children.first != NULL) {
1144 			/*
1145 			 * Descend the tree.
1146 			 */
1147 			np = np->dir_info->children.first;
1148 			if (mtree->indent)
1149 				mtree->depth++;
1150 			continue;
1151 		} else if (mtree->classic) {
1152 			/*
1153 			 * While printing mtree classic, if there are not
1154 			 * any directory files(except "." and "..") in the
1155 			 * directory, output two dots ".." as returning
1156 			 * the parent directory.
1157 			 */
1158 			ret = write_dot_dot_entry(a, np);
1159 			if (ret != ARCHIVE_OK)
1160 				return (ARCHIVE_FATAL);
1161 		}
1162 
1163 		while (np != np->parent) {
1164 			if (np->dir_info->chnext == NULL) {
1165 				/*
1166 				 * Ascend the tree; go back to the parent.
1167 				 */
1168 				if (mtree->indent)
1169 					mtree->depth--;
1170 				if (mtree->classic) {
1171 					ret = write_dot_dot_entry(a,
1172 						np->parent);
1173 					if (ret != ARCHIVE_OK)
1174 						return (ARCHIVE_FATAL);
1175 				}
1176 				np = np->parent;
1177 			} else {
1178 				/*
1179 				 * Switch to next mtree entry in the directory.
1180 				 */
1181 				np = np->dir_info->chnext;
1182 				break;
1183 			}
1184 		}
1185 	} while (np != np->parent);
1186 
1187 	return (ARCHIVE_OK);
1188 }
1189 
1190 static int
1191 archive_write_mtree_finish_entry(struct archive_write *a)
1192 {
1193 	struct mtree_writer *mtree = a->format_data;
1194 	struct mtree_entry *me;
1195 
1196 	if ((me = mtree->mtree_entry) == NULL)
1197 		return (ARCHIVE_OK);
1198 	mtree->mtree_entry = NULL;
1199 
1200 	if (me->reg_info)
1201 		sum_final(mtree, me->reg_info);
1202 
1203 	return (ARCHIVE_OK);
1204 }
1205 
1206 static int
1207 archive_write_mtree_close(struct archive_write *a)
1208 {
1209 	struct mtree_writer *mtree= a->format_data;
1210 	int ret;
1211 
1212 	if (mtree->root != NULL) {
1213 		ret = write_mtree_entry_tree(a);
1214 		if (ret != ARCHIVE_OK)
1215 			return (ARCHIVE_FATAL);
1216 	}
1217 
1218 	archive_write_set_bytes_in_last_block(&a->archive, 1);
1219 
1220 	return __archive_write_output(a, mtree->buf.s, mtree->buf.length);
1221 }
1222 
1223 static ssize_t
1224 archive_write_mtree_data(struct archive_write *a, const void *buff, size_t n)
1225 {
1226 	struct mtree_writer *mtree= a->format_data;
1227 
1228 	if (n > mtree->entry_bytes_remaining)
1229 		n = (size_t)mtree->entry_bytes_remaining;
1230 	mtree->entry_bytes_remaining -= n;
1231 
1232 	/* We don't need to compute a regular file sum */
1233 	if (mtree->mtree_entry == NULL)
1234 		return (n);
1235 
1236 	if (mtree->mtree_entry->filetype == AE_IFREG)
1237 		sum_update(mtree, buff, n);
1238 
1239 	return (n);
1240 }
1241 
1242 static int
1243 archive_write_mtree_free(struct archive_write *a)
1244 {
1245 	struct mtree_writer *mtree= a->format_data;
1246 
1247 	if (mtree == NULL)
1248 		return (ARCHIVE_OK);
1249 
1250 	/* Make sure we dot not leave any entries. */
1251 	mtree_entry_register_free(mtree);
1252 	archive_string_free(&mtree->cur_dirstr);
1253 	archive_string_free(&mtree->ebuf);
1254 	archive_string_free(&mtree->buf);
1255 	attr_counter_set_free(mtree);
1256 	free(mtree);
1257 	a->format_data = NULL;
1258 	return (ARCHIVE_OK);
1259 }
1260 
1261 static int
1262 archive_write_mtree_options(struct archive_write *a, const char *key,
1263     const char *value)
1264 {
1265 	struct mtree_writer *mtree= a->format_data;
1266 	int keybit = 0;
1267 
1268 	switch (key[0]) {
1269 	case 'a':
1270 		if (strcmp(key, "all") == 0)
1271 			keybit = ~0;
1272 		break;
1273 	case 'c':
1274 		if (strcmp(key, "cksum") == 0)
1275 			keybit = F_CKSUM;
1276 		break;
1277 	case 'd':
1278 		if (strcmp(key, "device") == 0)
1279 			keybit = F_DEV;
1280 		else if (strcmp(key, "dironly") == 0) {
1281 			mtree->dironly = (value != NULL)? 1: 0;
1282 			return (ARCHIVE_OK);
1283 		}
1284 		break;
1285 	case 'f':
1286 		if (strcmp(key, "flags") == 0)
1287 			keybit = F_FLAGS;
1288 		break;
1289 	case 'g':
1290 		if (strcmp(key, "gid") == 0)
1291 			keybit = F_GID;
1292 		else if (strcmp(key, "gname") == 0)
1293 			keybit = F_GNAME;
1294 		break;
1295 	case 'i':
1296 		if (strcmp(key, "indent") == 0) {
1297 			mtree->indent = (value != NULL)? 1: 0;
1298 			return (ARCHIVE_OK);
1299 		}
1300 		break;
1301 	case 'l':
1302 		if (strcmp(key, "link") == 0)
1303 			keybit = F_SLINK;
1304 		break;
1305 	case 'm':
1306 		if (strcmp(key, "md5") == 0 ||
1307 		    strcmp(key, "md5digest") == 0)
1308 			keybit = F_MD5;
1309 		if (strcmp(key, "mode") == 0)
1310 			keybit = F_MODE;
1311 		break;
1312 	case 'n':
1313 		if (strcmp(key, "nlink") == 0)
1314 			keybit = F_NLINK;
1315 		break;
1316 	case 'r':
1317 		if (strcmp(key, "ripemd160digest") == 0 ||
1318 		    strcmp(key, "rmd160") == 0 ||
1319 		    strcmp(key, "rmd160digest") == 0)
1320 			keybit = F_RMD160;
1321 		break;
1322 	case 's':
1323 		if (strcmp(key, "sha1") == 0 ||
1324 		    strcmp(key, "sha1digest") == 0)
1325 			keybit = F_SHA1;
1326 		if (strcmp(key, "sha256") == 0 ||
1327 		    strcmp(key, "sha256digest") == 0)
1328 			keybit = F_SHA256;
1329 		if (strcmp(key, "sha384") == 0 ||
1330 		    strcmp(key, "sha384digest") == 0)
1331 			keybit = F_SHA384;
1332 		if (strcmp(key, "sha512") == 0 ||
1333 		    strcmp(key, "sha512digest") == 0)
1334 			keybit = F_SHA512;
1335 		if (strcmp(key, "size") == 0)
1336 			keybit = F_SIZE;
1337 		break;
1338 	case 't':
1339 		if (strcmp(key, "time") == 0)
1340 			keybit = F_TIME;
1341 		else if (strcmp(key, "type") == 0)
1342 			keybit = F_TYPE;
1343 		break;
1344 	case 'u':
1345 		if (strcmp(key, "uid") == 0)
1346 			keybit = F_UID;
1347 		else if (strcmp(key, "uname") == 0)
1348 			keybit = F_UNAME;
1349 		else if (strcmp(key, "use-set") == 0) {
1350 			mtree->output_global_set = (value != NULL)? 1: 0;
1351 			return (ARCHIVE_OK);
1352 		}
1353 		break;
1354 	}
1355 	if (keybit != 0) {
1356 		if (value != NULL)
1357 			mtree->keys |= keybit;
1358 		else
1359 			mtree->keys &= ~keybit;
1360 		return (ARCHIVE_OK);
1361 	}
1362 
1363 	/* Note: The "warn" return is just to inform the options
1364 	 * supervisor that we didn't handle it.  It will generate
1365 	 * a suitable error if no one used this option. */
1366 	return (ARCHIVE_WARN);
1367 }
1368 
1369 static int
1370 archive_write_set_format_mtree_default(struct archive *_a, const char *fn)
1371 {
1372 	struct archive_write *a = (struct archive_write *)_a;
1373 	struct mtree_writer *mtree;
1374 
1375 	archive_check_magic(_a, ARCHIVE_WRITE_MAGIC, ARCHIVE_STATE_NEW, fn);
1376 
1377 	if (a->format_free != NULL)
1378 		(a->format_free)(a);
1379 
1380 	if ((mtree = calloc(1, sizeof(*mtree))) == NULL) {
1381 		archive_set_error(&a->archive, ENOMEM,
1382 		    "Can't allocate mtree data");
1383 		return (ARCHIVE_FATAL);
1384 	}
1385 
1386 	mtree->mtree_entry = NULL;
1387 	mtree->first = 1;
1388 	memset(&(mtree->set), 0, sizeof(mtree->set));
1389 	mtree->keys = DEFAULT_KEYS;
1390 	mtree->dironly = 0;
1391 	mtree->indent = 0;
1392 	archive_string_init(&mtree->ebuf);
1393 	archive_string_init(&mtree->buf);
1394 	mtree_entry_register_init(mtree);
1395 	a->format_data = mtree;
1396 	a->format_free = archive_write_mtree_free;
1397 	a->format_name = "mtree";
1398 	a->format_options = archive_write_mtree_options;
1399 	a->format_write_header = archive_write_mtree_header;
1400 	a->format_close = archive_write_mtree_close;
1401 	a->format_write_data = archive_write_mtree_data;
1402 	a->format_finish_entry = archive_write_mtree_finish_entry;
1403 	a->archive.archive_format = ARCHIVE_FORMAT_MTREE;
1404 	a->archive.archive_format_name = "mtree";
1405 
1406 	return (ARCHIVE_OK);
1407 }
1408 
1409 int
1410 archive_write_set_format_mtree(struct archive *_a)
1411 {
1412 	return archive_write_set_format_mtree_default(_a,
1413 		"archive_write_set_format_mtree");
1414 }
1415 
1416 int
1417 archive_write_set_format_mtree_classic(struct archive *_a)
1418 {
1419 	int r;
1420 
1421 	r = archive_write_set_format_mtree_default(_a,
1422 		"archive_write_set_format_mtree_classic");
1423 	if (r == ARCHIVE_OK) {
1424 		struct archive_write *a = (struct archive_write *)_a;
1425 		struct mtree_writer *mtree;
1426 
1427 		mtree = (struct mtree_writer *)a->format_data;
1428 
1429 		/* Set to output a mtree archive in classic format. */
1430 		mtree->classic = 1;
1431 		/* Basically, mtree classic format uses '/set' global
1432 		 * value. */
1433 		mtree->output_global_set = 1;
1434 	}
1435 	return (r);
1436 }
1437 
1438 static void
1439 sum_init(struct mtree_writer *mtree)
1440 {
1441 
1442 	mtree->compute_sum = 0;
1443 
1444 	if (mtree->keys & F_CKSUM) {
1445 		mtree->compute_sum |= F_CKSUM;
1446 		mtree->crc = 0;
1447 		mtree->crc_len = 0;
1448 	}
1449 #ifdef ARCHIVE_HAS_MD5
1450 	if (mtree->keys & F_MD5) {
1451 		if (archive_md5_init(&mtree->md5ctx) == ARCHIVE_OK)
1452 			mtree->compute_sum |= F_MD5;
1453 		else
1454 			mtree->keys &= ~F_MD5;/* Not supported. */
1455 	}
1456 #endif
1457 #ifdef ARCHIVE_HAS_RMD160
1458 	if (mtree->keys & F_RMD160) {
1459 		if (archive_rmd160_init(&mtree->rmd160ctx) == ARCHIVE_OK)
1460 			mtree->compute_sum |= F_RMD160;
1461 		else
1462 			mtree->keys &= ~F_RMD160;/* Not supported. */
1463 	}
1464 #endif
1465 #ifdef ARCHIVE_HAS_SHA1
1466 	if (mtree->keys & F_SHA1) {
1467 		if (archive_sha1_init(&mtree->sha1ctx) == ARCHIVE_OK)
1468 			mtree->compute_sum |= F_SHA1;
1469 		else
1470 			mtree->keys &= ~F_SHA1;/* Not supported. */
1471 	}
1472 #endif
1473 #ifdef ARCHIVE_HAS_SHA256
1474 	if (mtree->keys & F_SHA256) {
1475 		if (archive_sha256_init(&mtree->sha256ctx) == ARCHIVE_OK)
1476 			mtree->compute_sum |= F_SHA256;
1477 		else
1478 			mtree->keys &= ~F_SHA256;/* Not supported. */
1479 	}
1480 #endif
1481 #ifdef ARCHIVE_HAS_SHA384
1482 	if (mtree->keys & F_SHA384) {
1483 		if (archive_sha384_init(&mtree->sha384ctx) == ARCHIVE_OK)
1484 			mtree->compute_sum |= F_SHA384;
1485 		else
1486 			mtree->keys &= ~F_SHA384;/* Not supported. */
1487 	}
1488 #endif
1489 #ifdef ARCHIVE_HAS_SHA512
1490 	if (mtree->keys & F_SHA512) {
1491 		if (archive_sha512_init(&mtree->sha512ctx) == ARCHIVE_OK)
1492 			mtree->compute_sum |= F_SHA512;
1493 		else
1494 			mtree->keys &= ~F_SHA512;/* Not supported. */
1495 	}
1496 #endif
1497 }
1498 
1499 static void
1500 sum_update(struct mtree_writer *mtree, const void *buff, size_t n)
1501 {
1502 	if (mtree->compute_sum & F_CKSUM) {
1503 		/*
1504 		 * Compute a POSIX 1003.2 checksum
1505 		 */
1506 		const unsigned char *p;
1507 		size_t nn;
1508 
1509 		for (nn = n, p = buff; nn--; ++p)
1510 			COMPUTE_CRC(mtree->crc, *p);
1511 		mtree->crc_len += n;
1512 	}
1513 #ifdef ARCHIVE_HAS_MD5
1514 	if (mtree->compute_sum & F_MD5)
1515 		archive_md5_update(&mtree->md5ctx, buff, n);
1516 #endif
1517 #ifdef ARCHIVE_HAS_RMD160
1518 	if (mtree->compute_sum & F_RMD160)
1519 		archive_rmd160_update(&mtree->rmd160ctx, buff, n);
1520 #endif
1521 #ifdef ARCHIVE_HAS_SHA1
1522 	if (mtree->compute_sum & F_SHA1)
1523 		archive_sha1_update(&mtree->sha1ctx, buff, n);
1524 #endif
1525 #ifdef ARCHIVE_HAS_SHA256
1526 	if (mtree->compute_sum & F_SHA256)
1527 		archive_sha256_update(&mtree->sha256ctx, buff, n);
1528 #endif
1529 #ifdef ARCHIVE_HAS_SHA384
1530 	if (mtree->compute_sum & F_SHA384)
1531 		archive_sha384_update(&mtree->sha384ctx, buff, n);
1532 #endif
1533 #ifdef ARCHIVE_HAS_SHA512
1534 	if (mtree->compute_sum & F_SHA512)
1535 		archive_sha512_update(&mtree->sha512ctx, buff, n);
1536 #endif
1537 }
1538 
1539 static void
1540 sum_final(struct mtree_writer *mtree, struct reg_info *reg)
1541 {
1542 
1543 	if (mtree->compute_sum & F_CKSUM) {
1544 		uint64_t len;
1545 		/* Include the length of the file. */
1546 		for (len = mtree->crc_len; len != 0; len >>= 8)
1547 			COMPUTE_CRC(mtree->crc, len & 0xff);
1548 		reg->crc = ~mtree->crc;
1549 	}
1550 #ifdef ARCHIVE_HAS_MD5
1551 	if (mtree->compute_sum & F_MD5)
1552 		archive_md5_final(&mtree->md5ctx, reg->buf_md5);
1553 #endif
1554 #ifdef ARCHIVE_HAS_RMD160
1555 	if (mtree->compute_sum & F_RMD160)
1556 		archive_rmd160_final(&mtree->rmd160ctx, reg->buf_rmd160);
1557 #endif
1558 #ifdef ARCHIVE_HAS_SHA1
1559 	if (mtree->compute_sum & F_SHA1)
1560 		archive_sha1_final(&mtree->sha1ctx, reg->buf_sha1);
1561 #endif
1562 #ifdef ARCHIVE_HAS_SHA256
1563 	if (mtree->compute_sum & F_SHA256)
1564 		archive_sha256_final(&mtree->sha256ctx, reg->buf_sha256);
1565 #endif
1566 #ifdef ARCHIVE_HAS_SHA384
1567 	if (mtree->compute_sum & F_SHA384)
1568 		archive_sha384_final(&mtree->sha384ctx, reg->buf_sha384);
1569 #endif
1570 #ifdef ARCHIVE_HAS_SHA512
1571 	if (mtree->compute_sum & F_SHA512)
1572 		archive_sha512_final(&mtree->sha512ctx, reg->buf_sha512);
1573 #endif
1574 	/* Save what types of sum are computed. */
1575 	reg->compute_sum = mtree->compute_sum;
1576 }
1577 
1578 #if defined(ARCHIVE_HAS_MD5) || defined(ARCHIVE_HAS_RMD160) || \
1579     defined(ARCHIVE_HAS_SHA1) || defined(ARCHIVE_HAS_SHA256) || \
1580     defined(ARCHIVE_HAS_SHA384) || defined(ARCHIVE_HAS_SHA512)
1581 static void
1582 strappend_bin(struct archive_string *s, const unsigned char *bin, int n)
1583 {
1584 	static const char hex[] = "0123456789abcdef";
1585 	int i;
1586 
1587 	for (i = 0; i < n; i++) {
1588 		archive_strappend_char(s, hex[bin[i] >> 4]);
1589 		archive_strappend_char(s, hex[bin[i] & 0x0f]);
1590 	}
1591 }
1592 #endif
1593 
1594 static void
1595 sum_write(struct archive_string *str, struct reg_info *reg)
1596 {
1597 
1598 	if (reg->compute_sum & F_CKSUM) {
1599 		archive_string_sprintf(str, " cksum=%ju",
1600 		    (uintmax_t)reg->crc);
1601 	}
1602 #ifdef ARCHIVE_HAS_MD5
1603 	if (reg->compute_sum & F_MD5) {
1604 		archive_strcat(str, " md5digest=");
1605 		strappend_bin(str, reg->buf_md5, sizeof(reg->buf_md5));
1606 	}
1607 #endif
1608 #ifdef ARCHIVE_HAS_RMD160
1609 	if (reg->compute_sum & F_RMD160) {
1610 		archive_strcat(str, " rmd160digest=");
1611 		strappend_bin(str, reg->buf_rmd160, sizeof(reg->buf_rmd160));
1612 	}
1613 #endif
1614 #ifdef ARCHIVE_HAS_SHA1
1615 	if (reg->compute_sum & F_SHA1) {
1616 		archive_strcat(str, " sha1digest=");
1617 		strappend_bin(str, reg->buf_sha1, sizeof(reg->buf_sha1));
1618 	}
1619 #endif
1620 #ifdef ARCHIVE_HAS_SHA256
1621 	if (reg->compute_sum & F_SHA256) {
1622 		archive_strcat(str, " sha256digest=");
1623 		strappend_bin(str, reg->buf_sha256, sizeof(reg->buf_sha256));
1624 	}
1625 #endif
1626 #ifdef ARCHIVE_HAS_SHA384
1627 	if (reg->compute_sum & F_SHA384) {
1628 		archive_strcat(str, " sha384digest=");
1629 		strappend_bin(str, reg->buf_sha384, sizeof(reg->buf_sha384));
1630 	}
1631 #endif
1632 #ifdef ARCHIVE_HAS_SHA512
1633 	if (reg->compute_sum & F_SHA512) {
1634 		archive_strcat(str, " sha512digest=");
1635 		strappend_bin(str, reg->buf_sha512, sizeof(reg->buf_sha512));
1636 	}
1637 #endif
1638 }
1639 
1640 static int
1641 mtree_entry_cmp_node(const struct archive_rb_node *n1,
1642     const struct archive_rb_node *n2)
1643 {
1644 	const struct mtree_entry *e1 = (const struct mtree_entry *)n1;
1645 	const struct mtree_entry *e2 = (const struct mtree_entry *)n2;
1646 
1647 	return (strcmp(e2->basename.s, e1->basename.s));
1648 }
1649 
1650 static int
1651 mtree_entry_cmp_key(const struct archive_rb_node *n, const void *key)
1652 {
1653 	const struct mtree_entry *e = (const struct mtree_entry *)n;
1654 
1655 	return (strcmp((const char *)key, e->basename.s));
1656 }
1657 
1658 #if defined(_WIN32) || defined(__CYGWIN__)
1659 static int
1660 cleanup_backslash_1(char *p)
1661 {
1662 	int mb, dos;
1663 
1664 	mb = dos = 0;
1665 	while (*p) {
1666 		if (*(unsigned char *)p > 127)
1667 			mb = 1;
1668 		if (*p == '\\') {
1669 			/* If we have not met any multi-byte characters,
1670 			 * we can replace '\' with '/'. */
1671 			if (!mb)
1672 				*p = '/';
1673 			dos = 1;
1674 		}
1675 		p++;
1676 	}
1677 	if (!mb || !dos)
1678 		return (0);
1679 	return (-1);
1680 }
1681 
1682 static void
1683 cleanup_backslash_2(wchar_t *p)
1684 {
1685 
1686 	/* Convert a path-separator from '\' to  '/' */
1687 	while (*p != L'\0') {
1688 		if (*p == L'\\')
1689 			*p = L'/';
1690 		p++;
1691 	}
1692 }
1693 #endif
1694 
1695 /*
1696  * Generate a parent directory name and a base name from a pathname.
1697  */
1698 static int
1699 mtree_entry_setup_filenames(struct archive_write *a, struct mtree_entry *file,
1700     struct archive_entry *entry)
1701 {
1702 	const char *pathname;
1703 	char *p, *dirname, *slash;
1704 	size_t len;
1705 	int ret = ARCHIVE_OK;
1706 
1707 	archive_strcpy(&file->pathname, archive_entry_pathname(entry));
1708 #if defined(_WIN32) || defined(__CYGWIN__)
1709 	/*
1710 	 * Convert a path-separator from '\' to  '/'
1711 	 */
1712 	if (cleanup_backslash_1(file->pathname.s) != 0) {
1713 		const wchar_t *wp = archive_entry_pathname_w(entry);
1714 		struct archive_wstring ws;
1715 
1716 		if (wp != NULL) {
1717 			int r;
1718 			archive_string_init(&ws);
1719 			archive_wstrcpy(&ws, wp);
1720 			cleanup_backslash_2(ws.s);
1721 			archive_string_empty(&(file->pathname));
1722 			r = archive_string_append_from_wcs(&(file->pathname),
1723 			    ws.s, ws.length);
1724 			archive_wstring_free(&ws);
1725 			if (r < 0 && errno == ENOMEM) {
1726 				archive_set_error(&a->archive, ENOMEM,
1727 				    "Can't allocate memory");
1728 				return (ARCHIVE_FATAL);
1729 			}
1730 		}
1731 	}
1732 #else
1733 	(void)a; /* UNUSED */
1734 #endif
1735 	pathname =  file->pathname.s;
1736 	if (strcmp(pathname, ".") == 0) {
1737 		archive_strcpy(&file->basename, ".");
1738 		return (ARCHIVE_OK);
1739 	}
1740 
1741 	archive_strcpy(&(file->parentdir), pathname);
1742 
1743 	len = file->parentdir.length;
1744 	p = dirname = file->parentdir.s;
1745 
1746 	/*
1747 	 * Remove leading '/' and '../' elements
1748 	 */
1749 	while (*p) {
1750 		if (p[0] == '/') {
1751 			p++;
1752 			len--;
1753 		} else if (p[0] != '.')
1754 			break;
1755 		else if (p[1] == '.' && p[2] == '/') {
1756 			p += 3;
1757 			len -= 3;
1758 		} else
1759 			break;
1760 	}
1761 	if (p != dirname) {
1762 		memmove(dirname, p, len+1);
1763 		p = dirname;
1764 	}
1765 	/*
1766 	 * Remove "/","/." and "/.." elements from tail.
1767 	 */
1768 	while (len > 0) {
1769 		size_t ll = len;
1770 
1771 		if (len > 0 && p[len-1] == '/') {
1772 			p[len-1] = '\0';
1773 			len--;
1774 		}
1775 		if (len > 1 && p[len-2] == '/' && p[len-1] == '.') {
1776 			p[len-2] = '\0';
1777 			len -= 2;
1778 		}
1779 		if (len > 2 && p[len-3] == '/' && p[len-2] == '.' &&
1780 		    p[len-1] == '.') {
1781 			p[len-3] = '\0';
1782 			len -= 3;
1783 		}
1784 		if (ll == len)
1785 			break;
1786 	}
1787 	while (*p) {
1788 		if (p[0] == '/') {
1789 			if (p[1] == '/')
1790 				/* Convert '//' --> '/' */
1791 				strcpy(p, p+1);
1792 			else if (p[1] == '.' && p[2] == '/')
1793 				/* Convert '/./' --> '/' */
1794 				strcpy(p, p+2);
1795 			else if (p[1] == '.' && p[2] == '.' && p[3] == '/') {
1796 				/* Convert 'dir/dir1/../dir2/'
1797 				 *     --> 'dir/dir2/'
1798 				 */
1799 				char *rp = p -1;
1800 				while (rp >= dirname) {
1801 					if (*rp == '/')
1802 						break;
1803 					--rp;
1804 				}
1805 				if (rp > dirname) {
1806 					strcpy(rp, p+3);
1807 					p = rp;
1808 				} else {
1809 					strcpy(dirname, p+4);
1810 					p = dirname;
1811 				}
1812 			} else
1813 				p++;
1814 		} else
1815 			p++;
1816 	}
1817 	p = dirname;
1818 	len = strlen(p);
1819 
1820 	/*
1821 	 * Add "./" prefiex.
1822 	 * NOTE: If the pathname does not have a path separator, we have
1823 	 * to add "./" to the head of the pathename because mtree reader
1824 	 * will suppose that it is v1(a.k.a classic) mtree format and
1825 	 * change the directory unexpectedly and so it will make a wrong
1826 	 * path.
1827 	 */
1828 	if (strcmp(p, ".") != 0 && strncmp(p, "./", 2) != 0) {
1829 		struct archive_string as;
1830 		archive_string_init(&as);
1831 		archive_strcpy(&as, "./");
1832 		archive_strncat(&as, p, len);
1833 		archive_string_empty(&file->parentdir);
1834 		archive_string_concat(&file->parentdir, &as);
1835 		archive_string_free(&as);
1836 		p = file->parentdir.s;
1837 		len = archive_strlen(&file->parentdir);
1838 	}
1839 
1840 	/*
1841 	 * Find out the position which points the last position of
1842 	 * path separator('/').
1843 	 */
1844 	slash = NULL;
1845 	for (; *p != '\0'; p++) {
1846 		if (*p == '/')
1847 			slash = p;
1848 	}
1849 	if (slash == NULL) {
1850 		/* The pathname doesn't have a parent directory. */
1851 		file->parentdir.length = len;
1852 		archive_string_copy(&(file->basename), &(file->parentdir));
1853 		archive_string_empty(&(file->parentdir));
1854 		*file->parentdir.s = '\0';
1855 		return (ret);
1856 	}
1857 
1858 	/* Make a basename from dirname and slash */
1859 	*slash  = '\0';
1860 	file->parentdir.length = slash - dirname;
1861 	archive_strcpy(&(file->basename),  slash + 1);
1862 	return (ret);
1863 }
1864 
1865 static int
1866 mtree_entry_create_virtual_dir(struct archive_write *a, const char *pathname,
1867     struct mtree_entry **m_entry)
1868 {
1869 	struct archive_entry *entry;
1870 	struct mtree_entry *file;
1871 	int r;
1872 
1873 	entry = archive_entry_new();
1874 	if (entry == NULL) {
1875 		*m_entry = NULL;
1876 		archive_set_error(&a->archive, ENOMEM,
1877 		    "Can't allocate memory");
1878 		return (ARCHIVE_FATAL);
1879 	}
1880 	archive_entry_copy_pathname(entry, pathname);
1881 	archive_entry_set_mode(entry, AE_IFDIR | 0755);
1882 	archive_entry_set_mtime(entry, time(NULL), 0);
1883 
1884 	r = mtree_entry_new(a, entry, &file);
1885 	archive_entry_free(entry);
1886 	if (r < ARCHIVE_WARN) {
1887 		*m_entry = NULL;
1888 		archive_set_error(&a->archive, ENOMEM,
1889 		    "Can't allocate memory");
1890 		return (ARCHIVE_FATAL);
1891 	}
1892 
1893 	file->dir_info->virtual = 1;
1894 
1895 	*m_entry = file;
1896 	return (ARCHIVE_OK);
1897 }
1898 
1899 static void
1900 mtree_entry_register_add(struct mtree_writer *mtree, struct mtree_entry *file)
1901 {
1902         file->next = NULL;
1903         *mtree->file_list.last = file;
1904         mtree->file_list.last = &(file->next);
1905 }
1906 
1907 static void
1908 mtree_entry_register_init(struct mtree_writer *mtree)
1909 {
1910 	mtree->file_list.first = NULL;
1911 	mtree->file_list.last = &(mtree->file_list.first);
1912 }
1913 
1914 static void
1915 mtree_entry_register_free(struct mtree_writer *mtree)
1916 {
1917 	struct mtree_entry *file, *file_next;
1918 
1919 	file = mtree->file_list.first;
1920 	while (file != NULL) {
1921 		file_next = file->next;
1922 		mtree_entry_free(file);
1923 		file = file_next;
1924 	}
1925 }
1926 
1927 static int
1928 mtree_entry_add_child_tail(struct mtree_entry *parent,
1929     struct mtree_entry *child)
1930 {
1931 	child->dir_info->chnext = NULL;
1932 	*parent->dir_info->children.last = child;
1933 	parent->dir_info->children.last = &(child->dir_info->chnext);
1934 	return (1);
1935 }
1936 
1937 /*
1938  * Find a entry from a parent entry with the name.
1939  */
1940 static struct mtree_entry *
1941 mtree_entry_find_child(struct mtree_entry *parent, const char *child_name)
1942 {
1943 	struct mtree_entry *np;
1944 
1945 	if (parent == NULL)
1946 		return (NULL);
1947 	np = (struct mtree_entry *)__archive_rb_tree_find_node(
1948 	    &(parent->dir_info->rbtree), child_name);
1949 	return (np);
1950 }
1951 
1952 static int
1953 get_path_component(char *name, size_t n, const char *fn)
1954 {
1955 	char *p;
1956 	size_t l;
1957 
1958 	p = strchr(fn, '/');
1959 	if (p == NULL) {
1960 		if ((l = strlen(fn)) == 0)
1961 			return (0);
1962 	} else
1963 		l = p - fn;
1964 	if (l > n -1)
1965 		return (-1);
1966 	memcpy(name, fn, l);
1967 	name[l] = '\0';
1968 
1969 	return ((int)l);
1970 }
1971 
1972 /*
1973  * Add a new entry into the tree.
1974  */
1975 static int
1976 mtree_entry_tree_add(struct archive_write *a, struct mtree_entry **filep)
1977 {
1978 #if defined(_WIN32) && !defined(__CYGWIN__)
1979 	char name[_MAX_FNAME];/* Included null terminator size. */
1980 #elif defined(NAME_MAX) && NAME_MAX >= 255
1981 	char name[NAME_MAX+1];
1982 #else
1983 	char name[256];
1984 #endif
1985 	struct mtree_writer *mtree = (struct mtree_writer *)a->format_data;
1986 	struct mtree_entry *dent, *file, *np;
1987 	const char *fn, *p;
1988 	int l, r;
1989 
1990 	file = *filep;
1991 	if (file->parentdir.length == 0 && file->basename.length == 1 &&
1992 	    file->basename.s[0] == '.') {
1993 		file->parent = file;
1994 		if (mtree->root != NULL) {
1995 			np = mtree->root;
1996 			goto same_entry;
1997 		}
1998 		mtree->root = file;
1999 		mtree_entry_register_add(mtree, file);
2000 		return (ARCHIVE_OK);
2001 	}
2002 
2003 	if (file->parentdir.length == 0) {
2004 		archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
2005 		    "Internal programing error "
2006 		    "in generating canonical name for %s",
2007 		    file->pathname.s);
2008 		return (ARCHIVE_FAILED);
2009 	}
2010 
2011 	fn = p = file->parentdir.s;
2012 
2013 	/*
2014 	 * If the path of the parent directory of `file' entry is
2015 	 * the same as the path of `cur_dirent', add `file' entry to
2016 	 * `cur_dirent'.
2017 	 */
2018 	if (archive_strlen(&(mtree->cur_dirstr))
2019 	      == archive_strlen(&(file->parentdir)) &&
2020 	    strcmp(mtree->cur_dirstr.s, fn) == 0) {
2021 		if (!__archive_rb_tree_insert_node(
2022 		    &(mtree->cur_dirent->dir_info->rbtree),
2023 		    (struct archive_rb_node *)file)) {
2024 			/* There is the same name in the tree. */
2025 			np = (struct mtree_entry *)__archive_rb_tree_find_node(
2026 			    &(mtree->cur_dirent->dir_info->rbtree),
2027 			    file->basename.s);
2028 			goto same_entry;
2029 		}
2030 		file->parent = mtree->cur_dirent;
2031 		mtree_entry_register_add(mtree, file);
2032 		return (ARCHIVE_OK);
2033 	}
2034 
2035 	dent = mtree->root;
2036 	for (;;) {
2037 		l = get_path_component(name, sizeof(name), fn);
2038 		if (l == 0) {
2039 			np = NULL;
2040 			break;
2041 		}
2042 		if (l < 0) {
2043 			archive_set_error(&a->archive,
2044 			    ARCHIVE_ERRNO_MISC,
2045 			    "A name buffer is too small");
2046 			return (ARCHIVE_FATAL);
2047 		}
2048 		if (l == 1 && name[0] == '.' && dent != NULL &&
2049 		    dent == mtree->root) {
2050 			fn += l;
2051 			if (fn[0] == '/')
2052 				fn++;
2053 			continue;
2054 		}
2055 
2056 		np = mtree_entry_find_child(dent, name);
2057 		if (np == NULL || fn[0] == '\0')
2058 			break;
2059 
2060 		/* Find next sub directory. */
2061 		if (!np->dir_info) {
2062 			/* NOT Directory! */
2063 			archive_set_error(&a->archive,
2064 			    ARCHIVE_ERRNO_MISC,
2065 			    "`%s' is not directory, we cannot insert `%s' ",
2066 			    np->pathname.s, file->pathname.s);
2067 			return (ARCHIVE_FAILED);
2068 		}
2069 		fn += l;
2070 		if (fn[0] == '/')
2071 			fn++;
2072 		dent = np;
2073 	}
2074 	if (np == NULL) {
2075 		/*
2076 		 * Create virtual parent directories.
2077 		 */
2078 		while (fn[0] != '\0') {
2079 			struct mtree_entry *vp;
2080 			struct archive_string as;
2081 
2082 			archive_string_init(&as);
2083 			archive_strncat(&as, p, fn - p + l);
2084 			if (as.s[as.length-1] == '/') {
2085 				as.s[as.length-1] = '\0';
2086 				as.length--;
2087 			}
2088 			r = mtree_entry_create_virtual_dir(a, as.s, &vp);
2089 			archive_string_free(&as);
2090 			if (r < ARCHIVE_WARN)
2091 				return (r);
2092 
2093 			if (strcmp(vp->pathname.s, ".") == 0) {
2094 				vp->parent = vp;
2095 				mtree->root = vp;
2096 			} else {
2097 				__archive_rb_tree_insert_node(
2098 				    &(dent->dir_info->rbtree),
2099 				    (struct archive_rb_node *)vp);
2100 				vp->parent = dent;
2101 			}
2102 			mtree_entry_register_add(mtree, vp);
2103 			np = vp;
2104 
2105 			fn += l;
2106 			if (fn[0] == '/')
2107 				fn++;
2108 			l = get_path_component(name, sizeof(name), fn);
2109 			if (l < 0) {
2110 				archive_string_free(&as);
2111 				archive_set_error(&a->archive,
2112 				    ARCHIVE_ERRNO_MISC,
2113 				    "A name buffer is too small");
2114 				return (ARCHIVE_FATAL);
2115 			}
2116 			dent = np;
2117 		}
2118 
2119 		/* Found out the parent directory where `file' can be
2120 		 * inserted. */
2121 		mtree->cur_dirent = dent;
2122 		archive_string_empty(&(mtree->cur_dirstr));
2123 		archive_string_ensure(&(mtree->cur_dirstr),
2124 		    archive_strlen(&(dent->parentdir)) +
2125 		    archive_strlen(&(dent->basename)) + 2);
2126 		if (archive_strlen(&(dent->parentdir)) +
2127 		    archive_strlen(&(dent->basename)) == 0)
2128 			mtree->cur_dirstr.s[0] = 0;
2129 		else {
2130 			if (archive_strlen(&(dent->parentdir)) > 0) {
2131 				archive_string_copy(&(mtree->cur_dirstr),
2132 				    &(dent->parentdir));
2133 				archive_strappend_char(
2134 				    &(mtree->cur_dirstr), '/');
2135 			}
2136 			archive_string_concat(&(mtree->cur_dirstr),
2137 			    &(dent->basename));
2138 		}
2139 
2140 		if (!__archive_rb_tree_insert_node(
2141 		    &(dent->dir_info->rbtree),
2142 		    (struct archive_rb_node *)file)) {
2143 			np = (struct mtree_entry *)__archive_rb_tree_find_node(
2144 			    &(dent->dir_info->rbtree), file->basename.s);
2145 			goto same_entry;
2146 		}
2147 		file->parent = dent;
2148 		mtree_entry_register_add(mtree, file);
2149 		return (ARCHIVE_OK);
2150 	}
2151 
2152 same_entry:
2153 	/*
2154 	 * We have already has the entry the filename of which is
2155 	 * the same.
2156 	 */
2157 	r = mtree_entry_exchange_same_entry(a, np, file);
2158 	if (r < ARCHIVE_WARN)
2159 		return (r);
2160 	if (np->dir_info)
2161 		np->dir_info->virtual = 0;
2162 	*filep = np;
2163 	mtree_entry_free(file);
2164 	return (ARCHIVE_WARN);
2165 }
2166 
2167 static int
2168 mtree_entry_exchange_same_entry(struct archive_write *a, struct mtree_entry *np,
2169     struct mtree_entry *file)
2170 {
2171 
2172 	if ((np->mode & AE_IFMT) != (file->mode & AE_IFMT)) {
2173 		archive_set_error(&a->archive, ARCHIVE_ERRNO_MISC,
2174 		    "Found duplicate entries `%s' and its file type is "
2175 		    "different",
2176 		    np->pathname.s);
2177 		return (ARCHIVE_FAILED);
2178 	}
2179 
2180 	/* Update the existent mtree entry's attributes by the new one's. */
2181 	archive_string_empty(&np->symlink);
2182 	archive_string_concat(&np->symlink, &file->symlink);
2183 	archive_string_empty(&np->uname);
2184 	archive_string_concat(&np->uname, &file->uname);
2185 	archive_string_empty(&np->gname);
2186 	archive_string_concat(&np->gname, &file->gname);
2187 	archive_string_empty(&np->fflags_text);
2188 	archive_string_concat(&np->fflags_text, &file->fflags_text);
2189 	np->nlink = file->nlink;
2190 	np->filetype = file->filetype;
2191 	np->mode = file->mode;
2192 	np->size = file->size;
2193 	np->uid = file->uid;
2194 	np->gid = file->gid;
2195 	np->fflags_set = file->fflags_set;
2196 	np->fflags_clear = file->fflags_clear;
2197 	np->mtime = file->mtime;
2198 	np->mtime_nsec = file->mtime_nsec;
2199 	np->rdevmajor = file->rdevmajor;
2200 	np->rdevminor = file->rdevminor;
2201 
2202 	return (ARCHIVE_WARN);
2203 }
2204