aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/auditsc.c
diff options
context:
space:
mode:
authorDavid Woodhouse <dwmw2@shinybook.infradead.org>2005-06-24 09:14:05 -0400
committerDavid Woodhouse <dwmw2@shinybook.infradead.org>2005-06-24 09:14:05 -0400
commit5bb289b5a0becb53ac3e1d60815ff8b779296b73 (patch)
tree0db75422d66eec857e0c05cd4cf4d014e7c0e264 /kernel/auditsc.c
parent993e2d4106e94dae6e8cfbeb32073bd12cdee203 (diff)
AUDIT: Clean up user message filtering
Don't look up the task by its pid and then use the syscall filtering helper. Just implement our own filter helper which operates solely on the information in the netlink_skb_parms. Signed-off-by: David Woodhouse <dwmw2@infradead.org>
Diffstat (limited to 'kernel/auditsc.c')
-rw-r--r--kernel/auditsc.c56
1 files changed, 42 insertions, 14 deletions
diff --git a/kernel/auditsc.c b/kernel/auditsc.c
index 7b123f0a9481..34a990223c9e 100644
--- a/kernel/auditsc.c
+++ b/kernel/auditsc.c
@@ -40,6 +40,7 @@
40#include <linux/personality.h> 40#include <linux/personality.h>
41#include <linux/time.h> 41#include <linux/time.h>
42#include <linux/kthread.h> 42#include <linux/kthread.h>
43#include <linux/netlink.h>
43#include <asm/unistd.h> 44#include <asm/unistd.h>
44 45
45/* 0 = no checking 46/* 0 = no checking
@@ -530,35 +531,62 @@ static enum audit_state audit_filter_syscall(struct task_struct *tsk,
530 return AUDIT_BUILD_CONTEXT; 531 return AUDIT_BUILD_CONTEXT;
531} 532}
532 533
533int audit_filter_user(int pid, int type) 534static int audit_filter_user_rules(struct netlink_skb_parms *cb,
535 struct audit_rule *rule,
536 enum audit_state *state)
537{
538 int i;
539
540 for (i = 0; i < rule->field_count; i++) {
541 u32 field = rule->fields[i] & ~AUDIT_NEGATE;
542 u32 value = rule->values[i];
543 int result = 0;
544
545 switch (field) {
546 case AUDIT_PID:
547 result = (cb->creds.pid == value);
548 break;
549 case AUDIT_UID:
550 result = (cb->creds.uid == value);
551 break;
552 case AUDIT_GID:
553 result = (cb->creds.gid == value);
554 break;
555 case AUDIT_LOGINUID:
556 result = (cb->loginuid == value);
557 break;
558 }
559
560 if (rule->fields[i] & AUDIT_NEGATE)
561 result = !result;
562 if (!result)
563 return 0;
564 }
565 switch (rule->action) {
566 case AUDIT_NEVER: *state = AUDIT_DISABLED; break;
567 case AUDIT_POSSIBLE: *state = AUDIT_BUILD_CONTEXT; break;
568 case AUDIT_ALWAYS: *state = AUDIT_RECORD_CONTEXT; break;
569 }
570 return 1;
571}
572
573int audit_filter_user(struct netlink_skb_parms *cb, int type)
534{ 574{
535 struct task_struct *tsk;
536 struct audit_entry *e; 575 struct audit_entry *e;
537 enum audit_state state; 576 enum audit_state state;
538 int ret = 1; 577 int ret = 1;
539 578
540 read_lock(&tasklist_lock);
541 tsk = find_task_by_pid(pid);
542 if (tsk)
543 get_task_struct(tsk);
544 read_unlock(&tasklist_lock);
545
546 if (!tsk)
547 return -ESRCH;
548
549 rcu_read_lock(); 579 rcu_read_lock();
550 list_for_each_entry_rcu(e, &audit_filter_list[AUDIT_FILTER_USER], list) { 580 list_for_each_entry_rcu(e, &audit_filter_list[AUDIT_FILTER_USER], list) {
551 if (audit_filter_rules(tsk, &e->rule, NULL, &state)) { 581 if (audit_filter_user_rules(cb, &e->rule, &state)) {
552 if (state == AUDIT_DISABLED) 582 if (state == AUDIT_DISABLED)
553 ret = 0; 583 ret = 0;
554 break; 584 break;
555 } 585 }
556 } 586 }
557 rcu_read_unlock(); 587 rcu_read_unlock();
558 put_task_struct(tsk);
559 588
560 return ret; /* Audit by default */ 589 return ret; /* Audit by default */
561
562} 590}
563 591
564/* This should be called with task_lock() held. */ 592/* This should be called with task_lock() held. */