Using target side filters in rsyncd.conf works well for files that are only manipulated on the target. However, if files from the source system match a filter on the target you can generate a core and rsync will stop responding on that system. in /var/log/messages you will see: May 28 19:47:06 v-lab-30-244-127 rsyncd[9157]: receiving file list May 28 19:47:06 v-lab-30-244-127 rsyncd[9157]: skipping daemon-excluded directory ".snap1" May 28 19:47:06 v-lab-30-244-127 rsyncd[9157]: *** Skipping any contents from this failed directory *** May 28 13:47:06 v-lab-30-244-127 kernel: rsyncd[9157]: segfault at fffffffffffffff9 rip 0000003ba1a758bb rsp 00007fff5b1c7750 error 4 In this case '.snap1' directory was created, and a file created in that directory. The target has a filter: .fs_*/*** .snap*/*** which matches, and the daemon dumps core. The problem appears in versions 3.0.6, 3.0.7 & HEAD, it is in generator.c. There is an error path that takes a 'goto' that skips the initialization of sx struct, then the cleanup tries to free random memory with a call to free_acl(&sx). In acls.c the free is void free_acl(stat_x *sxp) { if (sxp->acc_acl) { rsync_acl_free(sxp->acc_acl); free(sxp->acc_acl); <<<<<<< uninitialized In version 3.0.6 the 'bad' goto is at line 1315: rprintf(FERROR_XFER, "skipping daemon-excluded %s \"%s\"\n", is_dir ? "directory" : "file", fname); if (is_dir) goto skipping_dir_contents; <<<<<<<<<<<<<<<<< bad goto The fix is to move the initialization earlier in the code: # diff -c generator.c.orig generator.c *** generator.c.orig 2009-04-26 08:51:50.000000000 -0600 --- generator.c 2010-06-02 15:04:36.000000000 -0600 *************** *** 1300,1305 **** --- 1300,1311 ---- skip_dir = NULL; } + #ifdef SUPPORT_ACLS + sx.acc_acl = sx.def_acl = NULL; + #endif + #ifdef SUPPORT_XATTRS + sx.xattr = NULL; + #endif if (daemon_filter_list.head && (*fname != '.' || fname[1])) { if (check_filter(&daemon_filter_list, FLOG, fname, is_dir) < 0) { if (is_dir < 0) *************** *** 1317,1328 **** } } - #ifdef SUPPORT_ACLS - sx.acc_acl = sx.def_acl = NULL; - #endif - #ifdef SUPPORT_XATTRS - sx.xattr = NULL; - #endif if (dry_run > 1 || (dry_missing_dir && is_below(file, dry_missing_dir))) { parent_is_dry_missing: if (fuzzy_dirlist) { --- 1323,1328 ----
Thanks for the bug report and the fix! This is now committed in the git repository (on both master and b3.0.x branches).