[PATCH 2/2] security,selinux: get rid of security_delete_hooks()

Ondrej Mosnacek omosnace at redhat.com
Tue Jan 7 13:31:54 UTC 2020


The only user is SELinux, which is hereby converted to check the
disabled flag in each hook instead of removing the hooks from the list.

The __lsm_ro_after_init macro is now removed and replaced with
__ro_after_init directly.

This fixes a race condition in SELinux runtime disable, which was
introduced with the switch to hook lists in b1d9e6b0646d ("LSM: Switch
to lists of hooks").

Suggested-by: Stephen Smalley <sds at tycho.nsa.gov>
Signed-off-by: Ondrej Mosnacek <omosnace at redhat.com>
---
 include/linux/lsm_hooks.h    |  31 --
 security/Kconfig             |   5 -
 security/apparmor/lsm.c      |   6 +-
 security/commoncap.c         |   2 +-
 security/loadpin/loadpin.c   |   2 +-
 security/lockdown/lockdown.c |   2 +-
 security/security.c          |   5 +-
 security/selinux/Kconfig     |   6 -
 security/selinux/hooks.c     | 742 ++++++++++++++++++++++++++++++-----
 security/smack/smack_lsm.c   |   4 +-
 security/tomoyo/tomoyo.c     |   6 +-
 security/yama/yama_lsm.c     |   2 +-
 12 files changed, 654 insertions(+), 159 deletions(-)

diff --git a/include/linux/lsm_hooks.h b/include/linux/lsm_hooks.h
index 20d8cf194fb7..5064060ce910 100644
--- a/include/linux/lsm_hooks.h
+++ b/include/linux/lsm_hooks.h
@@ -27,7 +27,6 @@
 
 #include <linux/security.h>
 #include <linux/init.h>
-#include <linux/rculist.h>
 
 /**
  * union security_list_options - Linux Security Module hook function list
@@ -2145,36 +2144,6 @@ extern struct lsm_info __start_early_lsm_info[], __end_early_lsm_info[];
 		__used __section(.early_lsm_info.init)			\
 		__aligned(sizeof(unsigned long))
 
-#ifdef CONFIG_SECURITY_SELINUX_DISABLE
-/*
- * Assuring the safety of deleting a security module is up to
- * the security module involved. This may entail ordering the
- * module's hook list in a particular way, refusing to disable
- * the module once a policy is loaded or any number of other
- * actions better imagined than described.
- *
- * The name of the configuration option reflects the only module
- * that currently uses the mechanism. Any developer who thinks
- * disabling their module is a good idea needs to be at least as
- * careful as the SELinux team.
- */
-static inline void security_delete_hooks(struct security_hook_list *hooks,
-						int count)
-{
-	int i;
-
-	for (i = 0; i < count; i++)
-		hlist_del_rcu(&hooks[i].list);
-}
-#endif /* CONFIG_SECURITY_SELINUX_DISABLE */
-
-/* Currently required to handle SELinux runtime hook disable. */
-#ifdef CONFIG_SECURITY_WRITABLE_HOOKS
-#define __lsm_ro_after_init
-#else
-#define __lsm_ro_after_init	__ro_after_init
-#endif /* CONFIG_SECURITY_WRITABLE_HOOKS */
-
 extern int lsm_inode_alloc(struct inode *inode);
 
 #endif /* ! __LINUX_LSM_HOOKS_H */
diff --git a/security/Kconfig b/security/Kconfig
index 2a1a2d396228..456764990a13 100644
--- a/security/Kconfig
+++ b/security/Kconfig
@@ -32,11 +32,6 @@ config SECURITY
 
 	  If you are unsure how to answer this question, answer N.
 
-config SECURITY_WRITABLE_HOOKS
-	depends on SECURITY
-	bool
-	default n
-
 config SECURITYFS
 	bool "Enable the securityfs filesystem"
 	help
diff --git a/security/apparmor/lsm.c b/security/apparmor/lsm.c
index b621ad74f54a..cd83812a440f 100644
--- a/security/apparmor/lsm.c
+++ b/security/apparmor/lsm.c
@@ -1158,13 +1158,13 @@ static int apparmor_inet_conn_request(struct sock *sk, struct sk_buff *skb,
 /*
  * The cred blob is a pointer to, not an instance of, an aa_task_ctx.
  */
-struct lsm_blob_sizes apparmor_blob_sizes __lsm_ro_after_init = {
+struct lsm_blob_sizes apparmor_blob_sizes __ro_after_init = {
 	.lbs_cred = sizeof(struct aa_task_ctx *),
 	.lbs_file = sizeof(struct aa_file_ctx),
 	.lbs_task = sizeof(struct aa_task_ctx),
 };
 
-static struct security_hook_list apparmor_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list apparmor_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(ptrace_access_check, apparmor_ptrace_access_check),
 	LSM_HOOK_INIT(ptrace_traceme, apparmor_ptrace_traceme),
 	LSM_HOOK_INIT(capget, apparmor_capget),
@@ -1368,7 +1368,7 @@ static const struct kernel_param_ops param_ops_aaintbool = {
 	.get = param_get_aaintbool
 };
 /* Boot time disable flag */
-static int apparmor_enabled __lsm_ro_after_init = 1;
+static int apparmor_enabled __ro_after_init = 1;
 module_param_named(enabled, apparmor_enabled, aaintbool, 0444);
 
 static int __init apparmor_enabled_setup(char *str)
diff --git a/security/commoncap.c b/security/commoncap.c
index f4ee0ae106b2..1471d9a5a9bc 100644
--- a/security/commoncap.c
+++ b/security/commoncap.c
@@ -1339,7 +1339,7 @@ int cap_mmap_file(struct file *file, unsigned long reqprot,
 
 #ifdef CONFIG_SECURITY
 
-static struct security_hook_list capability_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list capability_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(capable, cap_capable),
 	LSM_HOOK_INIT(settime, cap_settime),
 	LSM_HOOK_INIT(ptrace_access_check, cap_ptrace_access_check),
diff --git a/security/loadpin/loadpin.c b/security/loadpin/loadpin.c
index ee5cb944f4ad..9bbc08bee2c0 100644
--- a/security/loadpin/loadpin.c
+++ b/security/loadpin/loadpin.c
@@ -180,7 +180,7 @@ static int loadpin_load_data(enum kernel_load_data_id id)
 	return loadpin_read_file(NULL, (enum kernel_read_file_id) id);
 }
 
-static struct security_hook_list loadpin_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list loadpin_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(sb_free_security, loadpin_sb_free_security),
 	LSM_HOOK_INIT(kernel_read_file, loadpin_read_file),
 	LSM_HOOK_INIT(kernel_load_data, loadpin_load_data),
diff --git a/security/lockdown/lockdown.c b/security/lockdown/lockdown.c
index 5a952617a0eb..8071d0f542c8 100644
--- a/security/lockdown/lockdown.c
+++ b/security/lockdown/lockdown.c
@@ -71,7 +71,7 @@ static int lockdown_is_locked_down(enum lockdown_reason what)
 	return 0;
 }
 
-static struct security_hook_list lockdown_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list lockdown_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(locked_down, lockdown_is_locked_down),
 };
 
diff --git a/security/security.c b/security/security.c
index 2b5473d92416..3138a5d99813 100644
--- a/security/security.c
+++ b/security/security.c
@@ -27,6 +27,7 @@
 #include <linux/backing-dev.h>
 #include <linux/string.h>
 #include <linux/msg.h>
+#include <linux/rculist.h>
 #include <net/flow.h>
 
 #define MAX_LSM_EVM_XATTR	2
@@ -68,14 +69,14 @@ const char *const lockdown_reasons[LOCKDOWN_CONFIDENTIALITY_MAX+1] = {
 	[LOCKDOWN_CONFIDENTIALITY_MAX] = "confidentiality",
 };
 
-struct security_hook_heads security_hook_heads __lsm_ro_after_init;
+struct security_hook_heads security_hook_heads __ro_after_init;
 static BLOCKING_NOTIFIER_HEAD(blocking_lsm_notifier_chain);
 
 static struct kmem_cache *lsm_file_cache;
 static struct kmem_cache *lsm_inode_cache;
 
 char *lsm_names;
-static struct lsm_blob_sizes blob_sizes __lsm_ro_after_init;
+static struct lsm_blob_sizes blob_sizes __ro_after_init;
 
 /* Boot-time LSM user choice */
 static __initdata const char *chosen_lsm_order;
diff --git a/security/selinux/Kconfig b/security/selinux/Kconfig
index 996d35d950f7..caa5711478ad 100644
--- a/security/selinux/Kconfig
+++ b/security/selinux/Kconfig
@@ -26,7 +26,6 @@ config SECURITY_SELINUX_BOOTPARAM
 config SECURITY_SELINUX_DISABLE
 	bool "NSA SELinux runtime disable"
 	depends on SECURITY_SELINUX
-	select SECURITY_WRITABLE_HOOKS
 	default n
 	help
 	  This option enables writing to a selinuxfs node 'disable', which
@@ -37,11 +36,6 @@ config SECURITY_SELINUX_DISABLE
 	  portability across platforms where boot parameters are difficult
 	  to employ.
 
-	  NOTE: selecting this option will disable the '__ro_after_init'
-	  kernel hardening feature for security hooks.   Please consider
-	  using the selinux=0 boot parameter instead of enabling this
-	  option.
-
 	  If you are unsure how to answer this question, answer N.
 
 config SECURITY_SELINUX_DEVELOP
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c
index 47ad4db925cf..9ac2b6b69ff9 100644
--- a/security/selinux/hooks.c
+++ b/security/selinux/hooks.c
@@ -650,13 +650,15 @@ static int selinux_set_mnt_opts(struct super_block *sb,
 {
 	const struct cred *cred = current_cred();
 	struct superblock_security_struct *sbsec = sb->s_security;
-	struct dentry *root = sbsec->sb->s_root;
 	struct selinux_mnt_opts *opts = mnt_opts;
 	struct inode_security_struct *root_isec;
 	u32 fscontext_sid = 0, context_sid = 0, rootcontext_sid = 0;
 	u32 defcontext_sid = 0;
 	int rc = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	mutex_lock(&sbsec->lock);
 
 	if (!selinux_initialized(&selinux_state)) {
@@ -693,7 +695,7 @@ static int selinux_set_mnt_opts(struct super_block *sb,
 	    && !opts)
 		goto out;
 
-	root_isec = backing_inode_security_novalidate(root);
+	root_isec = backing_inode_security_novalidate(sbsec->sb->s_root);
 
 	/*
 	 * parse the mount options, check if they are valid sids.
@@ -919,10 +921,14 @@ static int selinux_sb_clone_mnt_opts(const struct super_block *oldsb,
 	int rc = 0;
 	const struct superblock_security_struct *oldsbsec = oldsb->s_security;
 	struct superblock_security_struct *newsbsec = newsb->s_security;
+	int set_fscontext, set_context, set_rootcontext;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	int set_fscontext =	(oldsbsec->flags & FSCONTEXT_MNT);
-	int set_context =	(oldsbsec->flags & CONTEXT_MNT);
-	int set_rootcontext =	(oldsbsec->flags & ROOTCONTEXT_MNT);
+	set_fscontext =		(oldsbsec->flags & FSCONTEXT_MNT);
+	set_context =		(oldsbsec->flags & CONTEXT_MNT);
+	set_rootcontext =	(oldsbsec->flags & ROOTCONTEXT_MNT);
 
 	/*
 	 * if the parent was able to be mounted it clearly had no special lsm
@@ -1041,6 +1047,9 @@ static int selinux_add_mnt_opt(const char *option, const char *val, int len,
 	int token = Opt_error;
 	int rc, i;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	for (i = 0; i < ARRAY_SIZE(tokens); i++) {
 		if (strcmp(option, tokens[i].name) == 0) {
 			token = tokens[i].opt;
@@ -1100,6 +1109,9 @@ static int selinux_sb_show_options(struct seq_file *m, struct super_block *sb)
 	struct superblock_security_struct *sbsec = sb->s_security;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!(sbsec->flags & SE_SBINITIALIZED))
 		return 0;
 
@@ -2044,22 +2056,27 @@ static inline u32 open_file_to_av(struct file *file)
 
 static int selinux_binder_set_context_mgr(struct task_struct *mgr)
 {
-	u32 mysid = current_sid();
-	u32 mgrsid = task_sid(mgr);
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	return avc_has_perm(&selinux_state,
-			    mysid, mgrsid, SECCLASS_BINDER,
+			    current_sid(), task_sid(mgr), SECCLASS_BINDER,
 			    BINDER__SET_CONTEXT_MGR, NULL);
 }
 
 static int selinux_binder_transaction(struct task_struct *from,
 				      struct task_struct *to)
 {
-	u32 mysid = current_sid();
-	u32 fromsid = task_sid(from);
-	u32 tosid = task_sid(to);
+	u32 mysid, fromsid, tosid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	mysid = current_sid();
+	fromsid = task_sid(from);
+	tosid = task_sid(to);
+
 	if (mysid != fromsid) {
 		rc = avc_has_perm(&selinux_state,
 				  mysid, fromsid, SECCLASS_BINDER,
@@ -2076,11 +2093,12 @@ static int selinux_binder_transaction(struct task_struct *from,
 static int selinux_binder_transfer_binder(struct task_struct *from,
 					  struct task_struct *to)
 {
-	u32 fromsid = task_sid(from);
-	u32 tosid = task_sid(to);
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	return avc_has_perm(&selinux_state,
-			    fromsid, tosid, SECCLASS_BINDER, BINDER__TRANSFER,
+			    task_sid(from), task_sid(to),
+			    SECCLASS_BINDER, BINDER__TRANSFER,
 			    NULL);
 }
 
@@ -2088,13 +2106,18 @@ static int selinux_binder_transfer_file(struct task_struct *from,
 					struct task_struct *to,
 					struct file *file)
 {
-	u32 sid = task_sid(to);
+	u32 sid;
 	struct file_security_struct *fsec = selinux_file(file);
 	struct dentry *dentry = file->f_path.dentry;
 	struct inode_security_struct *isec;
 	struct common_audit_data ad;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = task_sid(to);
+
 	ad.type = LSM_AUDIT_DATA_PATH;
 	ad.u.path = file->f_path;
 
@@ -2126,19 +2149,26 @@ static int selinux_binder_transfer_file(struct task_struct *from,
 static int selinux_ptrace_access_check(struct task_struct *child,
 				     unsigned int mode)
 {
-	u32 sid = current_sid();
-	u32 csid = task_sid(child);
+	u16 cls = SECCLASS_PROCESS;
+	u32 perm = PROCESS__PTRACE;
 
-	if (mode & PTRACE_MODE_READ)
-		return avc_has_perm(&selinux_state,
-				    sid, csid, SECCLASS_FILE, FILE__READ, NULL);
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	if (mode & PTRACE_MODE_READ) {
+		cls = SECCLASS_FILE;
+		perm = FILE__READ;
+	}
 
 	return avc_has_perm(&selinux_state,
-			    sid, csid, SECCLASS_PROCESS, PROCESS__PTRACE, NULL);
+			    current_sid(), task_sid(child), cls, perm, NULL);
 }
 
 static int selinux_ptrace_traceme(struct task_struct *parent)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    task_sid(parent), current_sid(), SECCLASS_PROCESS,
 			    PROCESS__PTRACE, NULL);
@@ -2147,6 +2177,9 @@ static int selinux_ptrace_traceme(struct task_struct *parent)
 static int selinux_capget(struct task_struct *target, kernel_cap_t *effective,
 			  kernel_cap_t *inheritable, kernel_cap_t *permitted)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(target), SECCLASS_PROCESS,
 			    PROCESS__GETCAP, NULL);
@@ -2157,6 +2190,9 @@ static int selinux_capset(struct cred *new, const struct cred *old,
 			  const kernel_cap_t *inheritable,
 			  const kernel_cap_t *permitted)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    cred_sid(old), cred_sid(new), SECCLASS_PROCESS,
 			    PROCESS__SETCAP, NULL);
@@ -2175,6 +2211,9 @@ static int selinux_capset(struct cred *new, const struct cred *old,
 static int selinux_capable(const struct cred *cred, struct user_namespace *ns,
 			   int cap, unsigned int opts)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return cred_has_capability(cred, cap, opts, ns == &init_user_ns);
 }
 
@@ -2186,6 +2225,9 @@ static int selinux_quotactl(int cmds, int type, int id, struct super_block *sb)
 	if (!sb)
 		return 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmds) {
 	case Q_SYNC:
 	case Q_QUOTAON:
@@ -2210,11 +2252,17 @@ static int selinux_quota_on(struct dentry *dentry)
 {
 	const struct cred *cred = current_cred();
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return dentry_has_perm(cred, dentry, FILE__QUOTAON);
 }
 
 static int selinux_syslog(int type)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (type) {
 	case SYSLOG_ACTION_READ_ALL:	/* Read last kernel messages */
 	case SYSLOG_ACTION_SIZE_BUFFER:	/* Return size of the log buffer */
@@ -2248,6 +2296,9 @@ static int selinux_vm_enough_memory(struct mm_struct *mm, long pages)
 {
 	int rc, cap_sys_admin = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	rc = cred_has_capability(current_cred(), CAP_SYS_ADMIN,
 				 CAP_OPT_NOAUDIT, true);
 	if (rc == 0)
@@ -2335,6 +2386,9 @@ static int selinux_bprm_set_creds(struct linux_binprm *bprm)
 	struct inode *inode = file_inode(bprm->file);
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	/* SELinux context only depends on initial program or script and not
 	 * the script interpreter */
 	if (bprm->called_set_creds)
@@ -2505,6 +2559,9 @@ static void selinux_bprm_committing_creds(struct linux_binprm *bprm)
 	struct rlimit *rlim, *initrlim;
 	int rc, i;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	new_tsec = selinux_cred(bprm->cred);
 	if (new_tsec->sid == new_tsec->osid)
 		return;
@@ -2552,6 +2609,9 @@ static void selinux_bprm_committed_creds(struct linux_binprm *bprm)
 	u32 osid, sid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	osid = tsec->osid;
 	sid = tsec->sid;
 
@@ -2592,11 +2652,17 @@ static void selinux_bprm_committed_creds(struct linux_binprm *bprm)
 
 static int selinux_sb_alloc_security(struct super_block *sb)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return superblock_alloc_security(sb);
 }
 
 static void selinux_sb_free_security(struct super_block *sb)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	superblock_free_security(sb);
 }
 
@@ -2622,6 +2688,9 @@ static int selinux_sb_eat_lsm_opts(char *options, void **mnt_opts)
 	bool first = true;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	while (1) {
 		int len = opt_len(from);
 		int token;
@@ -2682,6 +2751,9 @@ static int selinux_sb_remount(struct super_block *sb, void *mnt_opts)
 	u32 sid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!(sbsec->flags & SE_SBINITIALIZED))
 		return 0;
 
@@ -2732,6 +2804,9 @@ static int selinux_sb_kern_mount(struct super_block *sb)
 	const struct cred *cred = current_cred();
 	struct common_audit_data ad;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_DENTRY;
 	ad.u.dentry = sb->s_root;
 	return superblock_has_perm(cred, sb, FILESYSTEM__MOUNT, &ad);
@@ -2742,6 +2817,9 @@ static int selinux_sb_statfs(struct dentry *dentry)
 	const struct cred *cred = current_cred();
 	struct common_audit_data ad;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_DENTRY;
 	ad.u.dentry = dentry->d_sb->s_root;
 	return superblock_has_perm(cred, dentry->d_sb, FILESYSTEM__GETATTR, &ad);
@@ -2755,6 +2833,9 @@ static int selinux_mount(const char *dev_name,
 {
 	const struct cred *cred = current_cred();
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (flags & MS_REMOUNT)
 		return superblock_has_perm(cred, path->dentry->d_sb,
 					   FILESYSTEM__REMOUNT, NULL);
@@ -2766,6 +2847,9 @@ static int selinux_umount(struct vfsmount *mnt, int flags)
 {
 	const struct cred *cred = current_cred();
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return superblock_has_perm(cred, mnt->mnt_sb,
 				   FILESYSTEM__UNMOUNT, NULL);
 }
@@ -2776,6 +2860,9 @@ static int selinux_fs_context_dup(struct fs_context *fc,
 	const struct selinux_mnt_opts *src = src_fc->security;
 	struct selinux_mnt_opts *opts;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!src)
 		return 0;
 
@@ -2828,6 +2915,9 @@ static int selinux_fs_context_parse_param(struct fs_context *fc,
 	struct fs_parse_result result;
 	int opt, rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	opt = fs_parse(fc, &selinux_fs_parameters, param, &result);
 	if (opt < 0)
 		return opt;
@@ -2844,11 +2934,17 @@ static int selinux_fs_context_parse_param(struct fs_context *fc,
 
 static int selinux_inode_alloc_security(struct inode *inode)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return inode_alloc_security(inode);
 }
 
 static void selinux_inode_free_security(struct inode *inode)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	inode_free_security(inode);
 }
 
@@ -2859,6 +2955,9 @@ static int selinux_dentry_init_security(struct dentry *dentry, int mode,
 	u32 newsid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	rc = selinux_determine_inode_label(selinux_cred(current_cred()),
 					   d_inode(dentry->d_parent), name,
 					   inode_mode_to_security_class(mode),
@@ -2879,6 +2978,9 @@ static int selinux_dentry_create_files_as(struct dentry *dentry, int mode,
 	int rc;
 	struct task_security_struct *tsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	rc = selinux_determine_inode_label(selinux_cred(old),
 					   d_inode(dentry->d_parent), name,
 					   inode_mode_to_security_class(mode),
@@ -2902,6 +3004,9 @@ static int selinux_inode_init_security(struct inode *inode, struct inode *dir,
 	int rc;
 	char *context;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	sbsec = dir->i_sb->s_security;
 
 	newsid = tsec->create_sid;
@@ -2941,50 +3046,75 @@ static int selinux_inode_init_security(struct inode *inode, struct inode *dir,
 
 static int selinux_inode_create(struct inode *dir, struct dentry *dentry, umode_t mode)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_create(dir, dentry, SECCLASS_FILE);
 }
 
 static int selinux_inode_link(struct dentry *old_dentry, struct inode *dir, struct dentry *new_dentry)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_link(dir, old_dentry, MAY_LINK);
 }
 
 static int selinux_inode_unlink(struct inode *dir, struct dentry *dentry)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_link(dir, dentry, MAY_UNLINK);
 }
 
 static int selinux_inode_symlink(struct inode *dir, struct dentry *dentry, const char *name)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_create(dir, dentry, SECCLASS_LNK_FILE);
 }
 
 static int selinux_inode_mkdir(struct inode *dir, struct dentry *dentry, umode_t mask)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_create(dir, dentry, SECCLASS_DIR);
 }
 
 static int selinux_inode_rmdir(struct inode *dir, struct dentry *dentry)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_link(dir, dentry, MAY_RMDIR);
 }
 
 static int selinux_inode_mknod(struct inode *dir, struct dentry *dentry, umode_t mode, dev_t dev)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_create(dir, dentry, inode_mode_to_security_class(mode));
 }
 
 static int selinux_inode_rename(struct inode *old_inode, struct dentry *old_dentry,
 				struct inode *new_inode, struct dentry *new_dentry)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return may_rename(old_inode, old_dentry, new_inode, new_dentry);
 }
 
 static int selinux_inode_readlink(struct dentry *dentry)
 {
-	const struct cred *cred = current_cred();
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	return dentry_has_perm(cred, dentry, FILE__READ);
+	return dentry_has_perm(current_cred(), dentry, FILE__READ);
 }
 
 static int selinux_inode_follow_link(struct dentry *dentry, struct inode *inode,
@@ -2995,6 +3125,9 @@ static int selinux_inode_follow_link(struct dentry *dentry, struct inode *inode,
 	struct inode_security_struct *isec;
 	u32 sid;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	validate_creds(cred);
 
 	ad.type = LSM_AUDIT_DATA_DENTRY;
@@ -3040,6 +3173,9 @@ static int selinux_inode_permission(struct inode *inode, int mask)
 	int rc, rc2;
 	u32 audited, denied;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	from_access = mask & MAY_ACCESS;
 	mask &= (MAY_READ|MAY_WRITE|MAY_EXEC|MAY_APPEND);
 
@@ -3086,6 +3222,9 @@ static int selinux_inode_setattr(struct dentry *dentry, struct iattr *iattr)
 	unsigned int ia_valid = iattr->ia_valid;
 	__u32 av = FILE__WRITE;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	/* ATTR_FORCE is just used for ATTR_KILL_S[UG]ID. */
 	if (ia_valid & ATTR_FORCE) {
 		ia_valid &= ~(ATTR_KILL_SUID | ATTR_KILL_SGID | ATTR_MODE |
@@ -3109,6 +3248,9 @@ static int selinux_inode_setattr(struct dentry *dentry, struct iattr *iattr)
 
 static int selinux_inode_getattr(const struct path *path)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return path_has_perm(current_cred(), path, FILE__GETATTR);
 }
 
@@ -3131,9 +3273,12 @@ static int selinux_inode_setxattr(struct dentry *dentry, const char *name,
 	struct inode_security_struct *isec;
 	struct superblock_security_struct *sbsec;
 	struct common_audit_data ad;
-	u32 newsid, sid = current_sid();
+	u32 newsid, sid;
 	int rc = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (strcmp(name, XATTR_NAME_SELINUX)) {
 		rc = cap_inode_setxattr(dentry, name, value, size, flags);
 		if (rc)
@@ -3154,6 +3299,8 @@ static int selinux_inode_setxattr(struct dentry *dentry, const char *name,
 	if (!inode_owner_or_capable(inode))
 		return -EPERM;
 
+	sid = current_sid();
+
 	ad.type = LSM_AUDIT_DATA_DENTRY;
 	ad.u.dentry = dentry;
 
@@ -3225,6 +3372,9 @@ static void selinux_inode_post_setxattr(struct dentry *dentry, const char *name,
 	u32 newsid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	if (strcmp(name, XATTR_NAME_SELINUX)) {
 		/* Not an attribute we recognize, so nothing to do. */
 		return;
@@ -3260,20 +3410,25 @@ static void selinux_inode_post_setxattr(struct dentry *dentry, const char *name,
 
 static int selinux_inode_getxattr(struct dentry *dentry, const char *name)
 {
-	const struct cred *cred = current_cred();
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	return dentry_has_perm(cred, dentry, FILE__GETATTR);
+	return dentry_has_perm(current_cred(), dentry, FILE__GETATTR);
 }
 
 static int selinux_inode_listxattr(struct dentry *dentry)
 {
-	const struct cred *cred = current_cred();
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	return dentry_has_perm(cred, dentry, FILE__GETATTR);
+	return dentry_has_perm(current_cred(), dentry, FILE__GETATTR);
 }
 
 static int selinux_inode_removexattr(struct dentry *dentry, const char *name)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (strcmp(name, XATTR_NAME_SELINUX)) {
 		int rc = cap_inode_removexattr(dentry, name);
 		if (rc)
@@ -3297,6 +3452,9 @@ static int selinux_path_notify(const struct path *path, u64 mask,
 
 	struct common_audit_data ad;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_PATH;
 	ad.u.path = *path;
 
@@ -3345,6 +3503,9 @@ static int selinux_inode_getsecurity(struct inode *inode, const char *name, void
 	char *context = NULL;
 	struct inode_security_struct *isec;
 
+	if (selinux_disabled(&selinux_state))
+		return -EOPNOTSUPP;
+
 	if (strcmp(name, XATTR_SELINUX_SUFFIX))
 		return -EOPNOTSUPP;
 
@@ -3385,6 +3546,9 @@ static int selinux_inode_setsecurity(struct inode *inode, const char *name,
 	u32 newsid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return -EOPNOTSUPP;
+
 	if (strcmp(name, XATTR_SELINUX_SUFFIX))
 		return -EOPNOTSUPP;
 
@@ -3410,6 +3574,10 @@ static int selinux_inode_setsecurity(struct inode *inode, const char *name,
 static int selinux_inode_listsecurity(struct inode *inode, char *buffer, size_t buffer_size)
 {
 	const int len = sizeof(XATTR_NAME_SELINUX);
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (buffer && len <= buffer_size)
 		memcpy(buffer, XATTR_NAME_SELINUX, len);
 	return len;
@@ -3417,16 +3585,24 @@ static int selinux_inode_listsecurity(struct inode *inode, char *buffer, size_t
 
 static void selinux_inode_getsecid(struct inode *inode, u32 *secid)
 {
-	struct inode_security_struct *isec = inode_security_novalidate(inode);
+	struct inode_security_struct *isec;
+
+	if (selinux_disabled(&selinux_state))
+		return;
+
+	isec = inode_security_novalidate(inode);
 	*secid = isec->sid;
 }
 
 static int selinux_inode_copy_up(struct dentry *src, struct cred **new)
 {
-	u32 sid;
+	struct inode_security_struct *isec;
 	struct task_security_struct *tsec;
 	struct cred *new_creds = *new;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (new_creds == NULL) {
 		new_creds = prepare_creds();
 		if (!new_creds)
@@ -3435,14 +3611,17 @@ static int selinux_inode_copy_up(struct dentry *src, struct cred **new)
 
 	tsec = selinux_cred(new_creds);
 	/* Get label from overlay inode and set it in create_sid */
-	selinux_inode_getsecid(d_inode(src), &sid);
-	tsec->create_sid = sid;
+	isec = inode_security_novalidate(d_inode(src));
+	tsec->create_sid = isec->sid;
 	*new = new_creds;
 	return 0;
 }
 
 static int selinux_inode_copy_up_xattr(const char *name)
 {
+	if (selinux_disabled(&selinux_state))
+		return -EOPNOTSUPP;
+
 	/* The copy_up hook above sets the initial context on an inode, but we
 	 * don't then want to overwrite it by blindly copying all the lower
 	 * xattrs up.  Instead, we have to filter out SELinux-related xattrs.
@@ -3466,6 +3645,9 @@ static int selinux_kernfs_init_security(struct kernfs_node *kn_dir,
 	int rc;
 	char *context;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	rc = kernfs_xattr_get(kn_dir, XATTR_NAME_SELINUX, NULL, 0);
 	if (rc == -ENODATA)
 		return 0;
@@ -3537,14 +3719,16 @@ static int selinux_file_permission(struct file *file, int mask)
 	struct inode *inode = file_inode(file);
 	struct file_security_struct *fsec = selinux_file(file);
 	struct inode_security_struct *isec;
-	u32 sid = current_sid();
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	if (!mask)
 		/* No permission to check.  Existence test. */
 		return 0;
 
 	isec = inode_security(inode);
-	if (sid == fsec->sid && fsec->isid == isec->sid &&
+	if (current_sid() == fsec->sid && fsec->isid == isec->sid &&
 	    fsec->pseqno == avc_policy_seqno(&selinux_state))
 		/* No change since file_open check. */
 		return 0;
@@ -3554,6 +3738,9 @@ static int selinux_file_permission(struct file *file, int mask)
 
 static int selinux_file_alloc_security(struct file *file)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return file_alloc_security(file);
 }
 
@@ -3606,6 +3793,9 @@ static int selinux_file_ioctl(struct file *file, unsigned int cmd,
 	const struct cred *cred = current_cred();
 	int error = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case FIONREAD:
 	/* fall through */
@@ -3692,6 +3882,9 @@ static int selinux_mmap_addr(unsigned long addr)
 {
 	int rc = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (addr < CONFIG_LSM_MMAP_MIN_ADDR) {
 		u32 sid = current_sid();
 		rc = avc_has_perm(&selinux_state,
@@ -3708,6 +3901,9 @@ static int selinux_mmap_file(struct file *file, unsigned long reqprot,
 	struct common_audit_data ad;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (file) {
 		ad.type = LSM_AUDIT_DATA_FILE;
 		ad.u.file = file;
@@ -3729,7 +3925,12 @@ static int selinux_file_mprotect(struct vm_area_struct *vma,
 				 unsigned long prot)
 {
 	const struct cred *cred = current_cred();
-	u32 sid = cred_sid(cred);
+	u32 sid;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = cred_sid(cred);
 
 	if (selinux_state.checkreqprot)
 		prot = reqprot;
@@ -3768,9 +3969,10 @@ static int selinux_file_mprotect(struct vm_area_struct *vma,
 
 static int selinux_file_lock(struct file *file, unsigned int cmd)
 {
-	const struct cred *cred = current_cred();
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	return file_has_perm(cred, file, FILE__LOCK);
+	return file_has_perm(current_cred(), file, FILE__LOCK);
 }
 
 static int selinux_file_fcntl(struct file *file, unsigned int cmd,
@@ -3779,6 +3981,9 @@ static int selinux_file_fcntl(struct file *file, unsigned int cmd,
 	const struct cred *cred = current_cred();
 	int err = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case F_SETFL:
 		if ((file->f_flags & O_APPEND) && !(arg & O_APPEND)) {
@@ -3817,6 +4022,9 @@ static void selinux_file_set_fowner(struct file *file)
 {
 	struct file_security_struct *fsec;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	fsec = selinux_file(file);
 	fsec->fown_sid = current_sid();
 }
@@ -3825,10 +4033,12 @@ static int selinux_file_send_sigiotask(struct task_struct *tsk,
 				       struct fown_struct *fown, int signum)
 {
 	struct file *file;
-	u32 sid = task_sid(tsk);
 	u32 perm;
 	struct file_security_struct *fsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	/* struct fown_struct is never outside the context of a struct file */
 	file = container_of(fown, struct file, f_owner);
 
@@ -3840,15 +4050,16 @@ static int selinux_file_send_sigiotask(struct task_struct *tsk,
 		perm = signal_to_av(signum);
 
 	return avc_has_perm(&selinux_state,
-			    fsec->fown_sid, sid,
+			    fsec->fown_sid, task_sid(tsk),
 			    SECCLASS_PROCESS, perm, NULL);
 }
 
 static int selinux_file_receive(struct file *file)
 {
-	const struct cred *cred = current_cred();
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
-	return file_has_perm(cred, file, file_to_av(file));
+	return file_has_perm(current_cred(), file, file_to_av(file));
 }
 
 static int selinux_file_open(struct file *file)
@@ -3856,6 +4067,9 @@ static int selinux_file_open(struct file *file)
 	struct file_security_struct *fsec;
 	struct inode_security_struct *isec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	fsec = selinux_file(file);
 	isec = inode_security(file_inode(file));
 	/*
@@ -3883,7 +4097,12 @@ static int selinux_file_open(struct file *file)
 static int selinux_task_alloc(struct task_struct *task,
 			      unsigned long clone_flags)
 {
-	u32 sid = current_sid();
+	u32 sid;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = current_sid();
 
 	return avc_has_perm(&selinux_state,
 			    sid, sid, SECCLASS_PROCESS, PROCESS__FORK, NULL);
@@ -3898,6 +4117,9 @@ static int selinux_cred_prepare(struct cred *new, const struct cred *old,
 	const struct task_security_struct *old_tsec = selinux_cred(old);
 	struct task_security_struct *tsec = selinux_cred(new);
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	*tsec = *old_tsec;
 	return 0;
 }
@@ -3910,11 +4132,17 @@ static void selinux_cred_transfer(struct cred *new, const struct cred *old)
 	const struct task_security_struct *old_tsec = selinux_cred(old);
 	struct task_security_struct *tsec = selinux_cred(new);
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	*tsec = *old_tsec;
 }
 
 static void selinux_cred_getsecid(const struct cred *c, u32 *secid)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	*secid = cred_sid(c);
 }
 
@@ -3925,11 +4153,13 @@ static void selinux_cred_getsecid(const struct cred *c, u32 *secid)
 static int selinux_kernel_act_as(struct cred *new, u32 secid)
 {
 	struct task_security_struct *tsec = selinux_cred(new);
-	u32 sid = current_sid();
 	int ret;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ret = avc_has_perm(&selinux_state,
-			   sid, secid,
+			   current_sid(), secid,
 			   SECCLASS_KERNEL_SERVICE,
 			   KERNEL_SERVICE__USE_AS_OVERRIDE,
 			   NULL);
@@ -3950,11 +4180,13 @@ static int selinux_kernel_create_files_as(struct cred *new, struct inode *inode)
 {
 	struct inode_security_struct *isec = inode_security(inode);
 	struct task_security_struct *tsec = selinux_cred(new);
-	u32 sid = current_sid();
 	int ret;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ret = avc_has_perm(&selinux_state,
-			   sid, isec->sid,
+			   current_sid(), isec->sid,
 			   SECCLASS_KERNEL_SERVICE,
 			   KERNEL_SERVICE__CREATE_FILES_AS,
 			   NULL);
@@ -3968,6 +4200,9 @@ static int selinux_kernel_module_request(char *kmod_name)
 {
 	struct common_audit_data ad;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_KMOD;
 	ad.u.kmod_name = kmod_name;
 
@@ -4012,35 +4247,37 @@ static int selinux_kernel_module_from_file(struct file *file)
 static int selinux_kernel_read_file(struct file *file,
 				    enum kernel_read_file_id id)
 {
-	int rc = 0;
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	switch (id) {
 	case READING_MODULE:
-		rc = selinux_kernel_module_from_file(file);
-		break;
+		return selinux_kernel_module_from_file(file);
 	default:
 		break;
 	}
-
-	return rc;
+	return 0;
 }
 
 static int selinux_kernel_load_data(enum kernel_load_data_id id)
 {
-	int rc = 0;
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	switch (id) {
 	case LOADING_MODULE:
-		rc = selinux_kernel_module_from_file(NULL);
+		return selinux_kernel_module_from_file(NULL);
 	default:
 		break;
 	}
-
-	return rc;
+	return 0;
 }
 
 static int selinux_task_setpgid(struct task_struct *p, pid_t pgid)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__SETPGID, NULL);
@@ -4048,6 +4285,9 @@ static int selinux_task_setpgid(struct task_struct *p, pid_t pgid)
 
 static int selinux_task_getpgid(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__GETPGID, NULL);
@@ -4055,6 +4295,9 @@ static int selinux_task_getpgid(struct task_struct *p)
 
 static int selinux_task_getsid(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__GETSESSION, NULL);
@@ -4062,11 +4305,17 @@ static int selinux_task_getsid(struct task_struct *p)
 
 static void selinux_task_getsecid(struct task_struct *p, u32 *secid)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	*secid = task_sid(p);
 }
 
 static int selinux_task_setnice(struct task_struct *p, int nice)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__SETSCHED, NULL);
@@ -4074,6 +4323,9 @@ static int selinux_task_setnice(struct task_struct *p, int nice)
 
 static int selinux_task_setioprio(struct task_struct *p, int ioprio)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__SETSCHED, NULL);
@@ -4081,6 +4333,9 @@ static int selinux_task_setioprio(struct task_struct *p, int ioprio)
 
 static int selinux_task_getioprio(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__GETSCHED, NULL);
@@ -4091,6 +4346,9 @@ static int selinux_task_prlimit(const struct cred *cred, const struct cred *tcre
 {
 	u32 av = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!flags)
 		return 0;
 	if (flags & LSM_PRLIMIT_WRITE)
@@ -4107,6 +4365,9 @@ static int selinux_task_setrlimit(struct task_struct *p, unsigned int resource,
 {
 	struct rlimit *old_rlim = p->signal->rlim + resource;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	/* Control the ability to change the hard limit (whether
 	   lowering or raising it), so that the hard limit can
 	   later be used as a safe reset point for the soft limit
@@ -4121,6 +4382,9 @@ static int selinux_task_setrlimit(struct task_struct *p, unsigned int resource,
 
 static int selinux_task_setscheduler(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__SETSCHED, NULL);
@@ -4128,6 +4392,9 @@ static int selinux_task_setscheduler(struct task_struct *p)
 
 static int selinux_task_getscheduler(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__GETSCHED, NULL);
@@ -4135,6 +4402,9 @@ static int selinux_task_getscheduler(struct task_struct *p)
 
 static int selinux_task_movememory(struct task_struct *p)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), task_sid(p), SECCLASS_PROCESS,
 			    PROCESS__SETSCHED, NULL);
@@ -4146,6 +4416,9 @@ static int selinux_task_kill(struct task_struct *p, struct kernel_siginfo *info,
 	u32 secid;
 	u32 perm;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!sig)
 		perm = PROCESS__SIGNULL; /* null signal; existence test */
 	else
@@ -4162,11 +4435,13 @@ static void selinux_task_to_inode(struct task_struct *p,
 				  struct inode *inode)
 {
 	struct inode_security_struct *isec = selinux_inode(inode);
-	u32 sid = task_sid(p);
+
+	if (selinux_disabled(&selinux_state))
+		return;
 
 	spin_lock(&isec->lock);
 	isec->sclass = inode_mode_to_security_class(inode->i_mode);
-	isec->sid = sid;
+	isec->sid = task_sid(p);
 	isec->initialized = LABEL_INITIALIZED;
 	spin_unlock(&isec->lock);
 }
@@ -4506,6 +4781,9 @@ static int selinux_socket_create(int family, int type,
 	if (kern)
 		return 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	secclass = socket_type_to_security_class(family, type, protocol);
 	rc = socket_sockcreate_sid(tsec, secclass, &newsid);
 	if (rc)
@@ -4525,6 +4803,9 @@ static int selinux_socket_post_create(struct socket *sock, int family,
 	u32 sid = SECINITSID_KERNEL;
 	int err = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!kern) {
 		err = socket_sockcreate_sid(tsec, sclass, &sid);
 		if (err)
@@ -4555,6 +4836,9 @@ static int selinux_socket_socketpair(struct socket *socka,
 	struct sk_security_struct *sksec_a = socka->sk->sk_security;
 	struct sk_security_struct *sksec_b = sockb->sk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	sksec_a->peer_sid = sksec_b->sid;
 	sksec_b->peer_sid = sksec_a->sid;
 
@@ -4572,6 +4856,9 @@ static int selinux_socket_bind(struct socket *sock, struct sockaddr *address, in
 	u16 family;
 	int err;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = sock_has_perm(sk, SOCKET__BIND);
 	if (err)
 		goto out;
@@ -4796,6 +5083,9 @@ static int selinux_socket_connect(struct socket *sock,
 	int err;
 	struct sock *sk = sock->sk;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = selinux_socket_connect_helper(sock, address, addrlen);
 	if (err)
 		return err;
@@ -4805,6 +5095,9 @@ static int selinux_socket_connect(struct socket *sock,
 
 static int selinux_socket_listen(struct socket *sock, int backlog)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__LISTEN);
 }
 
@@ -4816,6 +5109,9 @@ static int selinux_socket_accept(struct socket *sock, struct socket *newsock)
 	u16 sclass;
 	u32 sid;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = sock_has_perm(sock->sk, SOCKET__ACCEPT);
 	if (err)
 		return err;
@@ -4837,22 +5133,34 @@ static int selinux_socket_accept(struct socket *sock, struct socket *newsock)
 static int selinux_socket_sendmsg(struct socket *sock, struct msghdr *msg,
 				  int size)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__WRITE);
 }
 
 static int selinux_socket_recvmsg(struct socket *sock, struct msghdr *msg,
 				  int size, int flags)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__READ);
 }
 
 static int selinux_socket_getsockname(struct socket *sock)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__GETATTR);
 }
 
 static int selinux_socket_getpeername(struct socket *sock)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__GETATTR);
 }
 
@@ -4860,6 +5168,9 @@ static int selinux_socket_setsockopt(struct socket *sock, int level, int optname
 {
 	int err;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = sock_has_perm(sock->sk, SOCKET__SETOPT);
 	if (err)
 		return err;
@@ -4870,11 +5181,17 @@ static int selinux_socket_setsockopt(struct socket *sock, int level, int optname
 static int selinux_socket_getsockopt(struct socket *sock, int level,
 				     int optname)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__GETOPT);
 }
 
 static int selinux_socket_shutdown(struct socket *sock, int how)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return sock_has_perm(sock->sk, SOCKET__SHUTDOWN);
 }
 
@@ -4889,6 +5206,9 @@ static int selinux_socket_unix_stream_connect(struct sock *sock,
 	struct lsm_network_audit net = {0,};
 	int err;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_NET;
 	ad.u.net = &net;
 	ad.u.net->sk = other;
@@ -4921,6 +5241,9 @@ static int selinux_socket_unix_may_send(struct socket *sock,
 	struct common_audit_data ad;
 	struct lsm_network_audit net = {0,};
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ad.type = LSM_AUDIT_DATA_NET;
 	ad.u.net = &net;
 	ad.u.net->sk = other->sk;
@@ -4994,13 +5317,15 @@ static int selinux_socket_sock_rcv_skb(struct sock *sk, struct sk_buff *skb)
 	int err;
 	struct sk_security_struct *sksec = sk->sk_security;
 	u16 family = sk->sk_family;
-	u32 sk_sid = sksec->sid;
 	struct common_audit_data ad;
 	struct lsm_network_audit net = {0,};
 	char *addrp;
 	u8 secmark_active;
 	u8 peerlbl_active;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (family != PF_INET && family != PF_INET6)
 		return 0;
 
@@ -5041,7 +5366,7 @@ static int selinux_socket_sock_rcv_skb(struct sock *sk, struct sk_buff *skb)
 			return err;
 		}
 		err = avc_has_perm(&selinux_state,
-				   sk_sid, peer_sid, SECCLASS_PEER,
+				   sksec->sid, peer_sid, SECCLASS_PEER,
 				   PEER__RECV, &ad);
 		if (err) {
 			selinux_netlbl_err(skb, family, err, 0);
@@ -5051,7 +5376,7 @@ static int selinux_socket_sock_rcv_skb(struct sock *sk, struct sk_buff *skb)
 
 	if (secmark_active) {
 		err = avc_has_perm(&selinux_state,
-				   sk_sid, skb->secmark, SECCLASS_PACKET,
+				   sksec->sid, skb->secmark, SECCLASS_PACKET,
 				   PACKET__RECV, &ad);
 		if (err)
 			return err;
@@ -5069,6 +5394,9 @@ static int selinux_socket_getpeersec_stream(struct socket *sock, char __user *op
 	struct sk_security_struct *sksec = sock->sk->sk_security;
 	u32 peer_sid = SECSID_NULL;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (sksec->sclass == SECCLASS_UNIX_STREAM_SOCKET ||
 	    sksec->sclass == SECCLASS_TCP_SOCKET ||
 	    sksec->sclass == SECCLASS_SCTP_SOCKET)
@@ -5102,6 +5430,9 @@ static int selinux_socket_getpeersec_dgram(struct socket *sock, struct sk_buff *
 	u16 family;
 	struct inode_security_struct *isec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (skb && skb->protocol == htons(ETH_P_IP))
 		family = PF_INET;
 	else if (skb && skb->protocol == htons(ETH_P_IPV6))
@@ -5128,6 +5459,9 @@ static int selinux_sk_alloc_security(struct sock *sk, int family, gfp_t priority
 {
 	struct sk_security_struct *sksec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	sksec = kzalloc(sizeof(*sksec), priority);
 	if (!sksec)
 		return -ENOMEM;
@@ -5145,6 +5479,9 @@ static void selinux_sk_free_security(struct sock *sk)
 {
 	struct sk_security_struct *sksec = sk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	sk->sk_security = NULL;
 	selinux_netlbl_sk_security_free(sksec);
 	kfree(sksec);
@@ -5155,6 +5492,9 @@ static void selinux_sk_clone_security(const struct sock *sk, struct sock *newsk)
 	struct sk_security_struct *sksec = sk->sk_security;
 	struct sk_security_struct *newsksec = newsk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	newsksec->sid = sksec->sid;
 	newsksec->peer_sid = sksec->peer_sid;
 	newsksec->sclass = sksec->sclass;
@@ -5164,6 +5504,9 @@ static void selinux_sk_clone_security(const struct sock *sk, struct sock *newsk)
 
 static void selinux_sk_getsecid(struct sock *sk, u32 *secid)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	if (!sk)
 		*secid = SECINITSID_ANY_SOCKET;
 	else {
@@ -5175,10 +5518,14 @@ static void selinux_sk_getsecid(struct sock *sk, u32 *secid)
 
 static void selinux_sock_graft(struct sock *sk, struct socket *parent)
 {
-	struct inode_security_struct *isec =
-		inode_security_novalidate(SOCK_INODE(parent));
+	struct inode_security_struct *isec;
 	struct sk_security_struct *sksec = sk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
+	isec = inode_security_novalidate(SOCK_INODE(parent));
+
 	if (sk->sk_family == PF_INET || sk->sk_family == PF_INET6 ||
 	    sk->sk_family == PF_UNIX)
 		isec->sid = sksec->sid;
@@ -5200,6 +5547,9 @@ static int selinux_sctp_assoc_request(struct sctp_endpoint *ep,
 	u32 conn_sid;
 	int err = 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!selinux_policycap_extsockclass())
 		return 0;
 
@@ -5270,6 +5620,9 @@ static int selinux_sctp_bind_connect(struct sock *sk, int optname,
 	struct sockaddr *addr;
 	struct socket *sock;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (!selinux_policycap_extsockclass())
 		return 0;
 
@@ -5346,6 +5699,9 @@ static void selinux_sctp_sk_clone(struct sctp_endpoint *ep, struct sock *sk,
 	struct sk_security_struct *sksec = sk->sk_security;
 	struct sk_security_struct *newsksec = newsk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	/* If policy does not support SECCLASS_SCTP_SOCKET then call
 	 * the non-sctp clone version.
 	 */
@@ -5367,6 +5723,9 @@ static int selinux_inet_conn_request(struct sock *sk, struct sk_buff *skb,
 	u32 connsid;
 	u32 peersid;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = selinux_skb_peerlbl_sid(skb, family, &peersid);
 	if (err)
 		return err;
@@ -5384,6 +5743,9 @@ static void selinux_inet_csk_clone(struct sock *newsk,
 {
 	struct sk_security_struct *newsksec = newsk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	newsksec->sid = req->secid;
 	newsksec->peer_sid = req->peer_secid;
 	/* NOTE: Ideally, we should also get the isec->sid for the
@@ -5401,6 +5763,9 @@ static void selinux_inet_conn_established(struct sock *sk, struct sk_buff *skb)
 	u16 family = sk->sk_family;
 	struct sk_security_struct *sksec = sk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	/* handle mapped IPv4 packets arriving via IPv6 sockets */
 	if (family == PF_INET6 && skb->protocol == htons(ETH_P_IP))
 		family = PF_INET;
@@ -5413,6 +5778,9 @@ static int selinux_secmark_relabel_packet(u32 sid)
 	const struct task_security_struct *__tsec;
 	u32 tsid;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	__tsec = selinux_cred(current_cred());
 	tsid = __tsec->sid;
 
@@ -5423,17 +5791,26 @@ static int selinux_secmark_relabel_packet(u32 sid)
 
 static void selinux_secmark_refcount_inc(void)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	atomic_inc(&selinux_secmark_refcount);
 }
 
 static void selinux_secmark_refcount_dec(void)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	atomic_dec(&selinux_secmark_refcount);
 }
 
 static void selinux_req_classify_flow(const struct request_sock *req,
 				      struct flowi *fl)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	fl->flowi_secid = req->secid;
 }
 
@@ -5441,6 +5818,9 @@ static int selinux_tun_dev_alloc_security(void **security)
 {
 	struct tun_security_struct *tunsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	tunsec = kzalloc(sizeof(*tunsec), GFP_KERNEL);
 	if (!tunsec)
 		return -ENOMEM;
@@ -5452,12 +5832,20 @@ static int selinux_tun_dev_alloc_security(void **security)
 
 static void selinux_tun_dev_free_security(void *security)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	kfree(security);
 }
 
 static int selinux_tun_dev_create(void)
 {
-	u32 sid = current_sid();
+	u32 sid;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = current_sid();
 
 	/* we aren't taking into account the "sockcreate" SID since the socket
 	 * that is being created here is not a socket in the traditional sense,
@@ -5475,6 +5863,9 @@ static int selinux_tun_dev_attach_queue(void *security)
 {
 	struct tun_security_struct *tunsec = security;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return avc_has_perm(&selinux_state,
 			    current_sid(), tunsec->sid, SECCLASS_TUN_SOCKET,
 			    TUN_SOCKET__ATTACH_QUEUE, NULL);
@@ -5485,6 +5876,9 @@ static int selinux_tun_dev_attach(struct sock *sk, void *security)
 	struct tun_security_struct *tunsec = security;
 	struct sk_security_struct *sksec = sk->sk_security;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	/* we don't currently perform any NetLabel based labeling here and it
 	 * isn't clear that we would want to do so anyway; while we could apply
 	 * labeling without the support of the TUN user the resulting labeled
@@ -5501,8 +5895,13 @@ static int selinux_tun_dev_attach(struct sock *sk, void *security)
 static int selinux_tun_dev_open(void *security)
 {
 	struct tun_security_struct *tunsec = security;
-	u32 sid = current_sid();
 	int err;
+	u32 sid;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = current_sid();
 
 	err = avc_has_perm(&selinux_state,
 			   sid, tunsec->sid, SECCLASS_TUN_SOCKET,
@@ -5885,6 +6284,9 @@ static unsigned int selinux_ipv6_postroute(void *priv,
 
 static int selinux_netlink_send(struct sock *sk, struct sk_buff *skb)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return selinux_nlmsg_perm(sk, skb);
 }
 
@@ -5922,6 +6324,9 @@ static int ipc_has_perm(struct kern_ipc_perm *ipc_perms,
 
 static int selinux_msg_msg_alloc_security(struct msg_msg *msg)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return msg_msg_alloc_security(msg);
 }
 
@@ -5930,9 +6335,11 @@ static int selinux_msg_queue_alloc_security(struct kern_ipc_perm *msq)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	isec = selinux_ipc(msq);
 	ipc_init_security(isec, SECCLASS_MSGQ);
 
@@ -5940,7 +6347,7 @@ static int selinux_msg_queue_alloc_security(struct kern_ipc_perm *msq)
 	ad.u.ipc_id = msq->key;
 
 	rc = avc_has_perm(&selinux_state,
-			  sid, isec->sid, SECCLASS_MSGQ,
+			  current_sid(), isec->sid, SECCLASS_MSGQ,
 			  MSGQ__CREATE, &ad);
 	return rc;
 }
@@ -5949,7 +6356,9 @@ static int selinux_msg_queue_associate(struct kern_ipc_perm *msq, int msqflg)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	isec = selinux_ipc(msq);
 
@@ -5957,7 +6366,7 @@ static int selinux_msg_queue_associate(struct kern_ipc_perm *msq, int msqflg)
 	ad.u.ipc_id = msq->key;
 
 	return avc_has_perm(&selinux_state,
-			    sid, isec->sid, SECCLASS_MSGQ,
+			    current_sid(), isec->sid, SECCLASS_MSGQ,
 			    MSGQ__ASSOCIATE, &ad);
 }
 
@@ -5966,6 +6375,9 @@ static int selinux_msg_queue_msgctl(struct kern_ipc_perm *msq, int cmd)
 	int err;
 	int perms;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case IPC_INFO:
 	case MSG_INFO:
@@ -5997,9 +6409,14 @@ static int selinux_msg_queue_msgsnd(struct kern_ipc_perm *msq, struct msg_msg *m
 	struct ipc_security_struct *isec;
 	struct msg_security_struct *msec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
+	u32 sid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = current_sid();
+
 	isec = selinux_ipc(msq);
 	msec = selinux_msg_msg(msg);
 
@@ -6045,9 +6462,14 @@ static int selinux_msg_queue_msgrcv(struct kern_ipc_perm *msq, struct msg_msg *m
 	struct ipc_security_struct *isec;
 	struct msg_security_struct *msec;
 	struct common_audit_data ad;
-	u32 sid = task_sid(target);
+	u32 sid;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = task_sid(target);
+
 	isec = selinux_ipc(msq);
 	msec = selinux_msg_msg(msg);
 
@@ -6069,9 +6491,11 @@ static int selinux_shm_alloc_security(struct kern_ipc_perm *shp)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	isec = selinux_ipc(shp);
 	ipc_init_security(isec, SECCLASS_SHM);
 
@@ -6079,8 +6503,8 @@ static int selinux_shm_alloc_security(struct kern_ipc_perm *shp)
 	ad.u.ipc_id = shp->key;
 
 	rc = avc_has_perm(&selinux_state,
-			  sid, isec->sid, SECCLASS_SHM,
-			  SHM__CREATE, &ad);
+			  current_sid(), isec->sid,
+			  SECCLASS_SHM, SHM__CREATE, &ad);
 	return rc;
 }
 
@@ -6088,7 +6512,9 @@ static int selinux_shm_associate(struct kern_ipc_perm *shp, int shmflg)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	isec = selinux_ipc(shp);
 
@@ -6096,8 +6522,8 @@ static int selinux_shm_associate(struct kern_ipc_perm *shp, int shmflg)
 	ad.u.ipc_id = shp->key;
 
 	return avc_has_perm(&selinux_state,
-			    sid, isec->sid, SECCLASS_SHM,
-			    SHM__ASSOCIATE, &ad);
+			    current_sid(), isec->sid,
+			    SECCLASS_SHM, SHM__ASSOCIATE, &ad);
 }
 
 /* Note, at this point, shp is locked down */
@@ -6106,6 +6532,9 @@ static int selinux_shm_shmctl(struct kern_ipc_perm *shp, int cmd)
 	int perms;
 	int err;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case IPC_INFO:
 	case SHM_INFO:
@@ -6141,6 +6570,9 @@ static int selinux_shm_shmat(struct kern_ipc_perm *shp,
 {
 	u32 perms;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (shmflg & SHM_RDONLY)
 		perms = SHM__READ;
 	else
@@ -6154,9 +6586,11 @@ static int selinux_sem_alloc_security(struct kern_ipc_perm *sma)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	isec = selinux_ipc(sma);
 	ipc_init_security(isec, SECCLASS_SEM);
 
@@ -6164,8 +6598,8 @@ static int selinux_sem_alloc_security(struct kern_ipc_perm *sma)
 	ad.u.ipc_id = sma->key;
 
 	rc = avc_has_perm(&selinux_state,
-			  sid, isec->sid, SECCLASS_SEM,
-			  SEM__CREATE, &ad);
+			  current_sid(), isec->sid,
+			  SECCLASS_SEM, SEM__CREATE, &ad);
 	return rc;
 }
 
@@ -6173,7 +6607,9 @@ static int selinux_sem_associate(struct kern_ipc_perm *sma, int semflg)
 {
 	struct ipc_security_struct *isec;
 	struct common_audit_data ad;
-	u32 sid = current_sid();
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
 
 	isec = selinux_ipc(sma);
 
@@ -6181,8 +6617,8 @@ static int selinux_sem_associate(struct kern_ipc_perm *sma, int semflg)
 	ad.u.ipc_id = sma->key;
 
 	return avc_has_perm(&selinux_state,
-			    sid, isec->sid, SECCLASS_SEM,
-			    SEM__ASSOCIATE, &ad);
+			    current_sid(), isec->sid,
+			    SECCLASS_SEM, SEM__ASSOCIATE, &ad);
 }
 
 /* Note, at this point, sma is locked down */
@@ -6191,6 +6627,9 @@ static int selinux_sem_semctl(struct kern_ipc_perm *sma, int cmd)
 	int err;
 	u32 perms;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case IPC_INFO:
 	case SEM_INFO:
@@ -6235,6 +6674,9 @@ static int selinux_sem_semop(struct kern_ipc_perm *sma,
 {
 	u32 perms;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (alter)
 		perms = SEM__READ | SEM__WRITE;
 	else
@@ -6247,7 +6689,9 @@ static int selinux_ipc_permission(struct kern_ipc_perm *ipcp, short flag)
 {
 	u32 av = 0;
 
-	av = 0;
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (flag & S_IRUGO)
 		av |= IPC__UNIX_READ;
 	if (flag & S_IWUGO)
@@ -6261,12 +6705,17 @@ static int selinux_ipc_permission(struct kern_ipc_perm *ipcp, short flag)
 
 static void selinux_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid)
 {
-	struct ipc_security_struct *isec = selinux_ipc(ipcp);
-	*secid = isec->sid;
+	if (selinux_disabled(&selinux_state))
+		return;
+
+	*secid = selinux_ipc(ipcp)->sid;
 }
 
 static void selinux_d_instantiate(struct dentry *dentry, struct inode *inode)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	if (inode)
 		inode_doinit_with_dentry(inode, dentry);
 }
@@ -6279,6 +6728,9 @@ static int selinux_getprocattr(struct task_struct *p,
 	int error;
 	unsigned len;
 
+	if (selinux_disabled(&selinux_state))
+		return -EINVAL;
+
 	rcu_read_lock();
 	__tsec = selinux_cred(__task_cred(p));
 
@@ -6325,10 +6777,15 @@ static int selinux_setprocattr(const char *name, void *value, size_t size)
 {
 	struct task_security_struct *tsec;
 	struct cred *new;
-	u32 mysid = current_sid(), sid = 0, ptsid;
+	u32 mysid, sid = 0, ptsid;
 	int error;
 	char *str = value;
 
+	if (selinux_disabled(&selinux_state))
+		return -EINVAL;
+
+	mysid = current_sid();
+
 	/*
 	 * Basic control over ability to set these attributes at all.
 	 */
@@ -6466,17 +6923,26 @@ abort_change:
 
 static int selinux_ismaclabel(const char *name)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return (strcmp(name, XATTR_SELINUX_SUFFIX) == 0);
 }
 
 static int selinux_secid_to_secctx(u32 secid, char **secdata, u32 *seclen)
 {
+	if (selinux_disabled(&selinux_state))
+		return -EOPNOTSUPP;
+
 	return security_sid_to_context(&selinux_state, secid,
 				       secdata, seclen);
 }
 
 static int selinux_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return security_context_to_sid(&selinux_state, secdata, seclen,
 				       secid, GFP_KERNEL);
 }
@@ -6490,6 +6956,9 @@ static void selinux_inode_invalidate_secctx(struct inode *inode)
 {
 	struct inode_security_struct *isec = selinux_inode(inode);
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	spin_lock(&isec->lock);
 	isec->initialized = LABEL_INVALID;
 	spin_unlock(&isec->lock);
@@ -6511,6 +6980,9 @@ static int selinux_inode_notifysecctx(struct inode *inode, void *ctx, u32 ctxlen
  */
 static int selinux_inode_setsecctx(struct dentry *dentry, void *ctx, u32 ctxlen)
 {
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	return __vfs_setxattr_noperm(dentry, XATTR_NAME_SELINUX, ctx, ctxlen, 0);
 }
 
@@ -6532,6 +7004,9 @@ static int selinux_key_alloc(struct key *k, const struct cred *cred,
 	const struct task_security_struct *tsec;
 	struct key_security_struct *ksec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	ksec = kzalloc(sizeof(struct key_security_struct), GFP_KERNEL);
 	if (!ksec)
 		return -ENOMEM;
@@ -6550,6 +7025,9 @@ static void selinux_key_free(struct key *k)
 {
 	struct key_security_struct *ksec = k->security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	k->security = NULL;
 	kfree(ksec);
 }
@@ -6568,6 +7046,9 @@ static int selinux_key_permission(key_ref_t key_ref,
 	if (perm == 0)
 		return 0;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	sid = cred_sid(cred);
 
 	key = key_ref_to_ptr(key_ref);
@@ -6584,6 +7065,9 @@ static int selinux_key_getsecurity(struct key *key, char **_buffer)
 	unsigned len;
 	int rc;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	rc = security_sid_to_context(&selinux_state, ksec->sid,
 				     &context, &len);
 	if (!rc)
@@ -6602,6 +7086,9 @@ static int selinux_ib_pkey_access(void *ib_sec, u64 subnet_prefix, u16 pkey_val)
 	struct ib_security_struct *sec = ib_sec;
 	struct lsm_ibpkey_audit ibpkey;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = sel_ib_pkey_sid(subnet_prefix, pkey_val, &sid);
 	if (err)
 		return err;
@@ -6625,6 +7112,9 @@ static int selinux_ib_endport_manage_subnet(void *ib_sec, const char *dev_name,
 	struct ib_security_struct *sec = ib_sec;
 	struct lsm_ibendport_audit ibendport;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	err = security_ib_endport_sid(&selinux_state, dev_name, port_num,
 				      &sid);
 
@@ -6645,6 +7135,9 @@ static int selinux_ib_alloc_security(void **ib_sec)
 {
 	struct ib_security_struct *sec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	sec = kzalloc(sizeof(*sec), GFP_KERNEL);
 	if (!sec)
 		return -ENOMEM;
@@ -6656,6 +7149,9 @@ static int selinux_ib_alloc_security(void **ib_sec)
 
 static void selinux_ib_free_security(void *ib_sec)
 {
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	kfree(ib_sec);
 }
 #endif
@@ -6667,6 +7163,9 @@ static int selinux_bpf(int cmd, union bpf_attr *attr,
 	u32 sid = current_sid();
 	int ret;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	switch (cmd) {
 	case BPF_MAP_CREATE:
 		ret = avc_has_perm(&selinux_state,
@@ -6734,23 +7233,27 @@ static int bpf_fd_pass(struct file *file, u32 sid)
 
 static int selinux_bpf_map(struct bpf_map *map, fmode_t fmode)
 {
-	u32 sid = current_sid();
 	struct bpf_security_struct *bpfsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	bpfsec = map->security;
 	return avc_has_perm(&selinux_state,
-			    sid, bpfsec->sid, SECCLASS_BPF,
+			    current_sid(), bpfsec->sid, SECCLASS_BPF,
 			    bpf_map_fmode_to_av(fmode), NULL);
 }
 
 static int selinux_bpf_prog(struct bpf_prog *prog)
 {
-	u32 sid = current_sid();
 	struct bpf_security_struct *bpfsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	bpfsec = prog->aux->security;
 	return avc_has_perm(&selinux_state,
-			    sid, bpfsec->sid, SECCLASS_BPF,
+			    current_sid(), bpfsec->sid, SECCLASS_BPF,
 			    BPF__PROG_RUN, NULL);
 }
 
@@ -6758,6 +7261,9 @@ static int selinux_bpf_map_alloc(struct bpf_map *map)
 {
 	struct bpf_security_struct *bpfsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	bpfsec = kzalloc(sizeof(*bpfsec), GFP_KERNEL);
 	if (!bpfsec)
 		return -ENOMEM;
@@ -6772,6 +7278,9 @@ static void selinux_bpf_map_free(struct bpf_map *map)
 {
 	struct bpf_security_struct *bpfsec = map->security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	map->security = NULL;
 	kfree(bpfsec);
 }
@@ -6780,6 +7289,9 @@ static int selinux_bpf_prog_alloc(struct bpf_prog_aux *aux)
 {
 	struct bpf_security_struct *bpfsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	bpfsec = kzalloc(sizeof(*bpfsec), GFP_KERNEL);
 	if (!bpfsec)
 		return -ENOMEM;
@@ -6794,6 +7306,9 @@ static void selinux_bpf_prog_free(struct bpf_prog_aux *aux)
 {
 	struct bpf_security_struct *bpfsec = aux->security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	aux->security = NULL;
 	kfree(bpfsec);
 }
@@ -6802,11 +7317,14 @@ static void selinux_bpf_prog_free(struct bpf_prog_aux *aux)
 static int selinux_lockdown(enum lockdown_reason what)
 {
 	struct common_audit_data ad;
-	u32 sid = current_sid();
+	u32 sid;
 	int invalid_reason = (what <= LOCKDOWN_NONE) ||
 			     (what == LOCKDOWN_INTEGRITY_MAX) ||
 			     (what >= LOCKDOWN_CONFIDENTIALITY_MAX);
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	if (WARN(invalid_reason, "Invalid lockdown reason")) {
 		audit_log(audit_context(),
 			  GFP_ATOMIC, AUDIT_SELINUX_ERR,
@@ -6814,6 +7332,8 @@ static int selinux_lockdown(enum lockdown_reason what)
 		return -EINVAL;
 	}
 
+	sid = current_sid();
+
 	ad.type = LSM_AUDIT_DATA_LOCKDOWN;
 	ad.u.reason = what;
 
@@ -6827,7 +7347,7 @@ static int selinux_lockdown(enum lockdown_reason what)
 				    LOCKDOWN__CONFIDENTIALITY, &ad);
 }
 
-struct lsm_blob_sizes selinux_blob_sizes __lsm_ro_after_init = {
+struct lsm_blob_sizes selinux_blob_sizes __ro_after_init = {
 	.lbs_cred = sizeof(struct task_security_struct),
 	.lbs_file = sizeof(struct file_security_struct),
 	.lbs_inode = sizeof(struct inode_security_struct),
@@ -6838,7 +7358,12 @@ struct lsm_blob_sizes selinux_blob_sizes __lsm_ro_after_init = {
 #ifdef CONFIG_PERF_EVENTS
 static int selinux_perf_event_open(struct perf_event_attr *attr, int type)
 {
-	u32 requested, sid = current_sid();
+	u32 requested, sid;
+
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	sid = current_sid();
 
 	if (type == PERF_SECURITY_OPEN)
 		requested = PERF_EVENT__OPEN;
@@ -6859,6 +7384,9 @@ static int selinux_perf_event_alloc(struct perf_event *event)
 {
 	struct perf_event_security_struct *perfsec;
 
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
 	perfsec = kzalloc(sizeof(*perfsec), GFP_KERNEL);
 	if (!perfsec)
 		return -ENOMEM;
@@ -6873,6 +7401,9 @@ static void selinux_perf_event_free(struct perf_event *event)
 {
 	struct perf_event_security_struct *perfsec = event->security;
 
+	if (selinux_disabled(&selinux_state))
+		return;
+
 	event->security = NULL;
 	kfree(perfsec);
 }
@@ -6880,23 +7411,27 @@ static void selinux_perf_event_free(struct perf_event *event)
 static int selinux_perf_event_read(struct perf_event *event)
 {
 	struct perf_event_security_struct *perfsec = event->security;
-	u32 sid = current_sid();
 
-	return avc_has_perm(&selinux_state, sid, perfsec->sid,
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	return avc_has_perm(&selinux_state, current_sid(), perfsec->sid,
 			    SECCLASS_PERF_EVENT, PERF_EVENT__READ, NULL);
 }
 
 static int selinux_perf_event_write(struct perf_event *event)
 {
 	struct perf_event_security_struct *perfsec = event->security;
-	u32 sid = current_sid();
 
-	return avc_has_perm(&selinux_state, sid, perfsec->sid,
+	if (selinux_disabled(&selinux_state))
+		return 0;
+
+	return avc_has_perm(&selinux_state, current_sid(), perfsec->sid,
 			    SECCLASS_PERF_EVENT, PERF_EVENT__WRITE, NULL);
 }
 #endif
 
-static struct security_hook_list selinux_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list selinux_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(binder_set_context_mgr, selinux_binder_set_context_mgr),
 	LSM_HOOK_INIT(binder_transaction, selinux_binder_transaction),
 	LSM_HOOK_INIT(binder_transfer_binder, selinux_binder_transfer_binder),
@@ -7315,18 +7850,19 @@ int selinux_disable(struct selinux_state *state)
 		return -EINVAL;
 	}
 
+	/*
+	 * Unregister netfilter hooks (must be done before
+	 * selinux_mark_disabled()).
+	 */
+	selinux_nf_ip_exit();
+
 	selinux_mark_disabled(state);
 
 	pr_info("SELinux:  Disabled at runtime.\n");
 
-	security_delete_hooks(selinux_hooks, ARRAY_SIZE(selinux_hooks));
-
 	/* Try to destroy the avc node cache */
 	avc_disable();
 
-	/* Unregister netfilter hooks. */
-	selinux_nf_ip_exit();
-
 	/* Unregister selinuxfs. */
 	exit_sel_fs();
 
diff --git a/security/smack/smack_lsm.c b/security/smack/smack_lsm.c
index ecea41ce919b..de50c69846e0 100644
--- a/security/smack/smack_lsm.c
+++ b/security/smack/smack_lsm.c
@@ -4583,7 +4583,7 @@ static int smack_dentry_create_files_as(struct dentry *dentry, int mode,
 	return 0;
 }
 
-struct lsm_blob_sizes smack_blob_sizes __lsm_ro_after_init = {
+struct lsm_blob_sizes smack_blob_sizes __ro_after_init = {
 	.lbs_cred = sizeof(struct task_smack),
 	.lbs_file = sizeof(struct smack_known *),
 	.lbs_inode = sizeof(struct inode_smack),
@@ -4591,7 +4591,7 @@ struct lsm_blob_sizes smack_blob_sizes __lsm_ro_after_init = {
 	.lbs_msg_msg = sizeof(struct smack_known *),
 };
 
-static struct security_hook_list smack_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list smack_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(ptrace_access_check, smack_ptrace_access_check),
 	LSM_HOOK_INIT(ptrace_traceme, smack_ptrace_traceme),
 	LSM_HOOK_INIT(syslog, smack_syslog),
diff --git a/security/tomoyo/tomoyo.c b/security/tomoyo/tomoyo.c
index 716c92ec941a..9dcdef99d431 100644
--- a/security/tomoyo/tomoyo.c
+++ b/security/tomoyo/tomoyo.c
@@ -486,7 +486,7 @@ static int tomoyo_socket_sendmsg(struct socket *sock, struct msghdr *msg,
 	return tomoyo_socket_sendmsg_permission(sock, msg, size);
 }
 
-struct lsm_blob_sizes tomoyo_blob_sizes __lsm_ro_after_init = {
+struct lsm_blob_sizes tomoyo_blob_sizes __ro_after_init = {
 	.lbs_task = sizeof(struct tomoyo_task),
 };
 
@@ -533,7 +533,7 @@ static void tomoyo_task_free(struct task_struct *task)
  * tomoyo_security_ops is a "struct security_operations" which is used for
  * registering TOMOYO.
  */
-static struct security_hook_list tomoyo_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list tomoyo_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(cred_prepare, tomoyo_cred_prepare),
 	LSM_HOOK_INIT(bprm_committed_creds, tomoyo_bprm_committed_creds),
 	LSM_HOOK_INIT(task_alloc, tomoyo_task_alloc),
@@ -569,7 +569,7 @@ static struct security_hook_list tomoyo_hooks[] __lsm_ro_after_init = {
 /* Lock for GC. */
 DEFINE_SRCU(tomoyo_ss);
 
-int tomoyo_enabled __lsm_ro_after_init = 1;
+int tomoyo_enabled __ro_after_init = 1;
 
 /**
  * tomoyo_init - Register TOMOYO Linux as a LSM module.
diff --git a/security/yama/yama_lsm.c b/security/yama/yama_lsm.c
index 94dc346370b1..c47d4e09bfb4 100644
--- a/security/yama/yama_lsm.c
+++ b/security/yama/yama_lsm.c
@@ -421,7 +421,7 @@ static int yama_ptrace_traceme(struct task_struct *parent)
 	return rc;
 }
 
-static struct security_hook_list yama_hooks[] __lsm_ro_after_init = {
+static struct security_hook_list yama_hooks[] __ro_after_init = {
 	LSM_HOOK_INIT(ptrace_access_check, yama_ptrace_access_check),
 	LSM_HOOK_INIT(ptrace_traceme, yama_ptrace_traceme),
 	LSM_HOOK_INIT(task_prctl, yama_task_prctl),
-- 
2.24.1




More information about the Linux-security-module-archive mailing list