audit: log on errors from filter user rules
[firefly-linux-kernel-4.4.55.git] / kernel / audit.c
index ce8514f9aa6c9b1888ef2ea4feec3b743f4c247f..15661ef8bece0e633342df02bc4151224cf620de 100644 (file)
@@ -869,13 +869,14 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh)
                        return 0;
 
                err = audit_filter_user(msg_type);
-               if (err == 1) {
+               if (err == 1) { /* match or error */
                        err = 0;
                        if (msg_type == AUDIT_USER_TTY) {
                                err = tty_audit_push_current();
                                if (err)
                                        break;
                        }
+                       mutex_unlock(&audit_cmd_mutex);
                        audit_log_common_recv_msg(&ab, msg_type);
                        if (msg_type != AUDIT_USER_TTY)
                                audit_log_format(ab, " msg='%.*s'",
@@ -893,6 +894,7 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh)
                        }
                        audit_set_portid(ab, NETLINK_CB(skb).portid);
                        audit_log_end(ab);
+                       mutex_lock(&audit_cmd_mutex);
                }
                break;
        case AUDIT_ADD_RULE:
@@ -1317,7 +1319,8 @@ struct audit_buffer *audit_log_start(struct audit_context *ctx, gfp_t gfp_mask,
        struct audit_buffer     *ab     = NULL;
        struct timespec         t;
        unsigned int            uninitialized_var(serial);
-       int reserve;
+       int reserve = 5; /* Allow atomic callers to go up to five
+                           entries over the normal backlog limit */
        unsigned long timeout_start = jiffies;
 
        if (audit_initialized != AUDIT_INITIALIZED)
@@ -1326,11 +1329,12 @@ struct audit_buffer *audit_log_start(struct audit_context *ctx, gfp_t gfp_mask,
        if (unlikely(audit_filter_type(type)))
                return NULL;
 
-       if (gfp_mask & __GFP_WAIT)
-               reserve = 0;
-       else
-               reserve = 5; /* Allow atomic callers to go up to five
-                               entries over the normal backlog limit */
+       if (gfp_mask & __GFP_WAIT) {
+               if (audit_pid && audit_pid == current->pid)
+                       gfp_mask &= ~__GFP_WAIT;
+               else
+                       reserve = 0;
+       }
 
        while (audit_backlog_limit
               && skb_queue_len(&audit_skb_queue) > audit_backlog_limit + reserve) {