Linux Kernel Architecture

(Jacob Rumans) #1

Chapter 19: Auditing


Since the general structure of all other auxiliary audit data structures is similar, this section doesn’t bother
with showing them explicitly. You can refer tokernel/auditsc.cfor their definitions.

Records, Rules and Filtering


The fundamental data structure to format an audit record is defined as follows:

kernel/audit.c
struct audit_buffer {
struct list_head list;
struct sk_buff *skb; /* formatted skb ready to send */
struct audit_context *ctx; /* NULL or associated context */
gfp_t gfp_mask;
};

listis a list element that allows for storing the buffer on various lists. Since netlink sockets are used
to communicate between kernel and userland, a socket buffer of typesk_buffis used to encapsulate
messages. The connection with the audit context is realized byctx(whichmayalsobeaNULLpointer if
no context exists because system call auditing is disabled), andgfp_maskfinally determines from which
memory pool allocations are supposed to be satisfied.

Since audit buffers are frequently used, the kernel keeps a number of pre-allocated instances of
audit_bufferready for use.audit_buffer_allocandaudit_buffer_freeare responsible for
allocating and initializing new buffers respectively freeing them — handling the audit buffer cache
is implicitly performed by these functions. Their implementation is straightforward, so they are not
discussed any further here.

An audit rule that is transferred from userspace into the kernel is represented by the following data
structure^3 :

<audit.h>
struct audit_rule_data {
__u32 flags; /* AUDIT_PER_{TASK,CALL}, AUDIT_PREPEND */
__u32 action; /* AUDIT_NEVER, AUDIT_POSSIBLE, AUDIT_ALWAYS */
__u32 field_count;
__u32 mask[AUDIT_BITMASK_SIZE]; /* syscall(s) affected */
__u32 fields[AUDIT_MAX_FIELDS];
__u32 values[AUDIT_MAX_FIELDS];
__u32 fieldflags[AUDIT_MAX_FIELDS];
__u32 buflen; /* total length of string fields */
char buf[0]; /* string fields buffer */
};

First,flagsdenotes when the rule is supposed to be activated. The following choices are possible:

<audit.h>
#define AUDIT_FILTER_USER 0x00 /* Apply rule to user-generated messages */
#define AUDIT_FILTER_TASK 0x01 /* Apply rule at task creation (not syscall) */
#define AUDIT_FILTER_ENTRY 0x02 /* Apply rule at syscall entry */

(^3) Previous kernel versions employed the slightly simplerstruct audit_rule, which did not allow for non-integer or variable-
length string data fields. The structure still exists in the kernel to provide backward-compatibility with userspace, but must not be
used by new code.

Free download pdf