Skip to content

Commit

Permalink
Btrfs: selinux support
Browse files Browse the repository at this point in the history
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>
  • Loading branch information
Jim Owens authored and Chris Mason committed Feb 4, 2009
1 parent bef62ef commit 0279b4c
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 4 deletions.
23 changes: 19 additions & 4 deletions fs/btrfs/inode.c
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,16 @@ static noinline int cow_file_range(struct inode *inode,
u64 start, u64 end, int *page_started,
unsigned long *nr_written, int unlock);

static int btrfs_init_inode_security(struct inode *inode, struct inode *dir)
{
int err;

err = btrfs_init_acl(inode, dir);
if (!err)
err = btrfs_xattr_security_init(inode, dir);
return err;
}

/*
* a very lame attempt at stopping writes when the FS is 85% full. There
* are countless ways this is incorrect, but it is better than nothing.
Expand Down Expand Up @@ -2037,6 +2047,7 @@ void btrfs_read_locked_inode(struct inode *inode)
inode->i_mapping->backing_dev_info = &root->fs_info->bdi;
break;
default:
inode->i_op = &btrfs_special_inode_operations;
init_special_inode(inode, inode->i_mode, rdev);
break;
}
Expand Down Expand Up @@ -3584,7 +3595,7 @@ static int btrfs_mknod(struct inode *dir, struct dentry *dentry,
if (IS_ERR(inode))
goto out_unlock;

err = btrfs_init_acl(inode, dir);
err = btrfs_init_inode_security(inode, dir);
if (err) {
drop_inode = 1;
goto out_unlock;
Expand Down Expand Up @@ -3647,7 +3658,7 @@ static int btrfs_create(struct inode *dir, struct dentry *dentry,
if (IS_ERR(inode))
goto out_unlock;

err = btrfs_init_acl(inode, dir);
err = btrfs_init_inode_security(inode, dir);
if (err) {
drop_inode = 1;
goto out_unlock;
Expand Down Expand Up @@ -3770,7 +3781,7 @@ static int btrfs_mkdir(struct inode *dir, struct dentry *dentry, int mode)

drop_on_err = 1;

err = btrfs_init_acl(inode, dir);
err = btrfs_init_inode_security(inode, dir);
if (err)
goto out_fail;

Expand Down Expand Up @@ -4732,7 +4743,7 @@ static int btrfs_symlink(struct inode *dir, struct dentry *dentry,
if (IS_ERR(inode))
goto out_unlock;

err = btrfs_init_acl(inode, dir);
err = btrfs_init_inode_security(inode, dir);
if (err) {
drop_inode = 1;
goto out_unlock;
Expand Down Expand Up @@ -5043,4 +5054,8 @@ static struct inode_operations btrfs_symlink_inode_operations = {
.follow_link = page_follow_link_light,
.put_link = page_put_link,
.permission = btrfs_permission,
.setxattr = btrfs_setxattr,
.getxattr = btrfs_getxattr,
.listxattr = btrfs_listxattr,
.removexattr = btrfs_removexattr,
};
32 changes: 32 additions & 0 deletions fs/btrfs/xattr.c
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include <linux/slab.h>
#include <linux/rwsem.h>
#include <linux/xattr.h>
#include <linux/security.h>
#include "ctree.h"
#include "btrfs_inode.h"
#include "transaction.h"
Expand Down Expand Up @@ -330,3 +331,34 @@ int btrfs_removexattr(struct dentry *dentry, const char *name)
return -EOPNOTSUPP;
return __btrfs_setxattr(dentry->d_inode, name, NULL, 0, XATTR_REPLACE);
}

int btrfs_xattr_security_init(struct inode *inode, struct inode *dir)
{
int err;
size_t len;
void *value;
char *suffix;
char *name;

err = security_inode_init_security(inode, dir, &suffix, &value, &len);
if (err) {
if (err == -EOPNOTSUPP)
return 0;
return err;
}

name = kmalloc(XATTR_SECURITY_PREFIX_LEN + strlen(suffix) + 1,
GFP_NOFS);
if (!name) {
err = -ENOMEM;
} else {
strcpy(name, XATTR_SECURITY_PREFIX);
strcpy(name + XATTR_SECURITY_PREFIX_LEN, suffix);
err = __btrfs_setxattr(inode, name, value, len, 0);
kfree(name);
}

kfree(suffix);
kfree(value);
return err;
}
2 changes: 2 additions & 0 deletions fs/btrfs/xattr.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,6 @@ extern int btrfs_setxattr(struct dentry *dentry, const char *name,
const void *value, size_t size, int flags);
extern int btrfs_removexattr(struct dentry *dentry, const char *name);

extern int btrfs_xattr_security_init(struct inode *inode, struct inode *dir);

#endif /* __XATTR__ */

0 comments on commit 0279b4c

Please sign in to comment.