Commit c1b773d8 authored by Chris Wright's avatar Chris Wright Committed by David Woodhouse

Add audit_log_type

Add audit_log_type to allow callers to specify type and pid when logging.
Convert audit_log to wrapper around audit_log_type.  Could have
converted all audit_log callers directly, but common case is default
of type AUDIT_KERNEL and pid 0.  Update audit_log_start to take type
and pid values when creating a new audit_buffer.  Move sequences that
did audit_log_start, audit_log_format, audit_set_type, audit_log_end,
to simply call audit_log_type directly.  This obsoletes audit_set_type
and audit_set_pid, so remove them.
Signed-off-by: default avatarChris Wright <chrisw@osdl.org>
Signed-off-by: default avatarDavid Woodhouse <dwmw2@infradead.org>
parent 197c69c6
...@@ -216,11 +216,14 @@ extern void audit_signal_info(int sig, struct task_struct *t); ...@@ -216,11 +216,14 @@ extern void audit_signal_info(int sig, struct task_struct *t);
#ifdef CONFIG_AUDIT #ifdef CONFIG_AUDIT
/* These are defined in audit.c */ /* These are defined in audit.c */
/* Public API */ /* Public API */
extern void audit_log(struct audit_context *ctx, #define audit_log(ctx, fmt, args...) \
const char *fmt, ...) audit_log_type(ctx, AUDIT_KERNEL, 0, fmt, ##args)
__attribute__((format(printf,2,3))); extern void audit_log_type(struct audit_context *ctx, int type,
int pid, const char *fmt, ...)
__attribute__((format(printf,4,5)));
extern struct audit_buffer *audit_log_start(struct audit_context *ctx); extern struct audit_buffer *audit_log_start(struct audit_context *ctx, int type,
int pid);
extern void audit_log_format(struct audit_buffer *ab, extern void audit_log_format(struct audit_buffer *ab,
const char *fmt, ...) const char *fmt, ...)
__attribute__((format(printf,2,3))); __attribute__((format(printf,2,3)));
...@@ -240,8 +243,9 @@ extern void audit_send_reply(int pid, int seq, int type, ...@@ -240,8 +243,9 @@ extern void audit_send_reply(int pid, int seq, int type,
void *payload, int size); void *payload, int size);
extern void audit_log_lost(const char *message); extern void audit_log_lost(const char *message);
#else #else
#define audit_log(t,f,...) do { ; } while (0) #define audit_log(c,f,...) do { ; } while (0)
#define audit_log_start(t) ({ NULL; }) #define audit_log_type(c,t,p,f,...) do { ; } while (0)
#define audit_log_start(c,t,p) ({ NULL; })
#define audit_log_vformat(b,f,a) do { ; } while (0) #define audit_log_vformat(b,f,a) do { ; } while (0)
#define audit_log_format(b,f,...) do { ; } while (0) #define audit_log_format(b,f,...) do { ; } while (0)
#define audit_log_end(b) do { ; } while (0) #define audit_log_end(b) do { ; } while (0)
......
...@@ -140,18 +140,6 @@ struct audit_buffer { ...@@ -140,18 +140,6 @@ struct audit_buffer {
struct audit_context *ctx; /* NULL or associated context */ struct audit_context *ctx; /* NULL or associated context */
}; };
void audit_set_type(struct audit_buffer *ab, int type)
{
struct nlmsghdr *nlh = (struct nlmsghdr *)ab->skb->data;
nlh->nlmsg_type = type;
}
static void audit_set_pid(struct audit_buffer *ab, pid_t pid)
{
struct nlmsghdr *nlh = (struct nlmsghdr *)ab->skb->data;
nlh->nlmsg_pid = pid;
}
struct audit_entry { struct audit_entry {
struct list_head list; struct list_head list;
struct audit_rule rule; struct audit_rule rule;
...@@ -344,7 +332,6 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) ...@@ -344,7 +332,6 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh)
void *data; void *data;
struct audit_status *status_get, status_set; struct audit_status *status_get, status_set;
int err; int err;
struct audit_buffer *ab;
u16 msg_type = nlh->nlmsg_type; u16 msg_type = nlh->nlmsg_type;
uid_t loginuid; /* loginuid of sender */ uid_t loginuid; /* loginuid of sender */
struct audit_sig_info sig_data; struct audit_sig_info sig_data;
...@@ -396,19 +383,13 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) ...@@ -396,19 +383,13 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh)
loginuid); loginuid);
break; break;
case AUDIT_USER: case AUDIT_USER:
ab = audit_log_start(NULL); audit_log_type(NULL, AUDIT_USER, pid,
if (!ab)
break; /* audit_panic has been called */
audit_log_format(ab,
"user pid=%d uid=%d length=%d loginuid=%u" "user pid=%d uid=%d length=%d loginuid=%u"
" msg='%.1024s'", " msg='%.1024s'",
pid, uid, pid, uid,
(int)(nlh->nlmsg_len (int)(nlh->nlmsg_len
- ((char *)data - (char *)nlh)), - ((char *)data - (char *)nlh)),
loginuid, (char *)data); loginuid, (char *)data);
audit_set_type(ab, AUDIT_USER);
audit_set_pid(ab, pid);
audit_log_end(ab);
break; break;
case AUDIT_ADD: case AUDIT_ADD:
case AUDIT_DEL: case AUDIT_DEL:
...@@ -560,12 +541,10 @@ static void audit_buffer_free(struct audit_buffer *ab) ...@@ -560,12 +541,10 @@ static void audit_buffer_free(struct audit_buffer *ab)
spin_unlock_irqrestore(&audit_freelist_lock, flags); spin_unlock_irqrestore(&audit_freelist_lock, flags);
} }
static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx, static struct audit_buffer * audit_buffer_alloc(int gfp_mask)
int gfp_mask)
{ {
unsigned long flags; unsigned long flags;
struct audit_buffer *ab = NULL; struct audit_buffer *ab = NULL;
struct nlmsghdr *nlh;
spin_lock_irqsave(&audit_freelist_lock, flags); spin_lock_irqsave(&audit_freelist_lock, flags);
if (!list_empty(&audit_freelist)) { if (!list_empty(&audit_freelist)) {
...@@ -587,12 +566,6 @@ static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx, ...@@ -587,12 +566,6 @@ static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx,
if (!ab->skb) if (!ab->skb)
goto err; goto err;
ab->ctx = ctx;
nlh = (struct nlmsghdr *)skb_put(ab->skb, NLMSG_SPACE(0));
nlh->nlmsg_type = AUDIT_KERNEL;
nlh->nlmsg_flags = 0;
nlh->nlmsg_pid = 0;
nlh->nlmsg_seq = 0;
return ab; return ab;
err: err:
audit_buffer_free(ab); audit_buffer_free(ab);
...@@ -605,11 +578,12 @@ static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx, ...@@ -605,11 +578,12 @@ static struct audit_buffer * audit_buffer_alloc(struct audit_context *ctx,
* syscall, then the syscall is marked as auditable and an audit record * syscall, then the syscall is marked as auditable and an audit record
* will be written at syscall exit. If there is no associated task, tsk * will be written at syscall exit. If there is no associated task, tsk
* should be NULL. */ * should be NULL. */
struct audit_buffer *audit_log_start(struct audit_context *ctx) struct audit_buffer *audit_log_start(struct audit_context *ctx, int type, int pid)
{ {
struct audit_buffer *ab = NULL; struct audit_buffer *ab = NULL;
struct timespec t; struct timespec t;
unsigned int serial; unsigned int serial;
struct nlmsghdr *nlh;
if (!audit_initialized) if (!audit_initialized)
return NULL; return NULL;
...@@ -626,12 +600,19 @@ struct audit_buffer *audit_log_start(struct audit_context *ctx) ...@@ -626,12 +600,19 @@ struct audit_buffer *audit_log_start(struct audit_context *ctx)
return NULL; return NULL;
} }
ab = audit_buffer_alloc(ctx, GFP_ATOMIC); ab = audit_buffer_alloc(GFP_ATOMIC);
if (!ab) { if (!ab) {
audit_log_lost("out of memory in audit_log_start"); audit_log_lost("out of memory in audit_log_start");
return NULL; return NULL;
} }
ab->ctx = ctx;
nlh = (struct nlmsghdr *)skb_put(ab->skb, NLMSG_SPACE(0));
nlh->nlmsg_type = type;
nlh->nlmsg_flags = 0;
nlh->nlmsg_pid = pid;
nlh->nlmsg_seq = 0;
if (!audit_get_stamp(ab->ctx, &t, &serial)) { if (!audit_get_stamp(ab->ctx, &t, &serial)) {
t = CURRENT_TIME; t = CURRENT_TIME;
serial = 0; serial = 0;
...@@ -828,12 +809,13 @@ void audit_log_end(struct audit_buffer *ab) ...@@ -828,12 +809,13 @@ void audit_log_end(struct audit_buffer *ab)
/* Log an audit record. This is a convenience function that calls /* Log an audit record. This is a convenience function that calls
* audit_log_start, audit_log_vformat, and audit_log_end. It may be * audit_log_start, audit_log_vformat, and audit_log_end. It may be
* called in any context. */ * called in any context. */
void audit_log(struct audit_context *ctx, const char *fmt, ...) void audit_log_type(struct audit_context *ctx, int type, int pid,
const char *fmt, ...)
{ {
struct audit_buffer *ab; struct audit_buffer *ab;
va_list args; va_list args;
ab = audit_log_start(ctx); ab = audit_log_start(ctx, type, pid);
if (ab) { if (ab) {
va_start(args, fmt); va_start(args, fmt);
audit_log_vformat(ab, fmt, args); audit_log_vformat(ab, fmt, args);
......
...@@ -648,7 +648,7 @@ static void audit_log_exit(struct audit_context *context) ...@@ -648,7 +648,7 @@ static void audit_log_exit(struct audit_context *context)
int i; int i;
struct audit_buffer *ab; struct audit_buffer *ab;
ab = audit_log_start(context); ab = audit_log_start(context, AUDIT_KERNEL, 0);
if (!ab) if (!ab)
return; /* audit_panic has been called */ return; /* audit_panic has been called */
audit_log_format(ab, "syscall=%d", context->major); audit_log_format(ab, "syscall=%d", context->major);
...@@ -680,7 +680,7 @@ static void audit_log_exit(struct audit_context *context) ...@@ -680,7 +680,7 @@ static void audit_log_exit(struct audit_context *context)
while (context->aux) { while (context->aux) {
struct audit_aux_data *aux; struct audit_aux_data *aux;
ab = audit_log_start(context); ab = audit_log_start(context, AUDIT_KERNEL, 0);
if (!ab) if (!ab)
continue; /* audit_panic has been called */ continue; /* audit_panic has been called */
...@@ -701,7 +701,7 @@ static void audit_log_exit(struct audit_context *context) ...@@ -701,7 +701,7 @@ static void audit_log_exit(struct audit_context *context)
} }
for (i = 0; i < context->name_count; i++) { for (i = 0; i < context->name_count; i++) {
ab = audit_log_start(context); ab = audit_log_start(context, AUDIT_KERNEL, 0);
if (!ab) if (!ab)
continue; /* audit_panic has been called */ continue; /* audit_panic has been called */
audit_log_format(ab, "item=%d", i); audit_log_format(ab, "item=%d", i);
...@@ -1005,22 +1005,13 @@ int audit_get_stamp(struct audit_context *ctx, ...@@ -1005,22 +1005,13 @@ int audit_get_stamp(struct audit_context *ctx,
return 0; return 0;
} }
extern int audit_set_type(struct audit_buffer *ab, int type);
int audit_set_loginuid(struct task_struct *task, uid_t loginuid) int audit_set_loginuid(struct task_struct *task, uid_t loginuid)
{ {
if (task->audit_context) { if (task->audit_context) {
struct audit_buffer *ab; audit_log_type(NULL, AUDIT_LOGIN, 0,
"login pid=%d uid=%u old loginuid=%u new loginuid=%u",
ab = audit_log_start(NULL); task->pid, task->uid, task->audit_context->loginuid,
if (ab) { loginuid);
audit_log_format(ab, "login pid=%d uid=%u "
"old loginuid=%u new loginuid=%u",
task->pid, task->uid,
task->audit_context->loginuid, loginuid);
audit_set_type(ab, AUDIT_LOGIN);
audit_log_end(ab);
}
task->audit_context->loginuid = loginuid; task->audit_context->loginuid = loginuid;
} }
return 0; return 0;
......
...@@ -549,7 +549,7 @@ void avc_audit(u32 ssid, u32 tsid, ...@@ -549,7 +549,7 @@ void avc_audit(u32 ssid, u32 tsid,
return; return;
} }
ab = audit_log_start(current->audit_context); ab = audit_log_start(current->audit_context, AUDIT_KERNEL, 0);
if (!ab) if (!ab)
return; /* audit_panic has been called */ return; /* audit_panic has been called */
audit_log_format(ab, "avc: %s ", denied ? "denied" : "granted"); audit_log_format(ab, "avc: %s ", denied ? "denied" : "granted");
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment