xref: /openbmc/linux/fs/posix_acl.c (revision 9fb29c73)
1  /*
2   * Copyright (C) 2002,2003 by Andreas Gruenbacher <a.gruenbacher@computer.org>
3   *
4   * Fixes from William Schumacher incorporated on 15 March 2001.
5   *    (Reported by Charles Bertsch, <CBertsch@microtest.com>).
6   */
7  
8  /*
9   *  This file contains generic functions for manipulating
10   *  POSIX 1003.1e draft standard 17 ACLs.
11   */
12  
13  #include <linux/kernel.h>
14  #include <linux/slab.h>
15  #include <linux/atomic.h>
16  #include <linux/fs.h>
17  #include <linux/sched.h>
18  #include <linux/cred.h>
19  #include <linux/posix_acl.h>
20  #include <linux/posix_acl_xattr.h>
21  #include <linux/xattr.h>
22  #include <linux/export.h>
23  #include <linux/user_namespace.h>
24  
25  static struct posix_acl **acl_by_type(struct inode *inode, int type)
26  {
27  	switch (type) {
28  	case ACL_TYPE_ACCESS:
29  		return &inode->i_acl;
30  	case ACL_TYPE_DEFAULT:
31  		return &inode->i_default_acl;
32  	default:
33  		BUG();
34  	}
35  }
36  
37  struct posix_acl *get_cached_acl(struct inode *inode, int type)
38  {
39  	struct posix_acl **p = acl_by_type(inode, type);
40  	struct posix_acl *acl;
41  
42  	for (;;) {
43  		rcu_read_lock();
44  		acl = rcu_dereference(*p);
45  		if (!acl || is_uncached_acl(acl) ||
46  		    refcount_inc_not_zero(&acl->a_refcount))
47  			break;
48  		rcu_read_unlock();
49  		cpu_relax();
50  	}
51  	rcu_read_unlock();
52  	return acl;
53  }
54  EXPORT_SYMBOL(get_cached_acl);
55  
56  struct posix_acl *get_cached_acl_rcu(struct inode *inode, int type)
57  {
58  	return rcu_dereference(*acl_by_type(inode, type));
59  }
60  EXPORT_SYMBOL(get_cached_acl_rcu);
61  
62  void set_cached_acl(struct inode *inode, int type, struct posix_acl *acl)
63  {
64  	struct posix_acl **p = acl_by_type(inode, type);
65  	struct posix_acl *old;
66  
67  	old = xchg(p, posix_acl_dup(acl));
68  	if (!is_uncached_acl(old))
69  		posix_acl_release(old);
70  }
71  EXPORT_SYMBOL(set_cached_acl);
72  
73  static void __forget_cached_acl(struct posix_acl **p)
74  {
75  	struct posix_acl *old;
76  
77  	old = xchg(p, ACL_NOT_CACHED);
78  	if (!is_uncached_acl(old))
79  		posix_acl_release(old);
80  }
81  
82  void forget_cached_acl(struct inode *inode, int type)
83  {
84  	__forget_cached_acl(acl_by_type(inode, type));
85  }
86  EXPORT_SYMBOL(forget_cached_acl);
87  
88  void forget_all_cached_acls(struct inode *inode)
89  {
90  	__forget_cached_acl(&inode->i_acl);
91  	__forget_cached_acl(&inode->i_default_acl);
92  }
93  EXPORT_SYMBOL(forget_all_cached_acls);
94  
95  struct posix_acl *get_acl(struct inode *inode, int type)
96  {
97  	void *sentinel;
98  	struct posix_acl **p;
99  	struct posix_acl *acl;
100  
101  	/*
102  	 * The sentinel is used to detect when another operation like
103  	 * set_cached_acl() or forget_cached_acl() races with get_acl().
104  	 * It is guaranteed that is_uncached_acl(sentinel) is true.
105  	 */
106  
107  	acl = get_cached_acl(inode, type);
108  	if (!is_uncached_acl(acl))
109  		return acl;
110  
111  	if (!IS_POSIXACL(inode))
112  		return NULL;
113  
114  	sentinel = uncached_acl_sentinel(current);
115  	p = acl_by_type(inode, type);
116  
117  	/*
118  	 * If the ACL isn't being read yet, set our sentinel.  Otherwise, the
119  	 * current value of the ACL will not be ACL_NOT_CACHED and so our own
120  	 * sentinel will not be set; another task will update the cache.  We
121  	 * could wait for that other task to complete its job, but it's easier
122  	 * to just call ->get_acl to fetch the ACL ourself.  (This is going to
123  	 * be an unlikely race.)
124  	 */
125  	if (cmpxchg(p, ACL_NOT_CACHED, sentinel) != ACL_NOT_CACHED)
126  		/* fall through */ ;
127  
128  	/*
129  	 * Normally, the ACL returned by ->get_acl will be cached.
130  	 * A filesystem can prevent that by calling
131  	 * forget_cached_acl(inode, type) in ->get_acl.
132  	 *
133  	 * If the filesystem doesn't have a get_acl() function at all, we'll
134  	 * just create the negative cache entry.
135  	 */
136  	if (!inode->i_op->get_acl) {
137  		set_cached_acl(inode, type, NULL);
138  		return NULL;
139  	}
140  	acl = inode->i_op->get_acl(inode, type);
141  
142  	if (IS_ERR(acl)) {
143  		/*
144  		 * Remove our sentinel so that we don't block future attempts
145  		 * to cache the ACL.
146  		 */
147  		cmpxchg(p, sentinel, ACL_NOT_CACHED);
148  		return acl;
149  	}
150  
151  	/*
152  	 * Cache the result, but only if our sentinel is still in place.
153  	 */
154  	posix_acl_dup(acl);
155  	if (unlikely(cmpxchg(p, sentinel, acl) != sentinel))
156  		posix_acl_release(acl);
157  	return acl;
158  }
159  EXPORT_SYMBOL(get_acl);
160  
161  /*
162   * Init a fresh posix_acl
163   */
164  void
165  posix_acl_init(struct posix_acl *acl, int count)
166  {
167  	refcount_set(&acl->a_refcount, 1);
168  	acl->a_count = count;
169  }
170  EXPORT_SYMBOL(posix_acl_init);
171  
172  /*
173   * Allocate a new ACL with the specified number of entries.
174   */
175  struct posix_acl *
176  posix_acl_alloc(int count, gfp_t flags)
177  {
178  	const size_t size = sizeof(struct posix_acl) +
179  	                    count * sizeof(struct posix_acl_entry);
180  	struct posix_acl *acl = kmalloc(size, flags);
181  	if (acl)
182  		posix_acl_init(acl, count);
183  	return acl;
184  }
185  EXPORT_SYMBOL(posix_acl_alloc);
186  
187  /*
188   * Clone an ACL.
189   */
190  static struct posix_acl *
191  posix_acl_clone(const struct posix_acl *acl, gfp_t flags)
192  {
193  	struct posix_acl *clone = NULL;
194  
195  	if (acl) {
196  		int size = sizeof(struct posix_acl) + acl->a_count *
197  		           sizeof(struct posix_acl_entry);
198  		clone = kmemdup(acl, size, flags);
199  		if (clone)
200  			refcount_set(&clone->a_refcount, 1);
201  	}
202  	return clone;
203  }
204  
205  /*
206   * Check if an acl is valid. Returns 0 if it is, or -E... otherwise.
207   */
208  int
209  posix_acl_valid(struct user_namespace *user_ns, const struct posix_acl *acl)
210  {
211  	const struct posix_acl_entry *pa, *pe;
212  	int state = ACL_USER_OBJ;
213  	int needs_mask = 0;
214  
215  	FOREACH_ACL_ENTRY(pa, acl, pe) {
216  		if (pa->e_perm & ~(ACL_READ|ACL_WRITE|ACL_EXECUTE))
217  			return -EINVAL;
218  		switch (pa->e_tag) {
219  			case ACL_USER_OBJ:
220  				if (state == ACL_USER_OBJ) {
221  					state = ACL_USER;
222  					break;
223  				}
224  				return -EINVAL;
225  
226  			case ACL_USER:
227  				if (state != ACL_USER)
228  					return -EINVAL;
229  				if (!kuid_has_mapping(user_ns, pa->e_uid))
230  					return -EINVAL;
231  				needs_mask = 1;
232  				break;
233  
234  			case ACL_GROUP_OBJ:
235  				if (state == ACL_USER) {
236  					state = ACL_GROUP;
237  					break;
238  				}
239  				return -EINVAL;
240  
241  			case ACL_GROUP:
242  				if (state != ACL_GROUP)
243  					return -EINVAL;
244  				if (!kgid_has_mapping(user_ns, pa->e_gid))
245  					return -EINVAL;
246  				needs_mask = 1;
247  				break;
248  
249  			case ACL_MASK:
250  				if (state != ACL_GROUP)
251  					return -EINVAL;
252  				state = ACL_OTHER;
253  				break;
254  
255  			case ACL_OTHER:
256  				if (state == ACL_OTHER ||
257  				    (state == ACL_GROUP && !needs_mask)) {
258  					state = 0;
259  					break;
260  				}
261  				return -EINVAL;
262  
263  			default:
264  				return -EINVAL;
265  		}
266  	}
267  	if (state == 0)
268  		return 0;
269  	return -EINVAL;
270  }
271  EXPORT_SYMBOL(posix_acl_valid);
272  
273  /*
274   * Returns 0 if the acl can be exactly represented in the traditional
275   * file mode permission bits, or else 1. Returns -E... on error.
276   */
277  int
278  posix_acl_equiv_mode(const struct posix_acl *acl, umode_t *mode_p)
279  {
280  	const struct posix_acl_entry *pa, *pe;
281  	umode_t mode = 0;
282  	int not_equiv = 0;
283  
284  	/*
285  	 * A null ACL can always be presented as mode bits.
286  	 */
287  	if (!acl)
288  		return 0;
289  
290  	FOREACH_ACL_ENTRY(pa, acl, pe) {
291  		switch (pa->e_tag) {
292  			case ACL_USER_OBJ:
293  				mode |= (pa->e_perm & S_IRWXO) << 6;
294  				break;
295  			case ACL_GROUP_OBJ:
296  				mode |= (pa->e_perm & S_IRWXO) << 3;
297  				break;
298  			case ACL_OTHER:
299  				mode |= pa->e_perm & S_IRWXO;
300  				break;
301  			case ACL_MASK:
302  				mode = (mode & ~S_IRWXG) |
303  				       ((pa->e_perm & S_IRWXO) << 3);
304  				not_equiv = 1;
305  				break;
306  			case ACL_USER:
307  			case ACL_GROUP:
308  				not_equiv = 1;
309  				break;
310  			default:
311  				return -EINVAL;
312  		}
313  	}
314          if (mode_p)
315                  *mode_p = (*mode_p & ~S_IRWXUGO) | mode;
316          return not_equiv;
317  }
318  EXPORT_SYMBOL(posix_acl_equiv_mode);
319  
320  /*
321   * Create an ACL representing the file mode permission bits of an inode.
322   */
323  struct posix_acl *
324  posix_acl_from_mode(umode_t mode, gfp_t flags)
325  {
326  	struct posix_acl *acl = posix_acl_alloc(3, flags);
327  	if (!acl)
328  		return ERR_PTR(-ENOMEM);
329  
330  	acl->a_entries[0].e_tag  = ACL_USER_OBJ;
331  	acl->a_entries[0].e_perm = (mode & S_IRWXU) >> 6;
332  
333  	acl->a_entries[1].e_tag  = ACL_GROUP_OBJ;
334  	acl->a_entries[1].e_perm = (mode & S_IRWXG) >> 3;
335  
336  	acl->a_entries[2].e_tag  = ACL_OTHER;
337  	acl->a_entries[2].e_perm = (mode & S_IRWXO);
338  	return acl;
339  }
340  EXPORT_SYMBOL(posix_acl_from_mode);
341  
342  /*
343   * Return 0 if current is granted want access to the inode
344   * by the acl. Returns -E... otherwise.
345   */
346  int
347  posix_acl_permission(struct inode *inode, const struct posix_acl *acl, int want)
348  {
349  	const struct posix_acl_entry *pa, *pe, *mask_obj;
350  	int found = 0;
351  
352  	want &= MAY_READ | MAY_WRITE | MAY_EXEC | MAY_NOT_BLOCK;
353  
354  	FOREACH_ACL_ENTRY(pa, acl, pe) {
355                  switch(pa->e_tag) {
356                          case ACL_USER_OBJ:
357  				/* (May have been checked already) */
358  				if (uid_eq(inode->i_uid, current_fsuid()))
359                                          goto check_perm;
360                                  break;
361                          case ACL_USER:
362  				if (uid_eq(pa->e_uid, current_fsuid()))
363                                          goto mask;
364  				break;
365                          case ACL_GROUP_OBJ:
366                                  if (in_group_p(inode->i_gid)) {
367  					found = 1;
368  					if ((pa->e_perm & want) == want)
369  						goto mask;
370                                  }
371  				break;
372                          case ACL_GROUP:
373  				if (in_group_p(pa->e_gid)) {
374  					found = 1;
375  					if ((pa->e_perm & want) == want)
376  						goto mask;
377                                  }
378                                  break;
379                          case ACL_MASK:
380                                  break;
381                          case ACL_OTHER:
382  				if (found)
383  					return -EACCES;
384  				else
385  					goto check_perm;
386  			default:
387  				return -EIO;
388                  }
389          }
390  	return -EIO;
391  
392  mask:
393  	for (mask_obj = pa+1; mask_obj != pe; mask_obj++) {
394  		if (mask_obj->e_tag == ACL_MASK) {
395  			if ((pa->e_perm & mask_obj->e_perm & want) == want)
396  				return 0;
397  			return -EACCES;
398  		}
399  	}
400  
401  check_perm:
402  	if ((pa->e_perm & want) == want)
403  		return 0;
404  	return -EACCES;
405  }
406  
407  /*
408   * Modify acl when creating a new inode. The caller must ensure the acl is
409   * only referenced once.
410   *
411   * mode_p initially must contain the mode parameter to the open() / creat()
412   * system calls. All permissions that are not granted by the acl are removed.
413   * The permissions in the acl are changed to reflect the mode_p parameter.
414   */
415  static int posix_acl_create_masq(struct posix_acl *acl, umode_t *mode_p)
416  {
417  	struct posix_acl_entry *pa, *pe;
418  	struct posix_acl_entry *group_obj = NULL, *mask_obj = NULL;
419  	umode_t mode = *mode_p;
420  	int not_equiv = 0;
421  
422  	/* assert(atomic_read(acl->a_refcount) == 1); */
423  
424  	FOREACH_ACL_ENTRY(pa, acl, pe) {
425                  switch(pa->e_tag) {
426                          case ACL_USER_OBJ:
427  				pa->e_perm &= (mode >> 6) | ~S_IRWXO;
428  				mode &= (pa->e_perm << 6) | ~S_IRWXU;
429  				break;
430  
431  			case ACL_USER:
432  			case ACL_GROUP:
433  				not_equiv = 1;
434  				break;
435  
436                          case ACL_GROUP_OBJ:
437  				group_obj = pa;
438                                  break;
439  
440                          case ACL_OTHER:
441  				pa->e_perm &= mode | ~S_IRWXO;
442  				mode &= pa->e_perm | ~S_IRWXO;
443                                  break;
444  
445                          case ACL_MASK:
446  				mask_obj = pa;
447  				not_equiv = 1;
448                                  break;
449  
450  			default:
451  				return -EIO;
452                  }
453          }
454  
455  	if (mask_obj) {
456  		mask_obj->e_perm &= (mode >> 3) | ~S_IRWXO;
457  		mode &= (mask_obj->e_perm << 3) | ~S_IRWXG;
458  	} else {
459  		if (!group_obj)
460  			return -EIO;
461  		group_obj->e_perm &= (mode >> 3) | ~S_IRWXO;
462  		mode &= (group_obj->e_perm << 3) | ~S_IRWXG;
463  	}
464  
465  	*mode_p = (*mode_p & ~S_IRWXUGO) | mode;
466          return not_equiv;
467  }
468  
469  /*
470   * Modify the ACL for the chmod syscall.
471   */
472  static int __posix_acl_chmod_masq(struct posix_acl *acl, umode_t mode)
473  {
474  	struct posix_acl_entry *group_obj = NULL, *mask_obj = NULL;
475  	struct posix_acl_entry *pa, *pe;
476  
477  	/* assert(atomic_read(acl->a_refcount) == 1); */
478  
479  	FOREACH_ACL_ENTRY(pa, acl, pe) {
480  		switch(pa->e_tag) {
481  			case ACL_USER_OBJ:
482  				pa->e_perm = (mode & S_IRWXU) >> 6;
483  				break;
484  
485  			case ACL_USER:
486  			case ACL_GROUP:
487  				break;
488  
489  			case ACL_GROUP_OBJ:
490  				group_obj = pa;
491  				break;
492  
493  			case ACL_MASK:
494  				mask_obj = pa;
495  				break;
496  
497  			case ACL_OTHER:
498  				pa->e_perm = (mode & S_IRWXO);
499  				break;
500  
501  			default:
502  				return -EIO;
503  		}
504  	}
505  
506  	if (mask_obj) {
507  		mask_obj->e_perm = (mode & S_IRWXG) >> 3;
508  	} else {
509  		if (!group_obj)
510  			return -EIO;
511  		group_obj->e_perm = (mode & S_IRWXG) >> 3;
512  	}
513  
514  	return 0;
515  }
516  
517  int
518  __posix_acl_create(struct posix_acl **acl, gfp_t gfp, umode_t *mode_p)
519  {
520  	struct posix_acl *clone = posix_acl_clone(*acl, gfp);
521  	int err = -ENOMEM;
522  	if (clone) {
523  		err = posix_acl_create_masq(clone, mode_p);
524  		if (err < 0) {
525  			posix_acl_release(clone);
526  			clone = NULL;
527  		}
528  	}
529  	posix_acl_release(*acl);
530  	*acl = clone;
531  	return err;
532  }
533  EXPORT_SYMBOL(__posix_acl_create);
534  
535  int
536  __posix_acl_chmod(struct posix_acl **acl, gfp_t gfp, umode_t mode)
537  {
538  	struct posix_acl *clone = posix_acl_clone(*acl, gfp);
539  	int err = -ENOMEM;
540  	if (clone) {
541  		err = __posix_acl_chmod_masq(clone, mode);
542  		if (err) {
543  			posix_acl_release(clone);
544  			clone = NULL;
545  		}
546  	}
547  	posix_acl_release(*acl);
548  	*acl = clone;
549  	return err;
550  }
551  EXPORT_SYMBOL(__posix_acl_chmod);
552  
553  int
554  posix_acl_chmod(struct inode *inode, umode_t mode)
555  {
556  	struct posix_acl *acl;
557  	int ret = 0;
558  
559  	if (!IS_POSIXACL(inode))
560  		return 0;
561  	if (!inode->i_op->set_acl)
562  		return -EOPNOTSUPP;
563  
564  	acl = get_acl(inode, ACL_TYPE_ACCESS);
565  	if (IS_ERR_OR_NULL(acl)) {
566  		if (acl == ERR_PTR(-EOPNOTSUPP))
567  			return 0;
568  		return PTR_ERR(acl);
569  	}
570  
571  	ret = __posix_acl_chmod(&acl, GFP_KERNEL, mode);
572  	if (ret)
573  		return ret;
574  	ret = inode->i_op->set_acl(inode, acl, ACL_TYPE_ACCESS);
575  	posix_acl_release(acl);
576  	return ret;
577  }
578  EXPORT_SYMBOL(posix_acl_chmod);
579  
580  int
581  posix_acl_create(struct inode *dir, umode_t *mode,
582  		struct posix_acl **default_acl, struct posix_acl **acl)
583  {
584  	struct posix_acl *p;
585  	struct posix_acl *clone;
586  	int ret;
587  
588  	*acl = NULL;
589  	*default_acl = NULL;
590  
591  	if (S_ISLNK(*mode) || !IS_POSIXACL(dir))
592  		return 0;
593  
594  	p = get_acl(dir, ACL_TYPE_DEFAULT);
595  	if (!p || p == ERR_PTR(-EOPNOTSUPP)) {
596  		*mode &= ~current_umask();
597  		return 0;
598  	}
599  	if (IS_ERR(p))
600  		return PTR_ERR(p);
601  
602  	ret = -ENOMEM;
603  	clone = posix_acl_clone(p, GFP_NOFS);
604  	if (!clone)
605  		goto err_release;
606  
607  	ret = posix_acl_create_masq(clone, mode);
608  	if (ret < 0)
609  		goto err_release_clone;
610  
611  	if (ret == 0)
612  		posix_acl_release(clone);
613  	else
614  		*acl = clone;
615  
616  	if (!S_ISDIR(*mode))
617  		posix_acl_release(p);
618  	else
619  		*default_acl = p;
620  
621  	return 0;
622  
623  err_release_clone:
624  	posix_acl_release(clone);
625  err_release:
626  	posix_acl_release(p);
627  	return ret;
628  }
629  EXPORT_SYMBOL_GPL(posix_acl_create);
630  
631  /**
632   * posix_acl_update_mode  -  update mode in set_acl
633   *
634   * Update the file mode when setting an ACL: compute the new file permission
635   * bits based on the ACL.  In addition, if the ACL is equivalent to the new
636   * file mode, set *acl to NULL to indicate that no ACL should be set.
637   *
638   * As with chmod, clear the setgit bit if the caller is not in the owning group
639   * or capable of CAP_FSETID (see inode_change_ok).
640   *
641   * Called from set_acl inode operations.
642   */
643  int posix_acl_update_mode(struct inode *inode, umode_t *mode_p,
644  			  struct posix_acl **acl)
645  {
646  	umode_t mode = inode->i_mode;
647  	int error;
648  
649  	error = posix_acl_equiv_mode(*acl, &mode);
650  	if (error < 0)
651  		return error;
652  	if (error == 0)
653  		*acl = NULL;
654  	if (!in_group_p(inode->i_gid) &&
655  	    !capable_wrt_inode_uidgid(inode, CAP_FSETID))
656  		mode &= ~S_ISGID;
657  	*mode_p = mode;
658  	return 0;
659  }
660  EXPORT_SYMBOL(posix_acl_update_mode);
661  
662  /*
663   * Fix up the uids and gids in posix acl extended attributes in place.
664   */
665  static void posix_acl_fix_xattr_userns(
666  	struct user_namespace *to, struct user_namespace *from,
667  	void *value, size_t size)
668  {
669  	struct posix_acl_xattr_header *header = value;
670  	struct posix_acl_xattr_entry *entry = (void *)(header + 1), *end;
671  	int count;
672  	kuid_t uid;
673  	kgid_t gid;
674  
675  	if (!value)
676  		return;
677  	if (size < sizeof(struct posix_acl_xattr_header))
678  		return;
679  	if (header->a_version != cpu_to_le32(POSIX_ACL_XATTR_VERSION))
680  		return;
681  
682  	count = posix_acl_xattr_count(size);
683  	if (count < 0)
684  		return;
685  	if (count == 0)
686  		return;
687  
688  	for (end = entry + count; entry != end; entry++) {
689  		switch(le16_to_cpu(entry->e_tag)) {
690  		case ACL_USER:
691  			uid = make_kuid(from, le32_to_cpu(entry->e_id));
692  			entry->e_id = cpu_to_le32(from_kuid(to, uid));
693  			break;
694  		case ACL_GROUP:
695  			gid = make_kgid(from, le32_to_cpu(entry->e_id));
696  			entry->e_id = cpu_to_le32(from_kgid(to, gid));
697  			break;
698  		default:
699  			break;
700  		}
701  	}
702  }
703  
704  void posix_acl_fix_xattr_from_user(void *value, size_t size)
705  {
706  	struct user_namespace *user_ns = current_user_ns();
707  	if (user_ns == &init_user_ns)
708  		return;
709  	posix_acl_fix_xattr_userns(&init_user_ns, user_ns, value, size);
710  }
711  
712  void posix_acl_fix_xattr_to_user(void *value, size_t size)
713  {
714  	struct user_namespace *user_ns = current_user_ns();
715  	if (user_ns == &init_user_ns)
716  		return;
717  	posix_acl_fix_xattr_userns(user_ns, &init_user_ns, value, size);
718  }
719  
720  /*
721   * Convert from extended attribute to in-memory representation.
722   */
723  struct posix_acl *
724  posix_acl_from_xattr(struct user_namespace *user_ns,
725  		     const void *value, size_t size)
726  {
727  	const struct posix_acl_xattr_header *header = value;
728  	const struct posix_acl_xattr_entry *entry = (const void *)(header + 1), *end;
729  	int count;
730  	struct posix_acl *acl;
731  	struct posix_acl_entry *acl_e;
732  
733  	if (!value)
734  		return NULL;
735  	if (size < sizeof(struct posix_acl_xattr_header))
736  		 return ERR_PTR(-EINVAL);
737  	if (header->a_version != cpu_to_le32(POSIX_ACL_XATTR_VERSION))
738  		return ERR_PTR(-EOPNOTSUPP);
739  
740  	count = posix_acl_xattr_count(size);
741  	if (count < 0)
742  		return ERR_PTR(-EINVAL);
743  	if (count == 0)
744  		return NULL;
745  
746  	acl = posix_acl_alloc(count, GFP_NOFS);
747  	if (!acl)
748  		return ERR_PTR(-ENOMEM);
749  	acl_e = acl->a_entries;
750  
751  	for (end = entry + count; entry != end; acl_e++, entry++) {
752  		acl_e->e_tag  = le16_to_cpu(entry->e_tag);
753  		acl_e->e_perm = le16_to_cpu(entry->e_perm);
754  
755  		switch(acl_e->e_tag) {
756  			case ACL_USER_OBJ:
757  			case ACL_GROUP_OBJ:
758  			case ACL_MASK:
759  			case ACL_OTHER:
760  				break;
761  
762  			case ACL_USER:
763  				acl_e->e_uid =
764  					make_kuid(user_ns,
765  						  le32_to_cpu(entry->e_id));
766  				if (!uid_valid(acl_e->e_uid))
767  					goto fail;
768  				break;
769  			case ACL_GROUP:
770  				acl_e->e_gid =
771  					make_kgid(user_ns,
772  						  le32_to_cpu(entry->e_id));
773  				if (!gid_valid(acl_e->e_gid))
774  					goto fail;
775  				break;
776  
777  			default:
778  				goto fail;
779  		}
780  	}
781  	return acl;
782  
783  fail:
784  	posix_acl_release(acl);
785  	return ERR_PTR(-EINVAL);
786  }
787  EXPORT_SYMBOL (posix_acl_from_xattr);
788  
789  /*
790   * Convert from in-memory to extended attribute representation.
791   */
792  int
793  posix_acl_to_xattr(struct user_namespace *user_ns, const struct posix_acl *acl,
794  		   void *buffer, size_t size)
795  {
796  	struct posix_acl_xattr_header *ext_acl = buffer;
797  	struct posix_acl_xattr_entry *ext_entry;
798  	int real_size, n;
799  
800  	real_size = posix_acl_xattr_size(acl->a_count);
801  	if (!buffer)
802  		return real_size;
803  	if (real_size > size)
804  		return -ERANGE;
805  
806  	ext_entry = (void *)(ext_acl + 1);
807  	ext_acl->a_version = cpu_to_le32(POSIX_ACL_XATTR_VERSION);
808  
809  	for (n=0; n < acl->a_count; n++, ext_entry++) {
810  		const struct posix_acl_entry *acl_e = &acl->a_entries[n];
811  		ext_entry->e_tag  = cpu_to_le16(acl_e->e_tag);
812  		ext_entry->e_perm = cpu_to_le16(acl_e->e_perm);
813  		switch(acl_e->e_tag) {
814  		case ACL_USER:
815  			ext_entry->e_id =
816  				cpu_to_le32(from_kuid(user_ns, acl_e->e_uid));
817  			break;
818  		case ACL_GROUP:
819  			ext_entry->e_id =
820  				cpu_to_le32(from_kgid(user_ns, acl_e->e_gid));
821  			break;
822  		default:
823  			ext_entry->e_id = cpu_to_le32(ACL_UNDEFINED_ID);
824  			break;
825  		}
826  	}
827  	return real_size;
828  }
829  EXPORT_SYMBOL (posix_acl_to_xattr);
830  
831  static int
832  posix_acl_xattr_get(const struct xattr_handler *handler,
833  		    struct dentry *unused, struct inode *inode,
834  		    const char *name, void *value, size_t size)
835  {
836  	struct posix_acl *acl;
837  	int error;
838  
839  	if (!IS_POSIXACL(inode))
840  		return -EOPNOTSUPP;
841  	if (S_ISLNK(inode->i_mode))
842  		return -EOPNOTSUPP;
843  
844  	acl = get_acl(inode, handler->flags);
845  	if (IS_ERR(acl))
846  		return PTR_ERR(acl);
847  	if (acl == NULL)
848  		return -ENODATA;
849  
850  	error = posix_acl_to_xattr(&init_user_ns, acl, value, size);
851  	posix_acl_release(acl);
852  
853  	return error;
854  }
855  
856  int
857  set_posix_acl(struct inode *inode, int type, struct posix_acl *acl)
858  {
859  	if (!IS_POSIXACL(inode))
860  		return -EOPNOTSUPP;
861  	if (!inode->i_op->set_acl)
862  		return -EOPNOTSUPP;
863  
864  	if (type == ACL_TYPE_DEFAULT && !S_ISDIR(inode->i_mode))
865  		return acl ? -EACCES : 0;
866  	if (!inode_owner_or_capable(inode))
867  		return -EPERM;
868  
869  	if (acl) {
870  		int ret = posix_acl_valid(inode->i_sb->s_user_ns, acl);
871  		if (ret)
872  			return ret;
873  	}
874  	return inode->i_op->set_acl(inode, acl, type);
875  }
876  EXPORT_SYMBOL(set_posix_acl);
877  
878  static int
879  posix_acl_xattr_set(const struct xattr_handler *handler,
880  		    struct dentry *unused, struct inode *inode,
881  		    const char *name, const void *value,
882  		    size_t size, int flags)
883  {
884  	struct posix_acl *acl = NULL;
885  	int ret;
886  
887  	if (value) {
888  		acl = posix_acl_from_xattr(&init_user_ns, value, size);
889  		if (IS_ERR(acl))
890  			return PTR_ERR(acl);
891  	}
892  	ret = set_posix_acl(inode, handler->flags, acl);
893  	posix_acl_release(acl);
894  	return ret;
895  }
896  
897  static bool
898  posix_acl_xattr_list(struct dentry *dentry)
899  {
900  	return IS_POSIXACL(d_backing_inode(dentry));
901  }
902  
903  const struct xattr_handler posix_acl_access_xattr_handler = {
904  	.name = XATTR_NAME_POSIX_ACL_ACCESS,
905  	.flags = ACL_TYPE_ACCESS,
906  	.list = posix_acl_xattr_list,
907  	.get = posix_acl_xattr_get,
908  	.set = posix_acl_xattr_set,
909  };
910  EXPORT_SYMBOL_GPL(posix_acl_access_xattr_handler);
911  
912  const struct xattr_handler posix_acl_default_xattr_handler = {
913  	.name = XATTR_NAME_POSIX_ACL_DEFAULT,
914  	.flags = ACL_TYPE_DEFAULT,
915  	.list = posix_acl_xattr_list,
916  	.get = posix_acl_xattr_get,
917  	.set = posix_acl_xattr_set,
918  };
919  EXPORT_SYMBOL_GPL(posix_acl_default_xattr_handler);
920  
921  int simple_set_acl(struct inode *inode, struct posix_acl *acl, int type)
922  {
923  	int error;
924  
925  	if (type == ACL_TYPE_ACCESS) {
926  		error = posix_acl_update_mode(inode,
927  				&inode->i_mode, &acl);
928  		if (error)
929  			return error;
930  	}
931  
932  	inode->i_ctime = current_time(inode);
933  	set_cached_acl(inode, type, acl);
934  	return 0;
935  }
936  
937  int simple_acl_create(struct inode *dir, struct inode *inode)
938  {
939  	struct posix_acl *default_acl, *acl;
940  	int error;
941  
942  	error = posix_acl_create(dir, &inode->i_mode, &default_acl, &acl);
943  	if (error)
944  		return error;
945  
946  	set_cached_acl(inode, ACL_TYPE_DEFAULT, default_acl);
947  	set_cached_acl(inode, ACL_TYPE_ACCESS, acl);
948  
949  	if (default_acl)
950  		posix_acl_release(default_acl);
951  	if (acl)
952  		posix_acl_release(acl);
953  	return 0;
954  }
955