From 1be7683220eb0a3b3fe1ec5b02fe4a41e71b2d7e Mon Sep 17 00:00:00 2001 From: Wayne Davison Date: Sat, 24 Jul 2004 17:05:46 +0000 Subject: [PATCH] When we need to create the partial_dir directory, remove anything that might be in the way (such as a symlink). --- partial-dir.diff | 80 ++++++++++++++++++++++++++++++++++-------------- 1 file changed, 57 insertions(+), 23 deletions(-) diff --git a/partial-dir.diff b/partial-dir.diff index 478563d..407d2e4 100644 --- a/partial-dir.diff +++ b/partial-dir.diff @@ -10,15 +10,16 @@ You must run "make proto" after applying this patch. /** * Close all open sockets and files, allowing a (somewhat) graceful -@@ -113,6 +114,8 @@ void _exit_cleanup(int code, const char +@@ -111,7 +112,8 @@ void _exit_cleanup(int code, const char + } + } - if (cleanup_got_literal && cleanup_fname && keep_partial) { +- if (cleanup_got_literal && cleanup_fname && keep_partial) { ++ if (cleanup_got_literal && cleanup_fname && keep_partial ++ && (!partial_dir || handle_partial_dir(cleanup_new_fname, 1))) { char *fname = cleanup_fname; -+ if (partial_dir) -+ handle_partial_dir(cleanup_new_fname, 1); cleanup_fname = NULL; if (cleanup_fd_r != -1) - close(cleanup_fd_r); --- orig/generator.c 2004-07-23 17:16:12 +++ generator.c 2004-07-23 19:19:47 @@ -42,6 +42,7 @@ extern int size_only; @@ -197,7 +198,7 @@ You must run "make proto" after applying this patch. cleanup_disable(); if (!recv_ok) { ---- orig/rsync.yo 2004-07-23 17:16:13 +--- orig/rsync.yo 2004-07-24 16:52:10 +++ rsync.yo 2004-07-23 19:36:41 @@ -317,6 +317,7 @@ verb( --ignore-errors delete even if there are I/O errors @@ -229,6 +230,16 @@ You must run "make proto" after applying this patch. dit(bf(--progress)) This option tells rsync to print information showing the progress of the transfer. This gives a bored user something to watch. +--- orig/t_stub.c 2004-05-15 20:10:13 ++++ t_stub.c 2004-07-24 17:00:35 +@@ -28,6 +28,7 @@ + + int modify_window = 0; + int module_id = -1; ++char *partial_dir; + struct exclude_list_struct server_exclude_list; + + void rprintf(UNUSED(enum logcode code), const char *format, ...) --- orig/util.c 2004-06-09 21:54:47 +++ util.c 2004-07-23 21:43:44 @@ -31,6 +31,7 @@ extern int verbose; @@ -239,16 +250,16 @@ You must run "make proto" after applying this patch. extern struct exclude_list_struct server_exclude_list; int sanitize_paths = 0; -@@ -945,6 +946,51 @@ char *full_fname(const char *fn) +@@ -945,6 +946,74 @@ char *full_fname(const char *fn) return result; } -+static char partialbuf[MAXPATHLEN]; ++static char partial_fname[MAXPATHLEN]; + +char *fname_in_partial_dir(const char *fname) +{ -+ char *t = partialbuf; -+ int sz = sizeof partialbuf; ++ char *t = partial_fname; ++ int sz = sizeof partial_fname; + const char *fn; + + if ((fn = strrchr(fname, '/')) != NULL) { @@ -262,30 +273,53 @@ You must run "make proto" after applying this patch. + } else + fn = fname; + if ((int)pathjoin(t, sz, partial_dir, fn) >= sz) { -+ *partialbuf = '\0'; ++ *partial_fname = '\0'; + return NULL; + } + -+ return partialbuf; ++ return partial_fname; +} + -+void handle_partial_dir(const char *fname, int create) ++int handle_partial_dir(const char *fname, int create) +{ -+ char *fn; ++ char *fn, *dir = partial_fname; + -+ if (fname != partialbuf) -+ return; ++ if (fname != partial_fname) ++ return 1; + if (!create && *partial_dir == '/') -+ return; -+ if (!(fn = strrchr(partialbuf, '/'))) -+ return; ++ return 1; ++ if (!(fn = strrchr(partial_fname, '/'))) ++ return 1; + + *fn = '\0'; -+ if (create) -+ do_mkdir(partialbuf, 0700); -+ else -+ do_rmdir(partialbuf); ++ if (create) { ++ STRUCT_STAT st; ++#if SUPPORT_LINKS ++ int statret = do_lstat(dir, &st); ++#else ++ int statret = do_stat(dir, &st); ++#endif ++ if (statret == 0 && !S_ISDIR(st.st_mode)) { ++ if (do_unlink(dir) < 0) ++ return 0; ++ statret = -1; ++ } ++ if (statret < 0) { ++ if (do_mkdir(dir, 0700) < 0) ++ return 0; ++#if SUPPORT_LINKS ++ statret = do_lstat(dir, &st); ++#else ++ statret = do_stat(dir, &st); ++#endif ++ if (statret < 0 || !S_ISDIR(st.st_mode)) ++ return 0; ++ } ++ } else ++ do_rmdir(dir); + *fn = '/'; ++ ++ return 1; +} + /** We need to supply our own strcmp function for file list comparisons -- 2.34.1