Patch from Stefan Nehlsen that allows a daemon to force the
authorWayne Davison <wayned@samba.org>
Sat, 23 Apr 2005 21:25:53 +0000 (21:25 +0000)
committerWayne Davison <wayned@samba.org>
Sat, 23 Apr 2005 21:25:53 +0000 (21:25 +0000)
file and/or directory permissions on received files.

rsyncd-perm.diff [new file with mode: 0644]

diff --git a/rsyncd-perm.diff b/rsyncd-perm.diff
new file mode 100644 (file)
index 0000000..27801bd
--- /dev/null
@@ -0,0 +1,154 @@
+--- orig/loadparm.c    2005-02-19 17:38:51
++++ loadparm.c 2005-03-31 08:28:41
+@@ -144,6 +144,10 @@ typedef struct
+       int timeout;
+       int max_connections;
+       BOOL ignore_nonreadable;
++      int create_mask;
++      int force_create_mode;
++      int directory_mask;
++      int force_directory_mode;
+ } service;
+@@ -186,7 +190,11 @@ static service sDefault =
+       "*.gz *.tgz *.zip *.z *.rpm *.deb *.iso *.bz2 *.tbz",    /* dont compress */
+       0,        /* timeout */
+       0,        /* max connections */
+-      False     /* ignore nonreadable */
++      False,    /* ignore nonreadable */
++      CHMOD_BITS, /* create mask */
++      0,        /* force create mode */
++      CHMOD_BITS, /* directory mask */
++      0         /* force directory mode */
+ };
+@@ -306,6 +314,10 @@ static struct parm_struct parm_table[] =
+   {"log format",       P_STRING,  P_LOCAL,  &sDefault.log_format,  NULL,   0},
+   {"refuse options",   P_STRING,  P_LOCAL,  &sDefault.refuse_options,NULL, 0},
+   {"dont compress",    P_STRING,  P_LOCAL,  &sDefault.dont_compress,NULL,  0},
++  {"create mask",      P_OCTAL,   P_LOCAL,  &sDefault.create_mask, NULL, 0},
++  {"force create mode",P_OCTAL,   P_LOCAL,  &sDefault.force_create_mode, NULL, 0},
++  {"directory mask",   P_OCTAL,   P_LOCAL,  &sDefault.directory_mask, NULL, 0},
++  {"force directory mode",P_OCTAL,P_LOCAL,  &sDefault.force_directory_mode, NULL, 0},
+   {NULL,               P_BOOL,    P_NONE,   NULL,                  NULL,   0}
+ };
+@@ -391,6 +403,10 @@ FN_LOCAL_STRING(lp_refuse_options, refus
+ FN_LOCAL_STRING(lp_dont_compress, dont_compress)
+ FN_LOCAL_INTEGER(lp_timeout, timeout)
+ FN_LOCAL_INTEGER(lp_max_connections, max_connections)
++FN_LOCAL_INTEGER(lp_create_mask, create_mask)
++FN_LOCAL_INTEGER(lp_force_create_mode, force_create_mode)
++FN_LOCAL_INTEGER(lp_directory_mask, directory_mask)
++FN_LOCAL_INTEGER(lp_force_directory_mode, force_directory_mode)
+ /* local prototypes */
+ static int    strwicmp(char *psz1, char *psz2);
+--- orig/rsync.c       2005-03-16 02:19:30
++++ rsync.c    2005-03-31 08:28:41
+@@ -56,6 +56,8 @@ int set_perms(char *fname,struct file_st
+       int updated = 0;
+       STRUCT_STAT st2;
+       int change_uid, change_gid;
++      extern int am_daemon;
++      extern int module_id;
+       if (!st) {
+               if (dry_run)
+@@ -126,9 +128,19 @@ int set_perms(char *fname,struct file_st
+ #ifdef HAVE_CHMOD
+       if (!S_ISLNK(st->st_mode)) {
+-              if ((st->st_mode & CHMOD_BITS) != (file->mode & CHMOD_BITS)) {
++              mode_t mode = file->mode; /* file->mode shouldn't be modified */
++              if (am_daemon) {
++                      if (S_ISDIR(st->st_mode)) {
++                              mode = (mode & lp_directory_mask(module_id))
++                                   | lp_force_directory_mode(module_id);
++                      } else {
++                              mode = (mode & lp_create_mask(module_id))
++                                   | lp_force_create_mode(module_id);
++                      }
++              }
++              if ((st->st_mode & CHMOD_BITS) != (mode & CHMOD_BITS)) {
+                       updated = 1;
+-                      if (do_chmod(fname,(file->mode & CHMOD_BITS)) != 0) {
++                      if (do_chmod(fname, (mode & CHMOD_BITS)) != 0) {
+                               rsyserr(FERROR, errno, "failed to set permissions on %s",
+                                       full_fname(fname));
+                               return 0;
+--- orig/rsyncd.conf.yo        2005-04-23 17:50:12
++++ rsyncd.conf.yo     2005-03-31 08:28:41
+@@ -221,6 +221,70 @@ file transfers to and from that module s
+ was run as root. This complements the "uid" option. The default is gid -2,
+ which is normally the group "nobody".
++dit(bf(create mask)) When a file is created (or touched) by rsyncd the
++permissions will be taken from the source file bit-wise 'AND'ed with this
++parameter. This parameter may be thought of as a bit-wise MASK for the UNIX
++modes of a file. Any bit not set here will be removed from the modes set
++on a file when it is created.
++
++The default value of this parameter is set to 07777 to be provide the
++default behaviour of older versions.
++
++Following this rsync  will bit-wise 'OR' the UNIX mode created from this
++parameter with the value  of the force create mode parameter which is set
++to 000 by default.
++
++This parameter does not affect directory modes. See the parameter
++"directory mask" for details.
++
++See also the "force create mode" parameter for forcing particular mode bits
++to be set on created files. See also the "directory mask" parameter for
++masking mode bits on created directories.
++
++dit(bf(force create mode)) This parameter specifies a set of UNIX
++mode bit permissions that will always be set on a file created by
++rsyncd. This is done by bitwise 'OR'ing these bits onto the mode
++bits of a file that is being created or having its permissions changed.
++
++The default for this parameter is (in octal) 000.  The modes in this
++parameter are bitwise 'OR'ed onto the file mode after the mask set in
++the "create mask" parameter is applied.
++
++See also the parameter "create mask" for details on
++masking mode bits on files.
++
++
++dit(bf(directory mask)) When a directory is created (or touched) by
++rsyncd the permissions will be taken from the source directory
++bit-wise 'AND'ed with this parameter. This parameter may be thought
++of as a bit-wise MASK for the UNIX modes of a file. Any bit not set
++here will be removed from the modes set on a file when it is created.
++
++The default value of this parameter is set to 07777 to be provide the
++default behaviour of older versions.
++ 
++Following this rsync  will bit-wise 'OR' the UNIX mode created from this
++parameter with the value  of the "force directory mode" parameter which
++is set to 000 by default.
++
++This parameter does not affect file modes. See the parameter "create mask"
++for details.  
++
++See also the "force directory mode" parameter for forcing particular
++mode bits to be set on created directories. See also the "create mask"
++parameter for masking mode bits on created files.
++ 
++dit(bf(force directory mode)) This parameter specifies a set of UNIX mode
++bit permissions that will always be set on a directory created by rsyncd.
++This is done by bitwise 'OR'ing these bits onto the mode bits of a directory
++that is being created. The default for this parameter is (in octal) 0000
++which will not add any extra permission bits to a created directory. This
++operation is done after the mode mask in the parameter "directory mask"
++is applied.
++
++See also the parameter  directory mask for details on masking mode bits on
++created directories.
++
+ dit(bf(filter)) The "filter" option allows you to specify a space-separated
+ list of filter rules that the server will not allow to be read or written.
+ This is only superficially equivalent to the client specifying these