aboutsummaryrefslogtreecommitdiffstats
path: root/fs/generic_acl.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/generic_acl.c')
-rw-r--r--fs/generic_acl.c62
1 files changed, 13 insertions, 49 deletions
diff --git a/fs/generic_acl.c b/fs/generic_acl.c
index 70e90b4974ce..d5e33a077a67 100644
--- a/fs/generic_acl.c
+++ b/fs/generic_acl.c
@@ -132,31 +132,17 @@ generic_acl_init(struct inode *inode, struct inode *dir)
132 if (!S_ISLNK(inode->i_mode)) 132 if (!S_ISLNK(inode->i_mode))
133 acl = get_cached_acl(dir, ACL_TYPE_DEFAULT); 133 acl = get_cached_acl(dir, ACL_TYPE_DEFAULT);
134 if (acl) { 134 if (acl) {
135 struct posix_acl *clone; 135 if (S_ISDIR(inode->i_mode))
136 136 set_cached_acl(inode, ACL_TYPE_DEFAULT, acl);
137 if (S_ISDIR(inode->i_mode)) { 137 error = posix_acl_create(&acl, GFP_KERNEL, &mode);
138 clone = posix_acl_clone(acl, GFP_KERNEL); 138 if (error < 0)
139 error = -ENOMEM; 139 return error;
140 if (!clone) 140 inode->i_mode = mode;
141 goto cleanup; 141 if (error > 0)
142 set_cached_acl(inode, ACL_TYPE_DEFAULT, clone); 142 set_cached_acl(inode, ACL_TYPE_ACCESS, acl);
143 posix_acl_release(clone);
144 }
145 clone = posix_acl_clone(acl, GFP_KERNEL);
146 error = -ENOMEM;
147 if (!clone)
148 goto cleanup;
149 error = posix_acl_create_masq(clone, &mode);
150 if (error >= 0) {
151 inode->i_mode = mode;
152 if (error > 0)
153 set_cached_acl(inode, ACL_TYPE_ACCESS, clone);
154 }
155 posix_acl_release(clone);
156 } 143 }
157 error = 0; 144 error = 0;
158 145
159cleanup:
160 posix_acl_release(acl); 146 posix_acl_release(acl);
161 return error; 147 return error;
162} 148}
@@ -170,44 +156,22 @@ cleanup:
170int 156int
171generic_acl_chmod(struct inode *inode) 157generic_acl_chmod(struct inode *inode)
172{ 158{
173 struct posix_acl *acl, *clone; 159 struct posix_acl *acl;
174 int error = 0; 160 int error = 0;
175 161
176 if (S_ISLNK(inode->i_mode)) 162 if (S_ISLNK(inode->i_mode))
177 return -EOPNOTSUPP; 163 return -EOPNOTSUPP;
178 acl = get_cached_acl(inode, ACL_TYPE_ACCESS); 164 acl = get_cached_acl(inode, ACL_TYPE_ACCESS);
179 if (acl) { 165 if (acl) {
180 clone = posix_acl_clone(acl, GFP_KERNEL); 166 error = posix_acl_chmod(&acl, GFP_KERNEL, inode->i_mode);
167 if (error)
168 return error;
169 set_cached_acl(inode, ACL_TYPE_ACCESS, acl);
181 posix_acl_release(acl); 170 posix_acl_release(acl);
182 if (!clone)
183 return -ENOMEM;
184 error = posix_acl_chmod_masq(clone, inode->i_mode);
185 if (!error)
186 set_cached_acl(inode, ACL_TYPE_ACCESS, clone);
187 posix_acl_release(clone);
188 } 171 }
189 return error; 172 return error;
190} 173}
191 174
192int
193generic_check_acl(struct inode *inode, int mask)
194{
195 if (mask & MAY_NOT_BLOCK) {
196 if (!negative_cached_acl(inode, ACL_TYPE_ACCESS))
197 return -ECHILD;
198 } else {
199 struct posix_acl *acl;
200
201 acl = get_cached_acl(inode, ACL_TYPE_ACCESS);
202 if (acl) {
203 int error = posix_acl_permission(inode, acl, mask);
204 posix_acl_release(acl);
205 return error;
206 }
207 }
208 return -EAGAIN;
209}
210
211const struct xattr_handler generic_acl_access_handler = { 175const struct xattr_handler generic_acl_access_handler = {
212 .prefix = POSIX_ACL_XATTR_ACCESS, 176 .prefix = POSIX_ACL_XATTR_ACCESS,
213 .flags = ACL_TYPE_ACCESS, 177 .flags = ACL_TYPE_ACCESS,