Skip new symlink conversion step if the remote rsync is not
authorWayne Davison <wayned@samba.org>
Sat, 2 Aug 2008 14:04:54 +0000 (07:04 -0700)
committerWayne Davison <wayned@samba.org>
Sat, 2 Aug 2008 14:04:54 +0000 (07:04 -0700)
new enough to do symlink content conversions.

compat.c
flist.c
options.c

index ef220e2..3c30604 100644 (file)
--- a/compat.c
+++ b/compat.c
@@ -57,12 +57,14 @@ extern struct filter_list_struct filter_list;
 extern int need_unsorted_flist;
 #ifdef ICONV_OPTION
 extern iconv_t ic_send, ic_recv;
+extern char *iconv_opt;
 #endif
 
 /* These index values are for the file-list's extra-attribute array. */
 int uid_ndx, gid_ndx, acls_ndx, xattrs_ndx, unsort_ndx;
 
 int receiver_symlink_times = 0; /* receiver can set the time on a symlink */
+int sender_symlink_iconv = 0;  /* sender should convert symlink content */
 
 #ifdef ICONV_OPTION
 int filesfrom_convert = 0;
@@ -70,6 +72,7 @@ int filesfrom_convert = 0;
 
 #define CF_INC_RECURSE  (1<<0)
 #define CF_SYMLINK_TIMES (1<<1)
+#define CF_SYMLINK_ICONV (1<<2)
 
 static const char *client_info;
 
@@ -248,6 +251,9 @@ void setup_protocol(int f_out,int f_in)
                        compat_flags = allow_inc_recurse ? CF_INC_RECURSE : 0;
 #if defined HAVE_LUTIMES && defined HAVE_UTIMES
                        compat_flags |= CF_SYMLINK_TIMES;
+#endif
+#ifdef ICONV_OPTION
+                       compat_flags |= CF_SYMLINK_ICONV;
 #endif
                        write_byte(f_out, compat_flags);
                } else
@@ -262,6 +268,11 @@ void setup_protocol(int f_out,int f_in)
 #if defined HAVE_LUTIMES && defined HAVE_UTIMES
                else
                        receiver_symlink_times = 1;
+#endif
+#ifdef ICONV_OPTION
+               sender_symlink_iconv = iconv_opt && (am_server
+                   ? strchr(client_info, 's') != NULL
+                   : !!(compat_flags & CF_SYMLINK_ICONV));
 #endif
                if (inc_recurse && !allow_inc_recurse) {
                        /* This should only be able to happen in a batch. */
diff --git a/flist.c b/flist.c
index 91806b5..2f08850 100644 (file)
--- a/flist.c
+++ b/flist.c
@@ -67,6 +67,7 @@ extern int protocol_version;
 extern int sanitize_paths;
 extern int munge_symlinks;
 extern int need_unsorted_flist;
+extern int sender_symlink_iconv;
 extern int unsort_ndx;
 extern struct stats stats;
 extern char *filesfrom_host;
@@ -817,7 +818,7 @@ static struct file_struct *recv_file_entry(struct file_list *flist,
                /* We don't know how much extra room we need to convert
                 * the as-yet-unread symlink name when converting it,
                 * so let's hope that a double-size buffer is plenty. */
-               if (ic_recv != (iconv_t)-1)
+               if (sender_symlink_iconv)
                        linkname_len = linkname_len * 2 + 1;
 #endif
                if (munge_symlinks)
@@ -961,7 +962,7 @@ static struct file_struct *recv_file_entry(struct file_list *flist,
                                linkname_len -= SYMLINK_PREFIX_LEN;
                        }
 #ifdef ICONV_OPTION
-                       if (ic_recv != (iconv_t)-1) {
+                       if (sender_symlink_iconv) {
                                xbuf outbuf, inbuf;
 
                                alloc_len = linkname_len;
@@ -1393,7 +1394,7 @@ static struct file_struct *send_file_name(int f, struct file_list *flist,
                        fbuf[outbuf.len] = '\0';
 
 #ifdef SUPPORT_LINKS
-                       if (symlink_len) {
+                       if (symlink_len && sender_symlink_iconv) {
                                INIT_XBUF(inbuf, (char*)symlink_name, symlink_len, (size_t)-1);
                                INIT_CONST_XBUF(outbuf, symlink_buf);
                                if (iconvbufs(ic_send, &inbuf, &outbuf, 0) < 0) {
index 4bb2ab3..aebfdf8 100644 (file)
--- a/options.c
+++ b/options.c
@@ -1827,9 +1827,17 @@ void server_options(char **args, int *argc_p)
                        argstr[x++] = 'i';
 #if defined HAVE_LUTIMES && defined HAVE_UTIMES
                argstr[x++] = 'L';
+#endif
+#ifdef ICONV_OPTION
+               argstr[x++] = 's';
 #endif
        }
 
+       if (x >= (int)sizeof argstr) { /* Not possible... */
+               rprintf(FERROR, "argstr overflow in server_options().\n");
+               exit_cleanup(RERR_MALLOC);
+       }
+
        argstr[x] = '\0';
 
        args[ac++] = argstr;
@@ -2053,6 +2061,11 @@ void server_options(char **args, int *argc_p)
        else if (remove_source_files)
                args[ac++] = "--remove-sent-files";
 
+       if (ac > MAX_SERVER_ARGS) { /* Not possible... */
+               rprintf(FERROR, "argc overflow in server_options().\n");
+               exit_cleanup(RERR_MALLOC);
+       }
+
        *argc_p = ac;
        return;