audit: make audit_del_rule() more robust
[firefly-linux-kernel-4.4.55.git] / kernel / auditfilter.c
index 83f6d298d2345e6f9dd2890760d6ca0d3cfa3417..7ca7d3b5aca2b2bb8c24495a9063b4d33b218a0c 100644 (file)
@@ -953,7 +953,6 @@ static inline int audit_del_rule(struct audit_entry *entry)
        mutex_lock(&audit_filter_mutex);
        e = audit_find_rule(entry, &list);
        if (!e) {
-               mutex_unlock(&audit_filter_mutex);
                ret = -ENOENT;
                goto out;
        }
@@ -964,10 +963,6 @@ static inline int audit_del_rule(struct audit_entry *entry)
        if (e->rule.tree)
                audit_remove_tree_rule(&e->rule);
 
-       list_del_rcu(&e->list);
-       list_del(&e->rule.list);
-       call_rcu(&e->rcu, audit_free_rule_rcu);
-
 #ifdef CONFIG_AUDITSYSCALL
        if (!dont_count)
                audit_n_rules--;
@@ -975,9 +970,14 @@ static inline int audit_del_rule(struct audit_entry *entry)
        if (!audit_match_signal(entry))
                audit_signals--;
 #endif
-       mutex_unlock(&audit_filter_mutex);
+
+       list_del_rcu(&e->list);
+       list_del(&e->rule.list);
+       call_rcu(&e->rcu, audit_free_rule_rcu);
 
 out:
+       mutex_unlock(&audit_filter_mutex);
+
        if (tree)
                audit_put_tree(tree);   /* that's the temporary one */