Skip to contentSkip to conversation

audit=0 appears not to completely disable auditing

PATCH In review Steve Grubb 4 participants 6 messages Mar 9, 2007 – Sep 26, 2007 Audit

lore
Share & tools
lore
#0 lore raw

PATCH 1/1 audit=0 appears not to completely disable auditing

Hi,

There was a bz, 231371, reporting that current upstream kernels do not completely disable auditing when boot with audit=0 and the audit daemon not configured to run. You can reproduce the problem by:

service auditd stop
auditctl -e 0
auditctl -w /etc/passwd
and you'd get an event in syslog:

Mar  9 15:43:04 localhost kernel: audit(1173472984.321:982): auid=4294967295

subj=user_u:system_r:auditctl_t:s0 op=add rule key=(null) list=4 res=1

The patch below solves this problem by checking audit_enabled before creating an audit event.

kernel/audit.c +83 -71
diff -urp linux-2.6.18.x86_64.orig/kernel/audit.c linux-2.6.18.x86_64/kernel/audit.c
@@ -238,46 +238,50 @@ void audit_log_lost(const char *message)
 
 static int audit_set_rate_limit(int limit, uid_t loginuid, u32 sid)
 {
-	int old	= audit_rate_limit;
+	if (audit_enabled) {
+		int old	= audit_rate_limit;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_rate_limit=%d old=%d by auid=%u subj=%s",
-				limit, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_rate_limit=%d old=%d by auid=%u",
-			limit, old, loginuid);
+					limit, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_rate_limit=%d old=%d by auid=%u",
+				limit, old, loginuid);
+	}
 	audit_rate_limit = limit;
 	return 0;
 }
 
 static int audit_set_backlog_limit(int limit, uid_t loginuid, u32 sid)
 {
-	int old	= audit_backlog_limit;
+	if (audit_enabled) {
+		int old	= audit_backlog_limit;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 			    "audit_backlog_limit=%d old=%d by auid=%u subj=%s",
-				limit, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_backlog_limit=%d old=%d by auid=%u",
-			limit, old, loginuid);
+					limit, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_backlog_limit=%d old=%d by auid=%u",
+				limit, old, loginuid);
+	}
 	audit_backlog_limit = limit;
 	return 0;
 }
@@ -289,21 +293,23 @@ static int audit_set_enabled(int state, 
 	if (state != 0 && state != 1)
 		return -EINVAL;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+	if (audit_enabled || state) {
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_enabled=%d old=%d by auid=%u subj=%s",
-				state, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_enabled=%d old=%d by auid=%u",
-			state, old, loginuid);
+					state, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_enabled=%d old=%d by auid=%u",
+				state, old, loginuid);
+	}
 	audit_enabled = state;
 	return 0;
 }
@@ -317,21 +323,23 @@ static int audit_set_failure(int state, 
 	    && state != AUDIT_FAIL_PANIC)
 		return -EINVAL;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+	if (audit_enabled) {
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_failure=%d old=%d by auid=%u subj=%s",
-				state, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_failure=%d old=%d by auid=%u",
-			state, old, loginuid);
+					state, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_failure=%d old=%d by auid=%u",
+				state, old, loginuid);
+	}
 	audit_failure = state;
 	return 0;
 }
@@ -536,22 +544,26 @@ static int audit_receive_msg(struct sk_b
 			if (err < 0) return err;
 		}
 		if (status_get->mask & AUDIT_STATUS_PID) {
-			int old   = audit_pid;
-			if (sid) {
-				if ((err = selinux_ctxid_to_string(
-						sid, &ctx, &len)))
-					return err;
-				else
+			if (audit_enabled) {
+				int old   = audit_pid;
+				if (sid) {
+					if ((err = selinux_ctxid_to_string(
+							sid, &ctx, &len)))
+						return err;
+					else
+						audit_log(NULL, GFP_KERNEL,
+							AUDIT_CONFIG_CHANGE,
+				"audit_pid=%d old=%d by auid=%u subj=%s",
+							status_get->pid, old,
+							loginuid, ctx);
+					kfree(ctx);
+				} else
 					audit_log(NULL, GFP_KERNEL,
 						AUDIT_CONFIG_CHANGE,
-						"audit_pid=%d old=%d by auid=%u subj=%s",
-						status_get->pid, old,
-						loginuid, ctx);
-				kfree(ctx);
-			} else
-				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 					"audit_pid=%d old=%d by auid=%u",
-					  status_get->pid, old, loginuid);
+						status_get->pid, old,
+						loginuid);
+			}
 			audit_pid = status_get->pid;
 		}
 		if (status_get->mask & AUDIT_STATUS_RATE_LIMIT)
kernel/auditfilter.c +33 -21

90 lines not on this page · raw message

#1 lore raw

Hi Steve,

Sorry for the delayed reply. I am just getting a chance to look at this.

Steve Grubb wrote: [Fri Mar 09 2007, 03:50:11PM EST]

Quoted 3 lines

There was a bz, 231371, reporting that current upstream kernels do not completely disable auditing when boot with audit=0 and the audit daemon not configured to run.

When audit_enabled was first implemented, it was only intended to turn off syscall auditing, not _all_ auditing. This was so users could use audit for selinux messages without the overhead of syscall audit.

However, since Al optimized the syscall audit data collection when there are no rules, maybe this isn't necessary anymore. Is that what you are thinking?

It does seem like audit_enabled has changed its meaning since it was introduced...

Quoted 2 lines

The patch below solves this problem by checking audit_enabled before creating an audit event.

If you want audit_enabled=0 to turn off audit completely, do you also want to drop selinux messages?

Amy

#2 lore raw
Quoted 2 lines · Amy Griffis

When audit_enabled was first implemented, it was only intended to turn off syscall auditing, not _all_ auditing.

At that time, syscall auditing *was* all auditing. :)

Quoted 2 lines

This was so users could use audit for selinux messages without the overhead of syscall audit.

SE Linux has always been different and you shouldn't really consider it in the auditing system for enable/disable. The reason its different is that it uses audit as a transport mechanism and can happily use syslogs, too.

Quoted 5 lines
Quoted 2 lines

The patch below solves this problem by checking audit_enabled before creating an audit event.

If you want audit_enabled=0 to turn off audit completely, do you also want to drop selinux messages?

No, the SE Linux folks want avc messages at all times unless the admin specifically sets a rule to suppress them.

-Steve

#3 lore raw

Steve Grubb wrote: [Thu Mar 22 2007, 05:55:45PM EDT]

Quoted 5 lines
Quoted 2 lines

If you want audit_enabled=0 to turn off audit completely, do you also want to drop selinux messages?

No, the SE Linux folks want avc messages at all times unless the admin specifically sets a rule to suppress them.

Okay, makes sense. Do you think audit should return an error if someone tries to add a rule when audit_enabled=0 ?

#4 lore raw
Quoted 9 lines · Amy Griffis

Steve Grubb wrote: [Thu Mar 22 2007, 05:55:45PM EDT]

Quoted 5 lines
Quoted 2 lines

If you want audit_enabled=0 to turn off audit completely, do you also want to drop selinux messages?

No, the SE Linux folks want avc messages at all times unless the admin specifically sets a rule to suppress them.

Okay, makes sense. Do you think audit should return an error if someone tries to add a rule when audit_enabled=0 ?

Yes, probably. You'd kind of think that the human doing the auditing would like a large and loud complaint if auditing had been accidentally disabled.

The only question is what behavior it should have if a site (for whatever reason) decides to first load all the rules, then enable auditing (possibly to avoid spurious complaints about processes because not all the rules have been loaded yet).

maintainer
#5 lore raw
In reply to Steve Grubb

Al,

What happened with this patch, it does not appear to have made it into the audit tree. We are still outputting audit messages (through dmesg/syslog) even when audit is turned off.

-Eric

Quoted 322 lines · Steve Grubb

Hi,

There was a bz, 231371, reporting that current upstream kernels do not completely disable auditing when boot with audit=0 and the audit daemon not configured to run. You can reproduce the problem by:

service auditd stop
auditctl -e 0
auditctl -w /etc/passwd
and you'd get an event in syslog:

Mar  9 15:43:04 localhost kernel: audit(1173472984.321:982): auid=4294967295

subj=user_u:system_r:auditctl_t:s0 op=add rule key=(null) list=4 res=1

The patch below solves this problem by checking audit_enabled before creating an audit event.

diff -urp linux-2.6.18.x86_64.orig/kernel/audit.c linux-2.6.18.x86_64/kernel/audit.c

kernel/audit.c +83 -71
@@ -238,46 +238,50 @@ void audit_log_lost(const char *message)
 
 static int audit_set_rate_limit(int limit, uid_t loginuid, u32 sid)
 {
-	int old	= audit_rate_limit;
+	if (audit_enabled) {
+		int old	= audit_rate_limit;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_rate_limit=%d old=%d by auid=%u subj=%s",
-				limit, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_rate_limit=%d old=%d by auid=%u",
-			limit, old, loginuid);
+					limit, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_rate_limit=%d old=%d by auid=%u",
+				limit, old, loginuid);
+	}
 	audit_rate_limit = limit;
 	return 0;
 }
 
 static int audit_set_backlog_limit(int limit, uid_t loginuid, u32 sid)
 {
-	int old	= audit_backlog_limit;
+	if (audit_enabled) {
+		int old	= audit_backlog_limit;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 			    "audit_backlog_limit=%d old=%d by auid=%u subj=%s",
-				limit, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_backlog_limit=%d old=%d by auid=%u",
-			limit, old, loginuid);
+					limit, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_backlog_limit=%d old=%d by auid=%u",
+				limit, old, loginuid);
+	}
 	audit_backlog_limit = limit;
 	return 0;
 }
@@ -289,21 +293,23 @@ static int audit_set_enabled(int state, 
 	if (state != 0 && state != 1)
 		return -EINVAL;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+	if (audit_enabled || state) {
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_enabled=%d old=%d by auid=%u subj=%s",
-				state, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_enabled=%d old=%d by auid=%u",
-			state, old, loginuid);
+					state, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_enabled=%d old=%d by auid=%u",
+				state, old, loginuid);
+	}
 	audit_enabled = state;
 	return 0;
 }
@@ -317,21 +323,23 @@ static int audit_set_failure(int state, 
 	    && state != AUDIT_FAIL_PANIC)
 		return -EINVAL;
 
-	if (sid) {
-		char *ctx = NULL;
-		u32 len;
-		int rc;
-		if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
-			return rc;
-		else
-			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+	if (audit_enabled) {
+		if (sid) {
+			char *ctx = NULL;
+			u32 len;
+			int rc;
+			if ((rc = selinux_ctxid_to_string(sid, &ctx, &len)))
+				return rc;
+			else
+				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 				"audit_failure=%d old=%d by auid=%u subj=%s",
-				state, old, loginuid, ctx);
-		kfree(ctx);
-	} else
-		audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
-			"audit_failure=%d old=%d by auid=%u",
-			state, old, loginuid);
+					state, old, loginuid, ctx);
+			kfree(ctx);
+		} else
+			audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
+				"audit_failure=%d old=%d by auid=%u",
+				state, old, loginuid);
+	}
 	audit_failure = state;
 	return 0;
 }
@@ -536,22 +544,26 @@ static int audit_receive_msg(struct sk_b
 			if (err < 0) return err;
 		}
 		if (status_get->mask & AUDIT_STATUS_PID) {
-			int old   = audit_pid;
-			if (sid) {
-				if ((err = selinux_ctxid_to_string(
-						sid, &ctx, &len)))
-					return err;
-				else
+			if (audit_enabled) {
+				int old   = audit_pid;
+				if (sid) {
+					if ((err = selinux_ctxid_to_string(
+							sid, &ctx, &len)))
+						return err;
+					else
+						audit_log(NULL, GFP_KERNEL,
+							AUDIT_CONFIG_CHANGE,
+				"audit_pid=%d old=%d by auid=%u subj=%s",
+							status_get->pid, old,
+							loginuid, ctx);
+					kfree(ctx);
+				} else
 					audit_log(NULL, GFP_KERNEL,
 						AUDIT_CONFIG_CHANGE,
-						"audit_pid=%d old=%d by auid=%u subj=%s",
-						status_get->pid, old,
-						loginuid, ctx);
-				kfree(ctx);
-			} else
-				audit_log(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE,
 					"audit_pid=%d old=%d by auid=%u",
-					  status_get->pid, old, loginuid);
+						status_get->pid, old,
+						loginuid);
+			}
 			audit_pid = status_get->pid;
 		}
 		if (status_get->mask & AUDIT_STATUS_RATE_LIMIT)

diff -urp linux-2.6.18.x86_64.orig/kernel/auditfilter.c linux-2.6.18.x86_64/kernel/auditfilter.c

kernel/auditfilter.c +33 -22
@@ -95,6 +95,8 @@ extern struct inotify_handle *audit_ih;
 /* Inotify events we care about. */
 #define AUDIT_IN_WATCH IN_MOVE|IN_CREATE|IN_DELETE|IN_DELETE_SELF|IN_MOVE_SELF
 
+extern int audit_enabled;
+
 void audit_free_parent(struct inotify_watch *i_watch)
 {
 	struct audit_parent *parent;
@@ -897,7 +899,6 @@ static void audit_update_watch(struct au
 	struct audit_watch *owatch, *nwatch, *nextw;
 	struct audit_krule *r, *nextr;
 	struct audit_entry *oentry, *nentry;
-	struct audit_buffer *ab;
 
 	mutex_lock(&audit_filter_mutex);
 	list_for_each_entry_safe(owatch, nextw, &parent->watches, wlist) {
@@ -937,13 +938,18 @@ static void audit_update_watch(struct au
 			call_rcu(&oentry->rcu, audit_free_rule_rcu);
 		}
 
-		ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE);
-		audit_log_format(ab, "op=updated rules specifying path=");
-		audit_log_untrustedstring(ab, owatch->path);
-		audit_log_format(ab, " with dev=%u ino=%lu\n", dev, ino);
-		audit_log_format(ab, " list=%d res=1", r->listnr);
-		audit_log_end(ab);
-
+		if (audit_enabled) {
+			struct audit_buffer *ab;
+			ab = audit_log_start(NULL, GFP_KERNEL,
+				AUDIT_CONFIG_CHANGE);
+			audit_log_format(ab,
+				"op=updated rules specifying path=");
+			audit_log_untrustedstring(ab, owatch->path);
+			audit_log_format(ab, " with dev=%u ino=%lu\n",
+				 dev, ino);
+			audit_log_format(ab, " list=%d res=1", r->listnr);
+			audit_log_end(ab);
+		}
 		audit_remove_watch(owatch);
 		goto add_watch_to_parent; /* event applies to a single watch */
 	}
@@ -962,25 +968,28 @@ static void audit_remove_parent_watches(
 	struct audit_watch *w, *nextw;
 	struct audit_krule *r, *nextr;
 	struct audit_entry *e;
-	struct audit_buffer *ab;
 
 	mutex_lock(&audit_filter_mutex);
 	parent->flags |= AUDIT_PARENT_INVALID;
 	list_for_each_entry_safe(w, nextw, &parent->watches, wlist) {
 		list_for_each_entry_safe(r, nextr, &w->rules, rlist) {
 			e = container_of(r, struct audit_entry, rule);
-
-			ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE);
-			audit_log_format(ab, "op=remove rule path=");
-			audit_log_untrustedstring(ab, w->path);
-			if (r->filterkey) {
-				audit_log_format(ab, " key=");
-				audit_log_untrustedstring(ab, r->filterkey);
-			} else
-				audit_log_format(ab, " key=(null)");
-			audit_log_format(ab, " list=%d res=1", r->listnr);
-			audit_log_end(ab);
-
+			if (audit_enabled) {
+				struct audit_buffer *ab;
+				ab = audit_log_start(NULL, GFP_KERNEL,
+					AUDIT_CONFIG_CHANGE);
+				audit_log_format(ab, "op=remove rule path=");
+				audit_log_untrustedstring(ab, w->path);
+				if (r->filterkey) {
+					audit_log_format(ab, " key=");
+					audit_log_untrustedstring(ab,
+							r->filterkey);
+				} else
+					audit_log_format(ab, " key=(null)");
+				audit_log_format(ab, " list=%d res=1",
+					r->listnr);
+				audit_log_end(ab);
+			}
 			list_del(&r->rlist);
 			list_del_rcu(&e->list);
 			call_rcu(&e->rcu, audit_free_rule_rcu);
@@ -1409,6 +1418,9 @@ static void audit_log_rule_change(uid_t 
 {
 	struct audit_buffer *ab;
 
+	if (!audit_enabled)
+		return;
+
 	ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_CONFIG_CHANGE);
 	if (!ab)
 		return;
 
--

Linux-audit mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/linux-audit