Commit 0279b4cd86685b5eea467c1b74ce94f0add2c0a3

Authored by Jim Owens
Committed by Chris Mason
1 parent bef62ef339

Btrfs: selinux support

Add call to LSM security initialization and save
resulting security xattr for new inodes.

Add xattr support to symlink inode ops.

Set inode->i_op for existing special files.

Signed-off-by: jim owens <jowens@hp.com>

Showing 3 changed files with 53 additions and 4 deletions Side-by-side Diff

... ... @@ -90,6 +90,16 @@
90 90 u64 start, u64 end, int *page_started,
91 91 unsigned long *nr_written, int unlock);
92 92  
  93 +static int btrfs_init_inode_security(struct inode *inode, struct inode *dir)
  94 +{
  95 + int err;
  96 +
  97 + err = btrfs_init_acl(inode, dir);
  98 + if (!err)
  99 + err = btrfs_xattr_security_init(inode, dir);
  100 + return err;
  101 +}
  102 +
93 103 /*
94 104 * a very lame attempt at stopping writes when the FS is 85% full. There
95 105 * are countless ways this is incorrect, but it is better than nothing.
... ... @@ -2037,6 +2047,7 @@
2037 2047 inode->i_mapping->backing_dev_info = &root->fs_info->bdi;
2038 2048 break;
2039 2049 default:
  2050 + inode->i_op = &btrfs_special_inode_operations;
2040 2051 init_special_inode(inode, inode->i_mode, rdev);
2041 2052 break;
2042 2053 }
... ... @@ -3584,7 +3595,7 @@
3584 3595 if (IS_ERR(inode))
3585 3596 goto out_unlock;
3586 3597  
3587   - err = btrfs_init_acl(inode, dir);
  3598 + err = btrfs_init_inode_security(inode, dir);
3588 3599 if (err) {
3589 3600 drop_inode = 1;
3590 3601 goto out_unlock;
... ... @@ -3647,7 +3658,7 @@
3647 3658 if (IS_ERR(inode))
3648 3659 goto out_unlock;
3649 3660  
3650   - err = btrfs_init_acl(inode, dir);
  3661 + err = btrfs_init_inode_security(inode, dir);
3651 3662 if (err) {
3652 3663 drop_inode = 1;
3653 3664 goto out_unlock;
... ... @@ -3770,7 +3781,7 @@
3770 3781  
3771 3782 drop_on_err = 1;
3772 3783  
3773   - err = btrfs_init_acl(inode, dir);
  3784 + err = btrfs_init_inode_security(inode, dir);
3774 3785 if (err)
3775 3786 goto out_fail;
3776 3787  
... ... @@ -4732,7 +4743,7 @@
4732 4743 if (IS_ERR(inode))
4733 4744 goto out_unlock;
4734 4745  
4735   - err = btrfs_init_acl(inode, dir);
  4746 + err = btrfs_init_inode_security(inode, dir);
4736 4747 if (err) {
4737 4748 drop_inode = 1;
4738 4749 goto out_unlock;
... ... @@ -5043,5 +5054,9 @@
5043 5054 .follow_link = page_follow_link_light,
5044 5055 .put_link = page_put_link,
5045 5056 .permission = btrfs_permission,
  5057 + .setxattr = btrfs_setxattr,
  5058 + .getxattr = btrfs_getxattr,
  5059 + .listxattr = btrfs_listxattr,
  5060 + .removexattr = btrfs_removexattr,
5046 5061 };
... ... @@ -21,6 +21,7 @@
21 21 #include <linux/slab.h>
22 22 #include <linux/rwsem.h>
23 23 #include <linux/xattr.h>
  24 +#include <linux/security.h>
24 25 #include "ctree.h"
25 26 #include "btrfs_inode.h"
26 27 #include "transaction.h"
... ... @@ -329,5 +330,36 @@
329 330 if (!btrfs_is_valid_xattr(name))
330 331 return -EOPNOTSUPP;
331 332 return __btrfs_setxattr(dentry->d_inode, name, NULL, 0, XATTR_REPLACE);
  333 +}
  334 +
  335 +int btrfs_xattr_security_init(struct inode *inode, struct inode *dir)
  336 +{
  337 + int err;
  338 + size_t len;
  339 + void *value;
  340 + char *suffix;
  341 + char *name;
  342 +
  343 + err = security_inode_init_security(inode, dir, &suffix, &value, &len);
  344 + if (err) {
  345 + if (err == -EOPNOTSUPP)
  346 + return 0;
  347 + return err;
  348 + }
  349 +
  350 + name = kmalloc(XATTR_SECURITY_PREFIX_LEN + strlen(suffix) + 1,
  351 + GFP_NOFS);
  352 + if (!name) {
  353 + err = -ENOMEM;
  354 + } else {
  355 + strcpy(name, XATTR_SECURITY_PREFIX);
  356 + strcpy(name + XATTR_SECURITY_PREFIX_LEN, suffix);
  357 + err = __btrfs_setxattr(inode, name, value, len, 0);
  358 + kfree(name);
  359 + }
  360 +
  361 + kfree(suffix);
  362 + kfree(value);
  363 + return err;
332 364 }
... ... @@ -36,5 +36,7 @@
36 36 const void *value, size_t size, int flags);
37 37 extern int btrfs_removexattr(struct dentry *dentry, const char *name);
38 38  
  39 +extern int btrfs_xattr_security_init(struct inode *inode, struct inode *dir);
  40 +
39 41 #endif /* __XATTR__ */