diff options
Diffstat (limited to 'security/selinux')
-rw-r--r-- | security/selinux/avc.c | 19 | ||||
-rw-r--r-- | security/selinux/hooks.c | 2 |
2 files changed, 16 insertions, 5 deletions
diff --git a/security/selinux/avc.c b/security/selinux/avc.c index 1ed0f076aadc..b4b5da1c0a42 100644 --- a/security/selinux/avc.c +++ b/security/selinux/avc.c @@ -868,8 +868,19 @@ u32 avc_policy_seqno(void) void avc_disable(void) { - avc_flush(); - synchronize_rcu(); - if (avc_node_cachep) - kmem_cache_destroy(avc_node_cachep); + /* + * If you are looking at this because you have realized that we are + * not destroying the avc_node_cachep it might be easy to fix, but + * I don't know the memory barrier semantics well enough to know. It's + * possible that some other task dereferenced security_ops when + * it still pointed to selinux operations. If that is the case it's + * possible that it is about to use the avc and is about to need the + * avc_node_cachep. I know I could wrap the security.c security_ops call + * in an rcu_lock, but seriously, it's not worth it. Instead I just flush + * the cache and get that memory back. + */ + if (avc_node_cachep) { + avc_flush(); + /* kmem_cache_destroy(avc_node_cachep); */ + } } diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index 417f7c994522..bb230d5d7085 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c @@ -2411,7 +2411,7 @@ static void selinux_bprm_committed_creds(struct linux_binprm *bprm) /* Wake up the parent if it is waiting so that it can recheck * wait permission to the new task SID. */ read_lock(&tasklist_lock); - wake_up_interruptible(¤t->real_parent->signal->wait_chldexit); + __wake_up_parent(current, current->real_parent); read_unlock(&tasklist_lock); } |