diff --git a/configure.ac b/configure.ac index f2f9f2d..7630095 100644 --- a/configure.ac +++ b/configure.ac @@ -22,6 +22,7 @@ AM_PROG_CC_C_O # Checks for libraries. NIH_INIT([dbus]) +LINUX_AUDIT # Checks for header files. diff --git a/m4/libaudit.m4 b/m4/libaudit.m4 new file mode 100644 index 0000000..6865fb8 --- /dev/null +++ b/m4/libaudit.m4 @@ -0,0 +1,25 @@ +# libaudit.m4 - Checks for the Linux Audit System support +# Copyright (c) 2009 Steve Grubb sgrubb@redhat.com +# +AC_DEFUN([LINUX_AUDIT], +[ + AC_ARG_WITH(libaudit, + [ --with-libaudit=[auto/yes/no] Add Linux audit support [default=auto]],, + with_libaudit=auto) + + # Check for Linux auditing API + # + # libaudit detection + + if test x$with_libaudit = xno ; then + have_libaudit=no; + else + # See if we have audit daemon library + AC_CHECK_LIB(audit, audit_log_user_message, + AUDIT_LDADD=-laudit,) + fi + AC_SUBST(AUDIT_LDADD) + if test x$AUDIT_LDADD != x ; then + AC_DEFINE(HAVE_LIBAUDIT,1,[linux audit support]) + fi +]) diff --git a/util/Makefile.am b/util/Makefile.am index 5519341..6e1b5a1 100644 --- a/util/Makefile.am +++ b/util/Makefile.am @@ -45,7 +45,8 @@ reboot_SOURCES = \ reboot_LDFLAGS = -static reboot_LDADD = \ ../nih/libnih.la \ - $(LTLIBINTL) + $(LTLIBINTL) \ + $(AUDIT_LDADD) runlevel_SOURCES = \ runlevel.c \ @@ -66,7 +67,8 @@ shutdown_LDADD = \ ../nih/libnih.la \ ../nih-dbus/libnih-dbus.la \ $(LTLIBINTL) \ - $(DBUS_LIBS) + $(DBUS_LIBS) \ + $(AUDIT_LDADD) telinit_SOURCES = \ telinit.c \ @@ -79,7 +81,8 @@ telinit_LDADD = \ ../nih/libnih.la \ ../nih-dbus/libnih-dbus.la \ $(LTLIBINTL) \ - $(DBUS_LIBS) + $(DBUS_LIBS) \ + $(AUDIT_LDADD) com_ubuntu_Upstart_OUTPUTS = \ @@ -201,7 +204,8 @@ test_sysv_LDADD = \ ../nih/libnih.la \ ../nih-dbus/libnih-dbus.la \ $(LTLIBINTL) \ - $(DBUS_LIBS) + $(DBUS_LIBS) \ + $(AUDIT_LDADD) test_telinit_SOURCES = tests/test_telinit.c telinit.c test_telinit_CFLAGS = $(AM_CFLAGS) -DTEST @@ -212,7 +216,8 @@ test_telinit_LDADD = \ com.ubuntu.Upstart.Job.o com.ubuntu.Upstart.Instance.o \ ../nih/libnih.la \ ../nih-dbus/libnih-dbus.la \ - $(DBUS_LIBS) + $(DBUS_LIBS) \ + $(AUDIT_LDADD) .PHONY: tests diff --git a/util/reboot.c b/util/reboot.c index dda2935..57e5467 100644 --- a/util/reboot.c +++ b/util/reboot.c @@ -36,6 +36,10 @@ #include #include +#ifdef HAVE_LIBAUDIT +#include +#endif + #include "utmp.h" @@ -96,7 +100,6 @@ static int poweroff = FALSE; **/ static int exit_only = FALSE; - /** * options: * @@ -119,6 +122,7 @@ static NihOption options[] = { NIH_OPTION_LAST }; +static void send_audit_event(void); int main (int argc, @@ -216,6 +220,8 @@ main (int argc, /* Re-enable Control-Alt-Delete in case it breaks */ reboot (RB_ENABLE_CAD); + send_audit_event (); + /* Do the syscall */ switch (mode) { case REBOOT: @@ -237,3 +243,21 @@ main (int argc, return 0; } + +/** + * send_audit_event + * + * Send system shutdown audit event + **/ +static void +send_audit_event (void) +{ +#ifdef HAVE_LIBAUDIT + int fd = audit_open (); + if (fd < 0) + return; + audit_log_user_message (fd, AUDIT_SYSTEM_SHUTDOWN, "init", + NULL, NULL, NULL, 1); + close (fd); +#endif +} diff --git a/util/sysv.c b/util/sysv.c index fbca39f..f4548ec 100644 --- a/util/sysv.c +++ b/util/sysv.c @@ -36,6 +36,11 @@ #include #include +#include +#ifdef HAVE_LIBAUDIT +#include +#endif + #include "dbus/upstart.h" #include "utmp.h" @@ -54,6 +59,7 @@ /* Prototypes for static functions */ static void error_handler (NihError **err, NihDBusMessage *message); +static void send_audit_event (int old, int level); /** @@ -161,6 +167,8 @@ sysv_change_runlevel (int runlevel, runlevel, prevlevel) < 0) nih_free (nih_error_get ()); + send_audit_event(prevlevel, runlevel); + /* Make the EmitEvent call, we don't wait for the event to finish * because sysvinit never did. */ @@ -199,3 +207,41 @@ error_handler (NihError ** err, { *err = nih_error_steal (); } + +/** + * send_audit_event + * @old: current run level + * @level: new run level + * + * Send system runlevel change audit event. If level is 0, then + * we consider this to be a reboot event. + **/ +static void +send_audit_event (int old, int level) +{ +#ifdef HAVE_LIBAUDIT + int fd = audit_open (); + + if (fd < 0) + return; + + /* first runlevel change after boot */ + if (old == 'N') + audit_log_user_message (fd, AUDIT_SYSTEM_BOOT, "init", + NULL, NULL, NULL, 1); + + char buf[64]; + + snprintf (buf, sizeof (buf), + "old-level=%c new-level=%c", old, level); + audit_log_user_message (fd, AUDIT_SYSTEM_RUNLEVEL, buf, + NULL, NULL, NULL, 1); + + /* shutdown or reboot */ + if (level == '0' || level == '6') + audit_log_user_message (fd, AUDIT_SYSTEM_SHUTDOWN, "init", + NULL, NULL, NULL, 1); + + close (fd); +#endif +}