That should have been -s.
[rsync/rsync.git] / flist.c
diff --git a/flist.c b/flist.c
index 4f3e25a..a67a1b4 100644 (file)
--- a/flist.c
+++ b/flist.c
@@ -52,6 +52,7 @@ extern int preserve_devices;
 extern int preserve_specials;
 extern int uid_ndx;
 extern int gid_ndx;
+extern int eol_nulls;
 extern int relative_paths;
 extern int implied_dirs;
 extern int file_extra_cnt;
@@ -63,6 +64,7 @@ extern int copy_unsafe_links;
 extern int protocol_version;
 extern int sanitize_paths;
 extern struct stats stats;
+extern char *filesfrom_host;
 
 extern char curr_dir[MAXPATHLEN];
 
@@ -1549,6 +1551,7 @@ void send_extra_file_list(int f, int at_least)
        while (future_cnt < at_least) {
                struct file_struct *file = dir_flist->sorted[send_dir_ndx];
                int dir_ndx, dstart = dir_count;
+               const char *pathname = F_PATHNAME(file);
                int32 *dp;
 
                flist = flist_new(0, "send_extra_file_list");
@@ -1573,7 +1576,8 @@ void send_extra_file_list(int f, int at_least)
                    && dir_flist->sorted[dir_ndx]->flags & FLAG_DUPLICATE) {
                        send_dir_ndx = dir_ndx;
                        file = dir_flist->sorted[dir_ndx];
-                       send1extra(f, file, flist);
+                       if (F_PATHNAME(file) != pathname)
+                               send1extra(f, file, flist);
                        dp = F_DIR_NODE_P(file);
                }
 
@@ -1641,6 +1645,8 @@ struct file_list *send_file_list(int f, int argc, char *argv[])
        int64 start_write;
        int use_ff_fd = 0;
        int flags, disable_buffering;
+       int reading_remotely = filesfrom_host != NULL;
+       int rl_nulls = eol_nulls || reading_remotely;
 
        rprintf(FLOG, "building file list\n");
        if (show_filelist_p())
@@ -1681,7 +1687,7 @@ struct file_list *send_file_list(int f, int argc, char *argv[])
                int is_dot_dir;
 
                if (use_ff_fd) {
-                       if (read_filesfrom_line(filesfrom_fd, fbuf) == 0)
+                       if (read_line(filesfrom_fd, fbuf, sizeof fbuf, !reading_remotely, rl_nulls) == 0)
                                break;
                        sanitize_path(fbuf, fbuf, "", 0, NULL);
                } else {
@@ -1787,16 +1793,11 @@ struct file_list *send_file_list(int f, int argc, char *argv[])
                dirlen = dir ? strlen(dir) : 0;
                if (dirlen != lastdir_len || memcmp(lastdir, dir, dirlen) != 0) {
                        if (!push_pathname(dir ? strdup(dir) : NULL, dirlen))
-                               goto push_error;
+                               continue;
                        lastdir = pathname;
                        lastdir_len = pathname_len;
-               } else if (!push_pathname(lastdir, lastdir_len)) {
-                 push_error:
-                       io_error |= IOERR_GENERAL;
-                       rsyserr(FERROR, errno, "push_dir %s failed in %s",
-                               full_fname(dir), curr_dir);
+               } else if (!push_pathname(lastdir, lastdir_len))
                        continue;
-               }
 
                if (fn != fbuf)
                        memmove(fbuf, fn, len + 1);
@@ -2299,19 +2300,20 @@ static void clean_flist(struct file_list *flist, int strip_root)
                        int keep, drop;
                        /* If one is a dir and the other is not, we want to
                         * keep the dir because it might have contents in the
-                        * list. */
+                        * list.  Otherwise keep the first one. */
                        if (S_ISDIR(file->mode)) {
                                struct file_struct *fp = flist->sorted[j];
-                               if (!S_ISDIR(fp->mode))
+                               if (!S_ISDIR(fp->mode) || !(fp->flags & FLAG_XFER_DIR))
                                        keep = i, drop = j;
-                               else
+                               else {
+                                       if (am_sender)
+                                               file->flags |= FLAG_DUPLICATE;
                                        keep = j, drop = i;
+                               }
                        } else
                                keep = j, drop = i;
 
-                       if (am_sender)
-                               flist->sorted[drop]->flags |= FLAG_DUPLICATE;
-                       else {
+                       if (!am_sender) {
                                if (verbose > 1) {
                                        rprintf(FINFO,
                                            "removing duplicate name %s from file list (%d)\n",