indent -kr -i8
[rsync/rsync.git] / flist.c
1 /* 
2    Copyright (C) Andrew Tridgell 1996
3    Copyright (C) Paul Mackerras 1996
4    Copyright (C) 2001, 2002 by Martin Pool <mbp@samba.org>
5    
6    This program is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 2 of the License, or
9    (at your option) any later version.
10    
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15    
16    You should have received a copy of the GNU General Public License
17    along with this program; if not, write to the Free Software
18    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21 /** @file flist.c
22  * Generate and receive file lists
23  *
24  * @todo Get rid of the string_area optimization.  Efficiently
25  * allocating blocks is the responsibility of the system's malloc
26  * library, not of rsync.
27  *
28  * @sa http://lists.samba.org/pipermail/rsync/2000-June/002351.html
29  *
30  **/
31
32 #include "rsync.h"
33
34 extern struct stats stats;
35
36 extern int verbose;
37 extern int am_server;
38 extern int always_checksum;
39
40 extern int cvs_exclude;
41
42 extern int recurse;
43
44 extern int one_file_system;
45 extern int make_backups;
46 extern int preserve_links;
47 extern int preserve_hard_links;
48 extern int preserve_perms;
49 extern int preserve_devices;
50 extern int preserve_uid;
51 extern int preserve_gid;
52 extern int preserve_times;
53 extern int relative_paths;
54 extern int copy_links;
55 extern int copy_unsafe_links;
56 extern int remote_version;
57 extern int io_error;
58 extern int sanitize_paths;
59
60 extern int read_batch;
61 extern int write_batch;
62
63 static char topsrcname[MAXPATHLEN];
64
65 static struct exclude_struct **local_exclude_list;
66
67 static struct file_struct null_file;
68
69 static void clean_flist(struct file_list *flist, int strip_root);
70
71
72 static int show_build_progress_p(void)
73 {
74         extern int do_progress;
75
76         return do_progress && verbose && recurse && !am_server;
77 }
78
79 /**
80  * True if we're local, etc, and should emit progress emssages.
81  **/
82 static void emit_build_progress(const struct file_list *flist)
83 {
84         rprintf(FINFO, " %d files...\r", flist->count);
85 }
86
87
88 static void finish_build_progress(const struct file_list *flist)
89 {
90         if (verbose && recurse && !am_server) {
91                 /* This overwrites the progress line, if any. */
92                 rprintf(FINFO, RSYNC_NAME ": %d files to consider.\n",
93                         flist->count);
94         }
95 }
96
97
98 static struct string_area *string_area_new(int size)
99 {
100         struct string_area *a;
101
102         if (size <= 0)
103                 size = ARENA_SIZE;
104         a = malloc(sizeof(*a));
105         if (!a)
106                 out_of_memory("string_area_new");
107         a->current = a->base = malloc(size);
108         if (!a->current)
109                 out_of_memory("string_area_new buffer");
110         a->end = a->base + size;
111         a->next = NULL;
112
113         return a;
114 }
115
116 static void string_area_free(struct string_area *a)
117 {
118         struct string_area *next;
119
120         for (; a; a = next) {
121                 next = a->next;
122                 free(a->base);
123         }
124 }
125
126 static char *string_area_malloc(struct string_area **ap, int size)
127 {
128         char *p;
129         struct string_area *a;
130
131         /* does the request fit into the current space? */
132         a = *ap;
133         if (a->current + size >= a->end) {
134                 /* no; get space, move new string_area to front of the list */
135                 a = string_area_new(size > ARENA_SIZE ? size : ARENA_SIZE);
136                 a->next = *ap;
137                 *ap = a;
138         }
139
140         /* have space; do the "allocation." */
141         p = a->current;
142         a->current += size;
143         return p;
144 }
145
146 static char *string_area_strdup(struct string_area **ap, const char *src)
147 {
148         char *dest = string_area_malloc(ap, strlen(src) + 1);
149         return strcpy(dest, src);
150 }
151
152 static void list_file_entry(struct file_struct *f)
153 {
154         char perms[11];
155
156         if (!f->basename)
157                 /* this can happen if duplicate names were removed */
158                 return;
159
160         permstring(perms, f->mode);
161
162         if (preserve_links && S_ISLNK(f->mode)) {
163                 rprintf(FINFO, "%s %11.0f %s %s -> %s\n",
164                         perms,
165                         (double) f->length, timestring(f->modtime),
166                         f_name(f), f->link);
167         } else {
168                 rprintf(FINFO, "%s %11.0f %s %s\n",
169                         perms,
170                         (double) f->length, timestring(f->modtime),
171                         f_name(f));
172         }
173 }
174
175
176 int readlink_stat(const char *Path, STRUCT_STAT * Buffer, char *Linkbuf)
177 {
178 #if SUPPORT_LINKS
179         if (copy_links) {
180                 return do_stat(Path, Buffer);
181         }
182         if (do_lstat(Path, Buffer) == -1) {
183                 return -1;
184         }
185         if (S_ISLNK(Buffer->st_mode)) {
186                 int l;
187                 if ((l =
188                      readlink((char *) Path, Linkbuf,
189                               MAXPATHLEN - 1)) == -1) {
190                         return -1;
191                 }
192                 Linkbuf[l] = 0;
193                 if (copy_unsafe_links && (topsrcname[0] != '\0') &&
194                     unsafe_symlink(Linkbuf, topsrcname)) {
195                         return do_stat(Path, Buffer);
196                 }
197         }
198         return 0;
199 #else
200         return do_stat(Path, Buffer);
201 #endif
202 }
203
204 int link_stat(const char *Path, STRUCT_STAT * Buffer)
205 {
206 #if SUPPORT_LINKS
207         if (copy_links) {
208                 return do_stat(Path, Buffer);
209         } else {
210                 return do_lstat(Path, Buffer);
211         }
212 #else
213         return do_stat(Path, Buffer);
214 #endif
215 }
216
217 /*
218   This function is used to check if a file should be included/excluded
219   from the list of files based on its name and type etc
220  */
221 static int check_exclude_file(int f, char *fname, STRUCT_STAT * st)
222 {
223         extern int delete_excluded;
224
225         /* f is set to -1 when calculating deletion file list */
226         if ((f == -1) && delete_excluded) {
227                 return 0;
228         }
229         if (check_exclude(fname, local_exclude_list, st)) {
230                 return 1;
231         }
232         return 0;
233 }
234
235 /* used by the one_file_system code */
236 static dev_t filesystem_dev;
237
238 static void set_filesystem(char *fname)
239 {
240         STRUCT_STAT st;
241         if (link_stat(fname, &st) != 0)
242                 return;
243         filesystem_dev = st.st_dev;
244 }
245
246
247 static int to_wire_mode(mode_t mode)
248 {
249         if (S_ISLNK(mode) && (_S_IFLNK != 0120000)) {
250                 return (mode & ~(_S_IFMT)) | 0120000;
251         }
252         return (int) mode;
253 }
254
255 static mode_t from_wire_mode(int mode)
256 {
257         if ((mode & (_S_IFMT)) == 0120000 && (_S_IFLNK != 0120000)) {
258                 return (mode & ~(_S_IFMT)) | _S_IFLNK;
259         }
260         return (mode_t) mode;
261 }
262
263
264 static void send_directory(int f, struct file_list *flist, char *dir);
265
266 static char *flist_dir;
267
268
269 static void send_file_entry(struct file_struct *file, int f,
270                             unsigned base_flags)
271 {
272         unsigned char flags;
273         static time_t last_time;
274         static mode_t last_mode;
275         static dev_t last_rdev;
276         static uid_t last_uid;
277         static gid_t last_gid;
278         static char lastname[MAXPATHLEN];
279         char *fname;
280         int l1, l2;
281
282         if (f == -1)
283                 return;
284
285         if (!file) {
286                 write_byte(f, 0);
287                 return;
288         }
289
290         fname = f_name(file);
291
292         flags = base_flags;
293
294         if (file->mode == last_mode)
295                 flags |= SAME_MODE;
296         if (file->rdev == last_rdev)
297                 flags |= SAME_RDEV;
298         if (file->uid == last_uid)
299                 flags |= SAME_UID;
300         if (file->gid == last_gid)
301                 flags |= SAME_GID;
302         if (file->modtime == last_time)
303                 flags |= SAME_TIME;
304
305         for (l1 = 0;
306              lastname[l1] && (fname[l1] == lastname[l1]) && (l1 < 255);
307              l1++);
308         l2 = strlen(fname) - l1;
309
310         if (l1 > 0)
311                 flags |= SAME_NAME;
312         if (l2 > 255)
313                 flags |= LONG_NAME;
314
315         /* we must make sure we don't send a zero flags byte or the other
316            end will terminate the flist transfer */
317         if (flags == 0 && !S_ISDIR(file->mode))
318                 flags |= FLAG_DELETE;
319         if (flags == 0)
320                 flags |= LONG_NAME;
321
322         write_byte(f, flags);
323         if (flags & SAME_NAME)
324                 write_byte(f, l1);
325         if (flags & LONG_NAME)
326                 write_int(f, l2);
327         else
328                 write_byte(f, l2);
329         write_buf(f, fname + l1, l2);
330
331         write_longint(f, file->length);
332         if (!(flags & SAME_TIME))
333                 write_int(f, (int) file->modtime);
334         if (!(flags & SAME_MODE))
335                 write_int(f, to_wire_mode(file->mode));
336         if (preserve_uid && !(flags & SAME_UID)) {
337                 add_uid(file->uid);
338                 write_int(f, (int) file->uid);
339         }
340         if (preserve_gid && !(flags & SAME_GID)) {
341                 add_gid(file->gid);
342                 write_int(f, (int) file->gid);
343         }
344         if (preserve_devices && IS_DEVICE(file->mode)
345             && !(flags & SAME_RDEV))
346                 write_int(f, (int) file->rdev);
347
348 #if SUPPORT_LINKS
349         if (preserve_links && S_ISLNK(file->mode)) {
350                 write_int(f, strlen(file->link));
351                 write_buf(f, file->link, strlen(file->link));
352         }
353 #endif
354
355 #if SUPPORT_HARD_LINKS
356         if (preserve_hard_links && S_ISREG(file->mode)) {
357                 if (remote_version < 26) {
358                         /* 32-bit dev_t and ino_t */
359                         write_int(f, (int) file->dev);
360                         write_int(f, (int) file->inode);
361                 } else {
362                         /* 64-bit dev_t and ino_t */
363                         write_longint(f, file->dev);
364                         write_longint(f, file->inode);
365                 }
366         }
367 #endif
368
369         if (always_checksum) {
370                 if (remote_version < 21) {
371                         write_buf(f, file->sum, 2);
372                 } else {
373                         write_buf(f, file->sum, MD4_SUM_LENGTH);
374                 }
375         }
376
377         last_mode = file->mode;
378         last_rdev = file->rdev;
379         last_uid = file->uid;
380         last_gid = file->gid;
381         last_time = file->modtime;
382
383         strlcpy(lastname, fname, MAXPATHLEN);
384         lastname[MAXPATHLEN - 1] = 0;
385 }
386
387
388
389 static void receive_file_entry(struct file_struct **fptr,
390                                unsigned flags, int f)
391 {
392         static time_t last_time;
393         static mode_t last_mode;
394         static dev_t last_rdev;
395         static uid_t last_uid;
396         static gid_t last_gid;
397         static char lastname[MAXPATHLEN];
398         char thisname[MAXPATHLEN];
399         unsigned int l1 = 0, l2 = 0;
400         char *p;
401         struct file_struct *file;
402
403         if (flags & SAME_NAME)
404                 l1 = read_byte(f);
405
406         if (flags & LONG_NAME)
407                 l2 = read_int(f);
408         else
409                 l2 = read_byte(f);
410
411         file = (struct file_struct *) malloc(sizeof(*file));
412         if (!file)
413                 out_of_memory("receive_file_entry");
414         memset((char *) file, 0, sizeof(*file));
415         (*fptr) = file;
416
417         if (l2 >= MAXPATHLEN - l1) {
418                 rprintf(FERROR,
419                         "overflow: flags=0x%x l1=%d l2=%d lastname=%s\n",
420                         flags, l1, l2, lastname);
421                 overflow("receive_file_entry");
422         }
423
424         strlcpy(thisname, lastname, l1 + 1);
425         read_sbuf(f, &thisname[l1], l2);
426         thisname[l1 + l2] = 0;
427
428         strlcpy(lastname, thisname, MAXPATHLEN);
429         lastname[MAXPATHLEN - 1] = 0;
430
431         clean_fname(thisname);
432
433         if (sanitize_paths) {
434                 sanitize_path(thisname, NULL);
435         }
436
437         if ((p = strrchr(thisname, '/'))) {
438                 static char *lastdir;
439                 *p = 0;
440                 if (lastdir && strcmp(thisname, lastdir) == 0) {
441                         file->dirname = lastdir;
442                 } else {
443                         file->dirname = strdup(thisname);
444                         lastdir = file->dirname;
445                 }
446                 file->basename = strdup(p + 1);
447         } else {
448                 file->dirname = NULL;
449                 file->basename = strdup(thisname);
450         }
451
452         if (!file->basename)
453                 out_of_memory("receive_file_entry 1");
454
455
456         file->flags = flags;
457         file->length = read_longint(f);
458         file->modtime =
459             (flags & SAME_TIME) ? last_time : (time_t) read_int(f);
460         file->mode =
461             (flags & SAME_MODE) ? last_mode : from_wire_mode(read_int(f));
462         if (preserve_uid)
463                 file->uid =
464                     (flags & SAME_UID) ? last_uid : (uid_t) read_int(f);
465         if (preserve_gid)
466                 file->gid =
467                     (flags & SAME_GID) ? last_gid : (gid_t) read_int(f);
468         if (preserve_devices && IS_DEVICE(file->mode))
469                 file->rdev =
470                     (flags & SAME_RDEV) ? last_rdev : (dev_t) read_int(f);
471
472         if (preserve_links && S_ISLNK(file->mode)) {
473                 int l = read_int(f);
474                 if (l < 0) {
475                         rprintf(FERROR, "overflow: l=%d\n", l);
476                         overflow("receive_file_entry");
477                 }
478                 file->link = (char *) malloc(l + 1);
479                 if (!file->link)
480                         out_of_memory("receive_file_entry 2");
481                 read_sbuf(f, file->link, l);
482                 if (sanitize_paths) {
483                         sanitize_path(file->link, file->dirname);
484                 }
485         }
486 #if SUPPORT_HARD_LINKS
487         if (preserve_hard_links && S_ISREG(file->mode)) {
488                 if (remote_version < 26) {
489                         file->dev = read_int(f);
490                         file->inode = read_int(f);
491                 } else {
492                         file->dev = read_longint(f);
493                         file->inode = read_longint(f);
494                 }
495         }
496 #endif
497
498         if (always_checksum) {
499                 file->sum = (char *) malloc(MD4_SUM_LENGTH);
500                 if (!file->sum)
501                         out_of_memory("md4 sum");
502                 if (remote_version < 21) {
503                         read_buf(f, file->sum, 2);
504                 } else {
505                         read_buf(f, file->sum, MD4_SUM_LENGTH);
506                 }
507         }
508
509         last_mode = file->mode;
510         last_rdev = file->rdev;
511         last_uid = file->uid;
512         last_gid = file->gid;
513         last_time = file->modtime;
514
515         if (!preserve_perms) {
516                 extern int orig_umask;
517                 /* set an appropriate set of permissions based on original
518                    permissions and umask. This emulates what GNU cp does */
519                 file->mode &= ~orig_umask;
520         }
521 }
522
523
524 /* determine if a file in a different filesstem should be skipped
525    when one_file_system is set. We bascally only want to include
526    the mount points - but they can be hard to find! */
527 static int skip_filesystem(char *fname, STRUCT_STAT * st)
528 {
529         STRUCT_STAT st2;
530         char *p = strrchr(fname, '/');
531
532         /* skip all but directories */
533         if (!S_ISDIR(st->st_mode))
534                 return 1;
535
536         /* if its not a subdirectory then allow */
537         if (!p)
538                 return 0;
539
540         *p = 0;
541         if (link_stat(fname, &st2)) {
542                 *p = '/';
543                 return 0;
544         }
545         *p = '/';
546
547         return (st2.st_dev != filesystem_dev);
548 }
549
550 #define STRDUP(ap, p)   (ap ? string_area_strdup(ap, p) : strdup(p))
551 /* IRIX cc cares that the operands to the ternary have the same type. */
552 #define MALLOC(ap, i)   (ap ? (void*) string_area_malloc(ap, i) : malloc(i))
553
554 /* create a file_struct for a named file */
555 struct file_struct *make_file(int f, char *fname, struct string_area **ap,
556                               int noexcludes)
557 {
558         struct file_struct *file;
559         STRUCT_STAT st;
560         char sum[SUM_LENGTH];
561         char *p;
562         char cleaned_name[MAXPATHLEN];
563         char linkbuf[MAXPATHLEN];
564         extern int module_id;
565
566         strlcpy(cleaned_name, fname, MAXPATHLEN);
567         cleaned_name[MAXPATHLEN - 1] = 0;
568         clean_fname(cleaned_name);
569         if (sanitize_paths) {
570                 sanitize_path(cleaned_name, NULL);
571         }
572         fname = cleaned_name;
573
574         memset(sum, 0, SUM_LENGTH);
575
576         if (readlink_stat(fname, &st, linkbuf) != 0) {
577                 int save_errno = errno;
578                 if ((errno == ENOENT) && copy_links && !noexcludes) {
579                         /* symlink pointing nowhere, see if excluded */
580                         memset((char *) &st, 0, sizeof(st));
581                         if (check_exclude_file(f, fname, &st)) {
582                                 /* file is excluded anyway, ignore silently */
583                                 return NULL;
584                         }
585                 }
586                 io_error = 1;
587                 rprintf(FERROR, "readlink %s: %s\n",
588                         fname, strerror(save_errno));
589                 return NULL;
590         }
591
592         /* we use noexcludes from backup.c */
593         if (noexcludes)
594                 goto skip_excludes;
595
596         if (S_ISDIR(st.st_mode) && !recurse) {
597                 rprintf(FINFO, "skipping directory %s\n", fname);
598                 return NULL;
599         }
600
601         if (one_file_system && st.st_dev != filesystem_dev) {
602                 if (skip_filesystem(fname, &st))
603                         return NULL;
604         }
605
606         if (check_exclude_file(f, fname, &st))
607                 return NULL;
608
609
610         if (lp_ignore_nonreadable(module_id) && access(fname, R_OK) != 0)
611                 return NULL;
612
613       skip_excludes:
614
615         if (verbose > 2)
616                 rprintf(FINFO, "make_file(%d,%s)\n", f, fname);
617
618         file = (struct file_struct *) malloc(sizeof(*file));
619         if (!file)
620                 out_of_memory("make_file");
621         memset((char *) file, 0, sizeof(*file));
622
623         if ((p = strrchr(fname, '/'))) {
624                 static char *lastdir;
625                 *p = 0;
626                 if (lastdir && strcmp(fname, lastdir) == 0) {
627                         file->dirname = lastdir;
628                 } else {
629                         file->dirname = strdup(fname);
630                         lastdir = file->dirname;
631                 }
632                 file->basename = STRDUP(ap, p + 1);
633                 *p = '/';
634         } else {
635                 file->dirname = NULL;
636                 file->basename = STRDUP(ap, fname);
637         }
638
639         file->modtime = st.st_mtime;
640         file->length = st.st_size;
641         file->mode = st.st_mode;
642         file->uid = st.st_uid;
643         file->gid = st.st_gid;
644         file->dev = st.st_dev;
645         file->inode = st.st_ino;
646 #ifdef HAVE_ST_RDEV
647         file->rdev = st.st_rdev;
648 #endif
649
650 #if SUPPORT_LINKS
651         if (S_ISLNK(st.st_mode)) {
652                 file->link = STRDUP(ap, linkbuf);
653         }
654 #endif
655
656         if (always_checksum) {
657                 file->sum = (char *) MALLOC(ap, MD4_SUM_LENGTH);
658                 if (!file->sum)
659                         out_of_memory("md4 sum");
660                 /* drat. we have to provide a null checksum for non-regular
661                    files in order to be compatible with earlier versions
662                    of rsync */
663                 if (S_ISREG(st.st_mode)) {
664                         file_checksum(fname, file->sum, st.st_size);
665                 } else {
666                         memset(file->sum, 0, MD4_SUM_LENGTH);
667                 }
668         }
669
670         if (flist_dir) {
671                 static char *lastdir;
672                 if (lastdir && strcmp(lastdir, flist_dir) == 0) {
673                         file->basedir = lastdir;
674                 } else {
675                         file->basedir = strdup(flist_dir);
676                         lastdir = file->basedir;
677                 }
678         } else {
679                 file->basedir = NULL;
680         }
681
682         if (!S_ISDIR(st.st_mode))
683                 stats.total_size += st.st_size;
684
685         return file;
686 }
687
688
689
690 void send_file_name(int f, struct file_list *flist, char *fname,
691                     int recursive, unsigned base_flags)
692 {
693         struct file_struct *file;
694
695         file = make_file(f, fname, &flist->string_area, 0);
696
697         if (!file)
698                 return;
699
700         if (show_build_progress_p() & !(flist->count % 100))
701                 emit_build_progress(flist);
702
703         if (flist->count >= flist->malloced) {
704                 if (flist->malloced < 1000)
705                         flist->malloced += 1000;
706                 else
707                         flist->malloced *= 2;
708                 flist->files =
709                     (struct file_struct **) realloc(flist->files,
710                                                     sizeof(flist->
711                                                            files[0]) *
712                                                     flist->malloced);
713                 if (!flist->files)
714                         out_of_memory("send_file_name");
715         }
716
717         if (write_batch)        /*  dw  */
718                 file->flags = FLAG_DELETE;
719
720         if (strcmp(file->basename, "")) {
721                 flist->files[flist->count++] = file;
722                 send_file_entry(file, f, base_flags);
723         }
724
725         if (S_ISDIR(file->mode) && recursive) {
726                 struct exclude_struct **last_exclude_list =
727                     local_exclude_list;
728                 send_directory(f, flist, f_name(file));
729                 local_exclude_list = last_exclude_list;
730                 return;
731         }
732 }
733
734
735
736 static void send_directory(int f, struct file_list *flist, char *dir)
737 {
738         DIR *d;
739         struct dirent *di;
740         char fname[MAXPATHLEN];
741         int l;
742         char *p;
743
744         d = opendir(dir);
745         if (!d) {
746                 io_error = 1;
747                 rprintf(FERROR, "opendir(%s): %s\n", dir, strerror(errno));
748                 return;
749         }
750
751         strlcpy(fname, dir, MAXPATHLEN);
752         l = strlen(fname);
753         if (fname[l - 1] != '/') {
754                 if (l == MAXPATHLEN - 1) {
755                         io_error = 1;
756                         rprintf(FERROR,
757                                 "skipping long-named directory %s\n",
758                                 fname);
759                         closedir(d);
760                         return;
761                 }
762                 strlcat(fname, "/", MAXPATHLEN);
763                 l++;
764         }
765         p = fname + strlen(fname);
766
767         local_exclude_list = NULL;
768
769         if (cvs_exclude) {
770                 if (strlen(fname) + strlen(".cvsignore") <= MAXPATHLEN - 1) {
771                         strcpy(p, ".cvsignore");
772                         local_exclude_list =
773                             make_exclude_list(fname, NULL, 0, 0);
774                 } else {
775                         io_error = 1;
776                         rprintf(FINFO,
777                                 "cannot cvs-exclude in long-named directory %s\n",
778                                 fname);
779                 }
780         }
781
782         for (di = readdir(d); di; di = readdir(d)) {
783                 char *dname = d_name(di);
784                 if (strcmp(dname, ".") == 0 || strcmp(dname, "..") == 0)
785                         continue;
786                 strlcpy(p, dname, MAXPATHLEN - l);
787                 send_file_name(f, flist, fname, recurse, 0);
788         }
789
790         if (local_exclude_list) {
791                 add_exclude_list("!", &local_exclude_list, 0);
792         }
793
794         closedir(d);
795 }
796
797
798 /*
799  *
800  * I *think* f==-1 means that the list should just be built in memory
801  * and not transmitted.  But who can tell? -- mbp
802  */
803 struct file_list *send_file_list(int f, int argc, char *argv[])
804 {
805         int i, l;
806         STRUCT_STAT st;
807         char *p, *dir, *olddir;
808         char lastpath[MAXPATHLEN] = "";
809         struct file_list *flist;
810         int64 start_write;
811
812         if (verbose && recurse && !am_server && f != -1) {
813                 rprintf(FINFO, RSYNC_NAME ": building file list...\n");
814                 if (verbose > 1)
815                         rprintf(FINFO, "\n");
816                 rflush(FINFO);
817         }
818
819         start_write = stats.total_written;
820
821         flist = flist_new();
822
823         if (f != -1) {
824                 io_start_buffering(f);
825         }
826
827         for (i = 0; i < argc; i++) {
828                 char *fname = topsrcname;
829
830                 strlcpy(fname, argv[i], MAXPATHLEN);
831
832                 l = strlen(fname);
833                 if (l != 1 && fname[l - 1] == '/') {
834                         if ((l == 2) && (fname[0] == '.')) {
835                                 /*  Turn ./ into just . rather than ./.
836                                    This was put in to avoid a problem with
837                                    rsync -aR --delete from ./
838                                    The send_file_name() below of ./ was
839                                    mysteriously preventing deletes */
840                                 fname[1] = 0;
841                         } else {
842                                 strlcat(fname, ".", MAXPATHLEN);
843                         }
844                 }
845
846                 if (link_stat(fname, &st) != 0) {
847                         if (f != -1) {
848                                 io_error = 1;
849                                 rprintf(FERROR, "link_stat %s : %s\n",
850                                         fname, strerror(errno));
851                         }
852                         continue;
853                 }
854
855                 if (S_ISDIR(st.st_mode) && !recurse) {
856                         rprintf(FINFO, "skipping directory %s\n", fname);
857                         continue;
858                 }
859
860                 dir = NULL;
861                 olddir = NULL;
862
863                 if (!relative_paths) {
864                         p = strrchr(fname, '/');
865                         if (p) {
866                                 *p = 0;
867                                 if (p == fname)
868                                         dir = "/";
869                                 else
870                                         dir = fname;
871                                 fname = p + 1;
872                         }
873                 } else if (f != -1 && (p = strrchr(fname, '/'))) {
874                         /* this ensures we send the intermediate directories,
875                            thus getting their permissions right */
876                         *p = 0;
877                         if (strcmp(lastpath, fname)) {
878                                 strlcpy(lastpath, fname, sizeof(lastpath));
879                                 *p = '/';
880                                 for (p = fname + 1; (p = strchr(p, '/'));
881                                      p++) {
882                                         int copy_links_saved = copy_links;
883                                         int recurse_saved = recurse;
884                                         *p = 0;
885                                         copy_links = copy_unsafe_links;
886                                         /* set recurse to 1 to prevent make_file
887                                            from ignoring directory, but still
888                                            turn off the recursive parameter to
889                                            send_file_name */
890                                         recurse = 1;
891                                         send_file_name(f, flist, fname, 0,
892                                                        0);
893                                         copy_links = copy_links_saved;
894                                         recurse = recurse_saved;
895                                         *p = '/';
896                                 }
897                         } else {
898                                 *p = '/';
899                         }
900                 }
901
902                 if (!*fname)
903                         fname = ".";
904
905                 if (dir && *dir) {
906                         olddir = push_dir(dir, 1);
907
908                         if (!olddir) {
909                                 io_error = 1;
910                                 rprintf(FERROR, "push_dir %s : %s\n",
911                                         dir, strerror(errno));
912                                 continue;
913                         }
914
915                         flist_dir = dir;
916                 }
917
918                 if (one_file_system)
919                         set_filesystem(fname);
920
921                 send_file_name(f, flist, fname, recurse, FLAG_DELETE);
922
923                 if (olddir != NULL) {
924                         flist_dir = NULL;
925                         if (pop_dir(olddir) != 0) {
926                                 rprintf(FERROR, "pop_dir %s : %s\n",
927                                         dir, strerror(errno));
928                                 exit_cleanup(RERR_FILESELECT);
929                         }
930                 }
931         }
932
933         topsrcname[0] = '\0';
934
935         if (f != -1) {
936                 send_file_entry(NULL, f, 0);
937         }
938
939         finish_build_progress(flist);
940
941         clean_flist(flist, 0);
942
943         /* now send the uid/gid list. This was introduced in protocol
944            version 15 */
945         if (f != -1 && remote_version >= 15) {
946                 send_uid_list(f);
947         }
948
949         /* if protocol version is >= 17 then send the io_error flag */
950         if (f != -1 && remote_version >= 17) {
951                 extern int module_id;
952                 write_int(f, lp_ignore_errors(module_id) ? 0 : io_error);
953         }
954
955         if (f != -1) {
956                 io_end_buffering(f);
957                 stats.flist_size = stats.total_written - start_write;
958                 stats.num_files = flist->count;
959                 if (write_batch)        /*  dw  */
960                         write_batch_flist_info(flist->count, flist->files);
961         }
962
963         if (verbose > 2)
964                 rprintf(FINFO, "send_file_list done\n");
965
966         return flist;
967 }
968
969
970 struct file_list *recv_file_list(int f)
971 {
972         struct file_list *flist;
973         unsigned char flags;
974         int64 start_read;
975         extern int list_only;
976
977         if (verbose && recurse && !am_server) {
978                 rprintf(FINFO, "receiving file list ... ");
979                 rflush(FINFO);
980         }
981
982         start_read = stats.total_read;
983
984         flist = (struct file_list *) malloc(sizeof(flist[0]));
985         if (!flist)
986                 goto oom;
987
988         flist->count = 0;
989         flist->malloced = 1000;
990         flist->files =
991             (struct file_struct **) malloc(sizeof(flist->files[0]) *
992                                            flist->malloced);
993         if (!flist->files)
994                 goto oom;
995
996
997         for (flags = read_byte(f); flags; flags = read_byte(f)) {
998                 int i = flist->count;
999
1000                 if (i >= flist->malloced) {
1001                         if (flist->malloced < 1000)
1002                                 flist->malloced += 1000;
1003                         else
1004                                 flist->malloced *= 2;
1005                         flist->files =
1006                             (struct file_struct **) realloc(flist->files,
1007                                                             sizeof(flist->
1008                                                                    files
1009                                                                    [0]) *
1010                                                             flist->
1011                                                             malloced);
1012                         if (!flist->files)
1013                                 goto oom;
1014                 }
1015
1016                 receive_file_entry(&flist->files[i], flags, f);
1017
1018                 if (S_ISREG(flist->files[i]->mode))
1019                         stats.total_size += flist->files[i]->length;
1020
1021                 flist->count++;
1022
1023                 if (verbose > 2)
1024                         rprintf(FINFO, "recv_file_name(%s)\n",
1025                                 f_name(flist->files[i]));
1026         }
1027
1028
1029         if (verbose > 2)
1030                 rprintf(FINFO, "received %d names\n", flist->count);
1031
1032         clean_flist(flist, relative_paths);
1033
1034         if (verbose && recurse && !am_server) {
1035                 rprintf(FINFO, "done\n");
1036         }
1037
1038         /* now recv the uid/gid list. This was introduced in protocol version 15 */
1039         if (f != -1 && remote_version >= 15) {
1040                 recv_uid_list(f, flist);
1041         }
1042
1043         /* if protocol version is >= 17 then recv the io_error flag */
1044         if (f != -1 && remote_version >= 17 && !read_batch) {   /* dw-added readbatch */
1045                 extern int module_id;
1046                 extern int ignore_errors;
1047                 if (lp_ignore_errors(module_id) || ignore_errors) {
1048                         read_int(f);
1049                 } else {
1050                         io_error |= read_int(f);
1051                 }
1052         }
1053
1054         if (list_only) {
1055                 int i;
1056                 for (i = 0; i < flist->count; i++) {
1057                         list_file_entry(flist->files[i]);
1058                 }
1059         }
1060
1061
1062         if (verbose > 2)
1063                 rprintf(FINFO, "recv_file_list done\n");
1064
1065         stats.flist_size = stats.total_read - start_read;
1066         stats.num_files = flist->count;
1067
1068         return flist;
1069
1070       oom:
1071         out_of_memory("recv_file_list");
1072         return NULL;            /* not reached */
1073 }
1074
1075
1076 /*
1077  * XXX: This is currently the hottest function while building the file
1078  * list, because building f_name()s every time is expensive.
1079  **/
1080 int file_compare(struct file_struct **f1, struct file_struct **f2)
1081 {
1082         if (!(*f1)->basename && !(*f2)->basename)
1083                 return 0;
1084         if (!(*f1)->basename)
1085                 return -1;
1086         if (!(*f2)->basename)
1087                 return 1;
1088         if ((*f1)->dirname == (*f2)->dirname)
1089                 return u_strcmp((*f1)->basename, (*f2)->basename);
1090         return u_strcmp(f_name(*f1), f_name(*f2));
1091 }
1092
1093
1094 int flist_find(struct file_list *flist, struct file_struct *f)
1095 {
1096         int low = 0, high = flist->count - 1;
1097
1098         if (flist->count <= 0)
1099                 return -1;
1100
1101         while (low != high) {
1102                 int mid = (low + high) / 2;
1103                 int ret =
1104                     file_compare(&flist->files[flist_up(flist, mid)], &f);
1105                 if (ret == 0)
1106                         return flist_up(flist, mid);
1107                 if (ret > 0) {
1108                         high = mid;
1109                 } else {
1110                         low = mid + 1;
1111                 }
1112         }
1113
1114         if (file_compare(&flist->files[flist_up(flist, low)], &f) == 0)
1115                 return flist_up(flist, low);
1116         return -1;
1117 }
1118
1119
1120 /*
1121  * free up one file
1122  */
1123 void free_file(struct file_struct *file)
1124 {
1125         if (!file)
1126                 return;
1127         if (file->basename)
1128                 free(file->basename);
1129         if (file->link)
1130                 free(file->link);
1131         if (file->sum)
1132                 free(file->sum);
1133         *file = null_file;
1134 }
1135
1136
1137 /*
1138  * allocate a new file list
1139  */
1140 struct file_list *flist_new()
1141 {
1142         struct file_list *flist;
1143
1144         flist = (struct file_list *) malloc(sizeof(flist[0]));
1145         if (!flist)
1146                 out_of_memory("send_file_list");
1147
1148         flist->count = 0;
1149         flist->malloced = 1000;
1150         flist->files =
1151             (struct file_struct **) malloc(sizeof(flist->files[0]) *
1152                                            flist->malloced);
1153         if (!flist->files)
1154                 out_of_memory("send_file_list");
1155 #if ARENA_SIZE > 0
1156         flist->string_area = string_area_new(0);
1157 #else
1158         flist->string_area = NULL;
1159 #endif
1160         return flist;
1161 }
1162
1163 /*
1164  * free up all elements in a flist
1165  */
1166 void flist_free(struct file_list *flist)
1167 {
1168         int i;
1169         for (i = 1; i < flist->count; i++) {
1170                 if (!flist->string_area)
1171                         free_file(flist->files[i]);
1172                 free(flist->files[i]);
1173         }
1174         memset((char *) flist->files, 0,
1175                sizeof(flist->files[0]) * flist->count);
1176         free(flist->files);
1177         if (flist->string_area)
1178                 string_area_free(flist->string_area);
1179         memset((char *) flist, 0, sizeof(*flist));
1180         free(flist);
1181 }
1182
1183
1184 /*
1185  * This routine ensures we don't have any duplicate names in our file list.
1186  * duplicate names can cause corruption because of the pipelining 
1187  */
1188 static void clean_flist(struct file_list *flist, int strip_root)
1189 {
1190         int i;
1191
1192         if (!flist || flist->count == 0)
1193                 return;
1194
1195         qsort(flist->files, flist->count,
1196               sizeof(flist->files[0]), (int (*)()) file_compare);
1197
1198         for (i = 1; i < flist->count; i++) {
1199                 if (flist->files[i]->basename &&
1200                     flist->files[i - 1]->basename &&
1201                     strcmp(f_name(flist->files[i]),
1202                            f_name(flist->files[i - 1])) == 0) {
1203                         if (verbose > 1 && !am_server)
1204                                 rprintf(FINFO,
1205                                         "removing duplicate name %s from file list %d\n",
1206                                         f_name(flist->files[i - 1]),
1207                                         i - 1);
1208                         /* it's not great that the flist knows the semantics of the
1209                          * file memory usage, but i'd rather not add a flag byte
1210                          * to that struct. XXX can i use a bit in the flags field? */
1211                         if (flist->string_area)
1212                                 flist->files[i][0] = null_file;
1213                         else
1214                                 free_file(flist->files[i]);
1215                 }
1216         }
1217
1218         /* FIXME: There is a bug here when filenames are repeated more
1219          * than once, because we don't handle freed files when doing
1220          * the comparison. */
1221
1222         if (strip_root) {
1223                 /* we need to strip off the root directory in the case
1224                    of relative paths, but this must be done _after_
1225                    the sorting phase */
1226                 for (i = 0; i < flist->count; i++) {
1227                         if (flist->files[i]->dirname &&
1228                             flist->files[i]->dirname[0] == '/') {
1229                                 memmove(&flist->files[i]->dirname[0],
1230                                         &flist->files[i]->dirname[1],
1231                                         strlen(flist->files[i]->dirname));
1232                         }
1233
1234                         if (flist->files[i]->dirname &&
1235                             !flist->files[i]->dirname[0]) {
1236                                 flist->files[i]->dirname = NULL;
1237                         }
1238                 }
1239         }
1240
1241
1242         if (verbose <= 3)
1243                 return;
1244
1245         for (i = 0; i < flist->count; i++) {
1246                 rprintf(FINFO, "[%d] i=%d %s %s mode=0%o len=%.0f\n",
1247                         (int) getpid(), i,
1248                         NS(flist->files[i]->dirname),
1249                         NS(flist->files[i]->basename),
1250                         (int) flist->files[i]->mode,
1251                         (double) flist->files[i]->length);
1252         }
1253 }
1254
1255
1256 /*
1257  * return the full filename of a flist entry
1258  *
1259  * This function is too expensive at the moment, because it copies
1260  * strings when often we only want to compare them.  In any case,
1261  * using strlcat is silly because it will walk the string repeatedly.
1262  */
1263 char *f_name(struct file_struct *f)
1264 {
1265         static char names[10][MAXPATHLEN];
1266         static int n;
1267         char *p = names[n];
1268
1269         if (!f || !f->basename)
1270                 return NULL;
1271
1272         n = (n + 1) % 10;
1273
1274         if (f->dirname) {
1275                 int off;
1276
1277                 off = strlcpy(p, f->dirname, MAXPATHLEN);
1278                 off += strlcpy(p + off, "/", MAXPATHLEN - off);
1279                 off += strlcpy(p + off, f->basename, MAXPATHLEN - off);
1280         } else {
1281                 strlcpy(p, f->basename, MAXPATHLEN);
1282         }
1283
1284         return p;
1285 }