X-Git-Url: https://mattmccutchen.net/rsync/rsync.git/blobdiff_plain/08b1b4860f7354916c777fd8ef16caa3f547ec7e..85f14172dc8e0caeff77444e7621724d68b912b9:/receiver.c diff --git a/receiver.c b/receiver.c index 124a2808..70978fd9 100644 --- a/receiver.c +++ b/receiver.c @@ -30,6 +30,7 @@ extern int dry_run; extern int read_batch; extern int batch_gen_fd; extern int am_server; +extern int protocol_version; extern int relative_paths; extern int keep_dirlinks; extern int preserve_hard_links; @@ -38,7 +39,7 @@ extern int cvs_exclude; extern int io_error; extern char *tmpdir; extern char *partial_dir; -extern char *compare_dest; +extern char *basis_dir[]; extern int make_backups; extern int do_progress; extern char *backup_dir; @@ -122,16 +123,16 @@ void delete_files(struct file_list *flist) continue; if (flist_find(flist,local_file_list->files[i]) < 0) { char *f = f_name(local_file_list->files[i]); - if (make_backups && (backup_dir || !is_backup_file(f))) { + int mode = local_file_list->files[i]->mode; + if (make_backups && (backup_dir || !is_backup_file(f)) + && !S_ISDIR(mode)) { make_backup(f); if (verbose) { rprintf(FINFO, "deleting %s\n", safe_fname(f)); } - } else { - int mode = local_file_list->files[i]->mode; + } else delete_one(f, S_ISDIR(mode) != 0); - } deletion_count++; } } @@ -288,7 +289,8 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r, offset += len; } - flush_write_file(fd); + if (flush_write_file(fd) < 0) + goto report_write_error; #ifdef HAVE_FTRUNCATE if (inplace && fd != -1) @@ -329,7 +331,8 @@ static void discard_receive_data(int f_in, OFF_T length) * main routine for receiver process. * * Receiver process runs on the same host as the generator process. */ -int recv_files(int f_in, struct file_list *flist, char *local_name) +int recv_files(int f_in, struct file_list *flist, char *local_name, + int f_in_name) { int next_gen_i = -1; int fd1,fd2; @@ -358,8 +361,13 @@ int recv_files(int f_in, struct file_list *flist, char *local_name) i = read_int(f_in); if (i == -1) { if (read_batch) { - if (next_gen_i != flist->count) - while (read_int(batch_gen_fd) != -1) {} + if (next_gen_i != flist->count) { + do { + if (f_in_name >= 0 + && next_gen_i >= 0) + read_byte(f_in_name); + } while (read_int(batch_gen_fd) != -1); + } next_gen_i = -1; } @@ -407,6 +415,8 @@ int recv_files(int f_in, struct file_list *flist, char *local_name) if (read_batch) { while (i > next_gen_i) { + if (f_in_name >= 0 && next_gen_i >= 0) + read_byte(f_in_name); next_gen_i = read_int(batch_gen_fd); if (next_gen_i == -1) next_gen_i = flist->count; @@ -417,6 +427,7 @@ int recv_files(int f_in, struct file_list *flist, char *local_name) discard_receive_data(f_in, file->length); continue; } + next_gen_i = -1; } if (server_exclude_list.head @@ -426,35 +437,33 @@ int recv_files(int f_in, struct file_list *flist, char *local_name) exit_cleanup(RERR_PROTOCOL); } - if (partial_dir) { - if ((partialptr = partial_dir_fname(fname)) != NULL) - fnamecmp = partialptr; - else + partialptr = partial_dir ? partial_dir_fname(fname) : fname; + + if (f_in_name >= 0) { + uchar j; + switch (j = read_byte(f_in_name)) { + case FNAMECMP_FNAME: fnamecmp = fname; + break; + case FNAMECMP_PARTIAL_DIR: + fnamecmp = partialptr ? partialptr : fname; + break; + case FNAMECMP_BACKUP: + fnamecmp = get_backup_name(fname); + break; + case FNAMECMP_BASIS_DIR: + default: + pathjoin(fnamecmpbuf, sizeof fnamecmpbuf, + basis_dir[j], fname); + fnamecmp = fnamecmpbuf; + break; + } } else - fnamecmp = partialptr = fname; - - if (inplace && make_backups) { - if (!(fnamecmp = get_backup_name(fname))) - fnamecmp = partialptr; - } + fnamecmp = fname; /* open the file */ fd1 = do_open(fnamecmp, O_RDONLY, 0); - if (fd1 == -1 && fnamecmp != fname) { - fnamecmp = fname; - fd1 = do_open(fnamecmp, O_RDONLY, 0); - } - - if (fd1 == -1 && compare_dest != NULL) { - /* try the file at compare_dest instead */ - pathjoin(fnamecmpbuf, sizeof fnamecmpbuf, - compare_dest, fname); - fnamecmp = fnamecmpbuf; - fd1 = do_open(fnamecmp, O_RDONLY, 0); - } - if (fd1 != -1 && do_fstat(fd1,&st) != 0) { rsyserr(FERROR, errno, "fstat %s failed", full_fname(fnamecmp));