Modifed to work with the latest acls.diff patch.
[rsync/rsync-patches.git] / adaptec_acl_mods.diff
1 Depends-On-Patch: acls.diff
2
3 After applying the above patch and this one, run these commands for a
4 successful build:
5
6     ./prepare-source
7     ./configure --enable-acl-support
8     make
9
10 Philip Lowman wrote:
11 > Attached is a small patch which is meant to be applied to a copy of
12 > rsync which has already been patched with acl support (the acls.diff
13 > file in the patches folder).  It allows the preservation of the delete,
14 > chmod, and chown bits which Adaptec has added to XFS on their SnapOS NAS
15 > units.  This is nice for backing up files between different NAS units
16 > and preserving all of the Samba ACLs.
17
18 > I'm not sure how useful this patch will be because I'm not sure if any
19 > other NAS vendors have standardized on their extensions to POSIX ACLs to
20 > support Samba in the same manner that Adaptec has.  FWIW, though, this
21 > will allow you to preserve acls when copying between different Adaptec
22 > based NAS units running SnapOS.
23
24 I (Wayne) tweaked the patch for style and to avoid using SMB_* constants
25 with literal values were needed.
26
27 --- old/acls.c
28 +++ new/acls.c
29 @@ -30,9 +30,11 @@ extern int am_root;
30  extern int dry_run;
31  extern int orig_umask;
32  
33 +typedef unsigned short abits;
34 +
35  typedef struct {
36         id_t id;
37 -       uchar access;
38 +       abits access;
39  } id_access;
40  
41  typedef struct {
42 @@ -41,15 +43,15 @@ typedef struct {
43         id_access *idas;
44  } ida_list;
45  
46 -#define NO_ENTRY ((uchar)0x80)
47 +#define NO_ENTRY ((abits)0x8000)
48  typedef struct {
49         ida_list users;
50         ida_list groups;
51         /* These will be NO_ENTRY if there's no such entry. */
52 -       uchar user_obj;
53 -       uchar group_obj;
54 -       uchar mask;
55 -       uchar other;
56 +       abits user_obj;
57 +       abits group_obj;
58 +       abits mask;
59 +       abits other;
60  } rsync_acl;
61  
62  static const rsync_acl rsync_acl_initializer =
63 @@ -148,7 +150,7 @@ static BOOL unpack_smb_acl(rsync_acl *ra
64              rc = sys_acl_get_entry(sacl, SMB_ACL_NEXT_ENTRY, &entry)) {
65                 SMB_ACL_TAG_T tag_type;
66                 SMB_ACL_PERMSET_T permset;
67 -               uchar access;
68 +               abits access;
69                 void *qualifier;
70                 id_access *ida;
71                 ida_list *idal;
72 @@ -162,6 +164,9 @@ static BOOL unpack_smb_acl(rsync_acl *ra
73                 }
74                 access = (sys_acl_get_perm(permset, SMB_ACL_READ) ? 4 : 0)
75                        | (sys_acl_get_perm(permset, SMB_ACL_WRITE) ? 2 : 0)
76 +                      | (sys_acl_get_perm(permset, SMB_ACL_DELETE) ? 8 : 0)
77 +                      | (sys_acl_get_perm(permset, SMB_ACL_CHMOD) ? 16 : 0)
78 +                      | (sys_acl_get_perm(permset, SMB_ACL_CHOWN) ? 32 : 0)
79                        | (sys_acl_get_perm(permset, SMB_ACL_EXECUTE) ? 1 : 0);
80                 /* continue == done with entry; break == store in given idal */
81                 switch (tag_type) {
82 @@ -559,13 +564,19 @@ static void expand_smb_acl_list(smb_acl_
83  #define COE(func,args) CALL_OR_ERROR(func,args,#func)
84  #define COE2(func,args) CALL_OR_ERROR(func,args,NULL)
85  
86 -static int store_access_in_entry(uchar access, SMB_ACL_ENTRY_T entry)
87 +static int store_access_in_entry(abits access, SMB_ACL_ENTRY_T entry)
88  {
89         const char *errfun = NULL;
90         SMB_ACL_PERMSET_T permset;
91  
92         COE( sys_acl_get_permset,(entry, &permset) );
93         COE( sys_acl_clear_perms,(permset) );
94 +       if (access & 32)
95 +               COE( sys_acl_add_perm(permset, SMB_ACL_CHOWN) );
96 +       if (access & 16)
97 +               COE( sys_acl_add_perm(permset, SMB_ACL_CHMOD) );
98 +       if (access & 8)
99 +               COE( sys_acl_add_perm(permset, SMB_ACL_DELETE) );
100         if (access & 4)
101                 COE( sys_acl_add_perm,(permset, SMB_ACL_READ) );
102         if (access & 2)
103 @@ -645,7 +656,7 @@ static BOOL pack_smb_acl(SMB_ACL_T *smb_
104         return False;
105  }
106  
107 -static mode_t change_sacl_perms(SMB_ACL_T sacl, uchar mask, mode_t old_mode, mode_t mode)
108 +static mode_t change_sacl_perms(SMB_ACL_T sacl, abits mask, mode_t old_mode, mode_t mode)
109  {
110         SMB_ACL_ENTRY_T entry;
111         int group_id = mask != NO_ENTRY ? SMB_ACL_MASK : SMB_ACL_GROUP_OBJ;
112 @@ -696,7 +707,7 @@ static mode_t change_sacl_perms(SMB_ACL_
113  
114  static void receive_rsync_acl(rsync_acl *racl, int f)
115  {
116 -       uchar computed_mask_bits = 0;
117 +       abits computed_mask_bits = 0;
118         ida_list *idal = NULL;
119         id_access *ida;
120         size_t count;
121 @@ -708,8 +719,8 @@ static void receive_rsync_acl(rsync_acl 
122  
123         while (count--) {
124                 char tag = read_byte(f);
125 -               uchar access = read_byte(f);
126 -               if (access & ~ (4 | 2 | 1)) {
127 +               abits access = read_byte(f);
128 +               if (access & ~(32 | 16 | 8 | 4 | 2 | 1)) {
129                         rprintf(FERROR, "receive_rsync_acl: bogus permset %o\n",
130                                 access);
131                         exit_cleanup(RERR_STREAMIO);
132 --- old/smb_acls.h
133 +++ new/smb_acls.h
134 @@ -33,6 +33,11 @@
135  #define SMB_ACL_READ           ACL_READ
136  #define SMB_ACL_WRITE          ACL_WRITE
137  #define SMB_ACL_EXECUTE                ACL_EXECUTE
138 +/* These are custom ACL bits used by Adaptec's modifications
139 + * to XFS on their SnapOS units. */
140 +#define SMB_ACL_DELETE         0x08
141 +#define SMB_ACL_CHMOD          0x10
142 +#define SMB_ACL_CHOWN          0x20
143  
144  /* Types of ACLs. */
145  #define SMB_ACL_USER           ACL_USER