aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--security/selinux/hooks.c22
-rw-r--r--security/selinux/include/security.h2
-rw-r--r--security/selinux/ss/services.c27
3 files changed, 37 insertions, 14 deletions
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c
index 4130d64359a3..85f74f665765 100644
--- a/security/selinux/hooks.c
+++ b/security/selinux/hooks.c
@@ -556,13 +556,15 @@ static int selinux_set_mnt_opts(struct super_block *sb,
556 struct task_security_struct *tsec = current->security; 556 struct task_security_struct *tsec = current->security;
557 struct superblock_security_struct *sbsec = sb->s_security; 557 struct superblock_security_struct *sbsec = sb->s_security;
558 const char *name = sb->s_type->name; 558 const char *name = sb->s_type->name;
559 struct inode *inode = sbsec->sb->s_root->d_inode; 559 struct dentry *root = sb->s_root;
560 struct inode_security_struct *root_isec = inode->i_security; 560 struct inode *root_inode = root->d_inode;
561 struct inode_security_struct *root_isec = root_inode->i_security;
561 u32 fscontext_sid = 0, context_sid = 0, rootcontext_sid = 0; 562 u32 fscontext_sid = 0, context_sid = 0, rootcontext_sid = 0;
562 u32 defcontext_sid = 0; 563 u32 defcontext_sid = 0;
563 char **mount_options = opts->mnt_opts; 564 char **mount_options = opts->mnt_opts;
564 int *flags = opts->mnt_opts_flags; 565 int *flags = opts->mnt_opts_flags;
565 int num_opts = opts->num_mnt_opts; 566 int num_opts = opts->num_mnt_opts;
567 bool can_xattr = false;
566 568
567 mutex_lock(&sbsec->lock); 569 mutex_lock(&sbsec->lock);
568 570
@@ -666,14 +668,24 @@ static int selinux_set_mnt_opts(struct super_block *sb,
666 goto out; 668 goto out;
667 } 669 }
668 670
669 if (strcmp(sb->s_type->name, "proc") == 0) 671 if (strcmp(name, "proc") == 0)
670 sbsec->proc = 1; 672 sbsec->proc = 1;
671 673
674 /*
675 * test if the fs supports xattrs, fs_use might make use of this if the
676 * fs has no definition in policy.
677 */
678 if (root_inode->i_op->getxattr) {
679 rc = root_inode->i_op->getxattr(root, XATTR_NAME_SELINUX, NULL, 0);
680 if (rc >= 0 || rc == -ENODATA)
681 can_xattr = true;
682 }
683
672 /* Determine the labeling behavior to use for this filesystem type. */ 684 /* Determine the labeling behavior to use for this filesystem type. */
673 rc = security_fs_use(sb->s_type->name, &sbsec->behavior, &sbsec->sid); 685 rc = security_fs_use(name, &sbsec->behavior, &sbsec->sid, can_xattr);
674 if (rc) { 686 if (rc) {
675 printk(KERN_WARNING "%s: security_fs_use(%s) returned %d\n", 687 printk(KERN_WARNING "%s: security_fs_use(%s) returned %d\n",
676 __func__, sb->s_type->name, rc); 688 __func__, name, rc);
677 goto out; 689 goto out;
678 } 690 }
679 691
diff --git a/security/selinux/include/security.h b/security/selinux/include/security.h
index 7c543003d653..44cba2e21dcf 100644
--- a/security/selinux/include/security.h
+++ b/security/selinux/include/security.h
@@ -136,7 +136,7 @@ int security_get_allow_unknown(void);
136#define SECURITY_FS_USE_MNTPOINT 6 /* use mountpoint labeling */ 136#define SECURITY_FS_USE_MNTPOINT 6 /* use mountpoint labeling */
137 137
138int security_fs_use(const char *fstype, unsigned int *behavior, 138int security_fs_use(const char *fstype, unsigned int *behavior,
139 u32 *sid); 139 u32 *sid, bool can_xattr);
140 140
141int security_genfs_sid(const char *fstype, char *name, u16 sclass, 141int security_genfs_sid(const char *fstype, char *name, u16 sclass,
142 u32 *sid); 142 u32 *sid);
diff --git a/security/selinux/ss/services.c b/security/selinux/ss/services.c
index b52f923ce680..8e42da120101 100644
--- a/security/selinux/ss/services.c
+++ b/security/selinux/ss/services.c
@@ -1934,7 +1934,8 @@ out:
1934int security_fs_use( 1934int security_fs_use(
1935 const char *fstype, 1935 const char *fstype,
1936 unsigned int *behavior, 1936 unsigned int *behavior,
1937 u32 *sid) 1937 u32 *sid,
1938 bool can_xattr)
1938{ 1939{
1939 int rc = 0; 1940 int rc = 0;
1940 struct ocontext *c; 1941 struct ocontext *c;
@@ -1948,6 +1949,7 @@ int security_fs_use(
1948 c = c->next; 1949 c = c->next;
1949 } 1950 }
1950 1951
1952 /* look for labeling behavior defined in policy */
1951 if (c) { 1953 if (c) {
1952 *behavior = c->v.behavior; 1954 *behavior = c->v.behavior;
1953 if (!c->sid[0]) { 1955 if (!c->sid[0]) {
@@ -1958,14 +1960,23 @@ int security_fs_use(
1958 goto out; 1960 goto out;
1959 } 1961 }
1960 *sid = c->sid[0]; 1962 *sid = c->sid[0];
1963 goto out;
1964 }
1965
1966 /* labeling behavior not in policy, use xattrs if possible */
1967 if (can_xattr) {
1968 *behavior = SECURITY_FS_USE_XATTR;
1969 *sid = SECINITSID_FS;
1970 goto out;
1971 }
1972
1973 /* no behavior in policy and can't use xattrs, try GENFS */
1974 rc = security_genfs_sid(fstype, "/", SECCLASS_DIR, sid);
1975 if (rc) {
1976 *behavior = SECURITY_FS_USE_NONE;
1977 rc = 0;
1961 } else { 1978 } else {
1962 rc = security_genfs_sid(fstype, "/", SECCLASS_DIR, sid); 1979 *behavior = SECURITY_FS_USE_GENFS;
1963 if (rc) {
1964 *behavior = SECURITY_FS_USE_NONE;
1965 rc = 0;
1966 } else {
1967 *behavior = SECURITY_FS_USE_GENFS;
1968 }
1969 } 1980 }
1970 1981
1971out: 1982out: