Moved the EXDEV handling into robust_rename().
authorWayne Davison <wayned@samba.org>
Tue, 17 Feb 2004 23:13:10 +0000 (23:13 +0000)
committerWayne Davison <wayned@samba.org>
Tue, 17 Feb 2004 23:13:10 +0000 (23:13 +0000)
backup.c
rsync.c
util.c

index 35568d9..2078861 100644 (file)
--- a/backup.c
+++ b/backup.c
@@ -130,42 +130,10 @@ failure:
 /* robustly move a file, creating new directory structures if necessary */
 static int robust_move(char *src, char *dst)
 {
-       int keep_trying = 4;
-       int keep_path_extfs = 0;
-       int failed;
-
-       while (keep_trying) {
-               if (keep_path_extfs) {
-                       failed = copy_file(src, dst, 0755);
-                       if (!failed)
-                               do_unlink(src);
-               } else
-                       failed = robust_rename(src, dst);
-
-               if (failed) {
-                       if (verbose > 2) {
-                               rprintf(FERROR, "robust_move failed: %s(%d)\n",
-                                       strerror(errno), errno);
-                       }
-                       switch (errno) {
-                       case EXDEV:     /* external filesystem */
-                               keep_path_extfs = 1;
-                               keep_trying--;
-                               break;
-                       case ENOENT:    /* no directory to write to */
-                               if (make_bak_dir(dst) < 0)
-                                       keep_trying = 0;
-                               else
-                                       keep_trying--;
-                               break;
-                       default:
-                               keep_trying = 0;
-                               break;
-                       }
-               } else
-                       keep_trying = 0;
-       }
-       return !failed;
+       if (robust_rename(src, dst, 0755) != 0 || errno != ENOENT
+           || make_bak_dir(dst) < 0 || robust_rename(src, dst, 0755) != 0)
+               return -1;
+       return 0;
 }
 
 
diff --git a/rsync.c b/rsync.c
index 78fedab..cf310e9 100644 (file)
--- a/rsync.c
+++ b/rsync.c
@@ -158,7 +158,7 @@ int set_perms(char *fname,struct file_struct *file,STRUCT_STAT *st,
        change_gid = preserve_gid && file->gid != GID_NONE
                && st->st_gid != file->gid;
        if (change_uid || change_gid) {
-               if (verbose > 2 && !dry_run) {
+               if (verbose > 2) {
                        if (change_uid) {
                                rprintf(FINFO,
                                    "set uid of %s from %ld to %ld\n",
@@ -231,25 +231,17 @@ void sig_int(void)
    and ownership */
 void finish_transfer(char *fname, char *fnametmp, struct file_struct *file)
 {
+       int ret;
+
        if (make_backups && !make_backup(fname))
                return;
 
        /* move tmp file over real file */
-       if (robust_rename(fnametmp,fname) != 0) {
-               if (errno == EXDEV) {
-                       /* rename failed on cross-filesystem link.
-                          Copy the file instead. */
-                       if (copy_file(fnametmp,fname, file->mode & INITACCESSPERMS)) {
-                               rprintf(FERROR, "copy %s -> \"%s\": %s\n",
-                                       full_fname(fnametmp), fname,
-                                       strerror(errno));
-                       } else {
-                               set_perms(fname,file,NULL,0);
-                       }
-               } else {
-                       rprintf(FERROR,"rename %s -> \"%s\": %s\n",
-                               full_fname(fnametmp), fname, strerror(errno));
-               }
+       ret = robust_rename(fnametmp, fname, file->mode & INITACCESSPERMS);
+       if (ret != 0) {
+               rprintf(FERROR, "%s %s -> \"%s\": %s\n",
+                   ret == -2 ? "copy" : "rename",
+                   full_fname(fnametmp), fname, strerror(errno));
                do_unlink(fnametmp);
        } else {
                set_perms(fname,file,NULL,0);
diff --git a/util.c b/util.c
index fd01283..cb47c2a 100644 (file)
--- a/util.c
+++ b/util.c
@@ -353,18 +353,33 @@ int robust_unlink(char *fname)
 #endif
 }
 
-int robust_rename(char *from, char *to)
+/* Returns 0 on success, -1 on most errors, and -2 if we got an error
+ * trying to copy the file across file systems. */
+int robust_rename(char *from, char *to, int mode)
 {
-#ifndef ETXTBSY
-       return do_rename(from, to);
-#else
-       int rc = do_rename(from, to);
-       if (rc == 0 || errno != ETXTBSY)
-               return rc;
-       if (robust_unlink(to) != 0)
-               return -1;
-       return do_rename(from, to);
+       int tries = 4;
+
+       while (tries--) {
+               if (do_rename(from, to) == 0)
+                       return 0;
+
+               switch (errno) {
+#ifdef ETXTBSY
+               case ETXTBSY:
+                       if (robust_unlink(to) != 0)
+                               return -1;
+                       break;
 #endif
+               case EXDEV:
+                       if (copy_file(from, to, mode) != 0)
+                               return -2;
+                       do_unlink(from);
+                       return 0;
+               default:
+                       return -1;
+               }
+       }
+       return -1;
 }