? config.cache ? dbus-1.1.1.tar.gz ? test/data/valid-config-files/session.d ? test/name-test/run-with-tmp-session-bus.conf Index: ChangeLog =================================================================== RCS file: /cvs/dbus/dbus/ChangeLog,v retrieving revision 1.1311 diff -u -p -r1.1311 ChangeLog --- ChangeLog 12 Jun 2007 19:39:47 -0000 1.1311 +++ ChangeLog 13 Jun 2007 16:27:31 -0000 @@ -1,3 +1,14 @@ +2007-06-13 Havoc Pennington + + * configure.ac, bus/selinux.c, dbus/dbus-sysdeps-unix-util.c: add + libaudit support, no clue what this means really but now we have + it. Patches from Fedora package. + + * bus/bus.c (bus_context_new): move selinux initialization after + changing to daemon user, patch from Fedora package + + * dbus/dbus-transport.c (auth_via_unix_user_function): fix a typo + 2007-06-12 Havoc Pennington * dbus/dbus-message.c (dbus_message_iter_open_container): improve Index: configure.in =================================================================== RCS file: /cvs/dbus/dbus/configure.in,v retrieving revision 1.206 diff -u -p -r1.206 configure.in --- configure.in 9 Jun 2007 21:53:18 -0000 1.206 +++ configure.in 13 Jun 2007 16:27:32 -0000 @@ -56,6 +56,7 @@ AC_ARG_ENABLE(doxygen-docs, AS_HELP_STRI AC_ARG_ENABLE(gcov, AS_HELP_STRING([--enable-gcov],[compile with coverage profiling instrumentation (gcc only)]),enable_gcov=$enableval,enable_gcov=no) AC_ARG_ENABLE(abstract-sockets, AS_HELP_STRING([--enable-abstract-sockets],[use abstract socket namespace (linux only)]),enable_abstract_sockets=$enableval,enable_abstract_sockets=auto) AC_ARG_ENABLE(selinux, AS_HELP_STRING([--enable-selinux],[build with SELinux support]),enable_selinux=$enableval,enable_selinux=auto) +AC_ARG_ENABLE(libaudit, [ --enable-libaudit build audit daemon support for SELinux],enable_libaudit=$enableval,enable_libaudit=auto) AC_ARG_ENABLE(dnotify, AS_HELP_STRING([--enable-dnotify],[build with dnotify support (linux only)]),enable_dnotify=$enableval,enable_dnotify=auto) AC_ARG_ENABLE(kqueue, AS_HELP_STRING([--enable-kqueue],[build with kqueue support]),enable_kqueue=$enableval,enable_kqueue=auto) AC_ARG_ENABLE(console-owner-file, AS_HELP_STRING([--enable-console-owner-file],[enable console owner file]),enable_console_owner_file=$enableval,enable_console_owner_file=auto) @@ -904,6 +905,27 @@ fi AM_CONDITIONAL(HAVE_CONSOLE_OWNER_FILE, test x$have_console_owner_file = xyes) +# libaudit detection +if test x$enable_libaudit = xno ; then + have_libaudit=no; +else + # See if we have audit daemon & capabilities library + AC_CHECK_LIB(audit, audit_log_user_avc_message, + have_libaudit=yes, have_libaudit=no) + if test x$have_libaudit = xyes ; then + AC_CHECK_LIB(cap, cap_set_proc, + have_libaudit=yes, have_libaudit=no) + fi +fi + +AM_CONDITIONAL(HAVE_LIBAUDIT, test x$have_libaudit = xyes) + +if test x$have_libaudit = xyes ; then + SELINUX_LIBS="$SELINUX_LIBS -laudit" + LIBS="-lcap $LIBS" + AC_DEFINE(HAVE_LIBAUDIT,1,[audit daemon SELinux support]) +fi + #### Set up final flags DBUS_CLIENT_CFLAGS= DBUS_CLIENT_LIBS="$THREAD_LIBS" Index: bus/bus.c =================================================================== RCS file: /cvs/dbus/dbus/bus/bus.c,v retrieving revision 1.79 diff -u -p -r1.79 bus.c --- bus/bus.c 9 Jun 2007 23:41:32 -0000 1.79 +++ bus/bus.c 13 Jun 2007 16:27:34 -0000 @@ -739,11 +739,6 @@ bus_context_new (const DBusString *confi _dbus_string_free (&pid); } - if (!bus_selinux_full_init ()) - { - _dbus_warn ("SELinux initialization failed\n"); - } - if (!process_config_postinit (context, parser, error)) { _DBUS_ASSERT_ERROR_IS_SET (error); @@ -767,6 +762,11 @@ bus_context_new (const DBusString *confi goto failed; } } + + if (!bus_selinux_full_init ()) + { + _dbus_warn ("SELinux initialization failed\n"); + } dbus_server_free_data_slot (&server_data_slot); Index: bus/selinux.c =================================================================== RCS file: /cvs/dbus/dbus/bus/selinux.c,v retrieving revision 1.19 diff -u -p -r1.19 selinux.c --- bus/selinux.c 8 Aug 2006 23:29:03 -0000 1.19 +++ bus/selinux.c 13 Jun 2007 16:27:35 -0000 @@ -38,6 +38,9 @@ #include #include #include +#ifdef HAVE_LIBAUDIT +#include +#endif /* HAVE_LIBAUDIT */ #endif /* HAVE_SELINUX */ #define BUS_SID_FROM_SELINUX(sid) ((BusSELinuxID*) (sid)) @@ -100,11 +103,50 @@ static const struct avc_lock_callback lo * @param variable argument list */ #ifdef HAVE_SELINUX + +#ifdef HAVE_LIBAUDIT +static int audit_fd = -1; +#endif + +static void +audit_init(void) +{ +#ifdef HAVE_LIBAUDIT + audit_fd = audit_open (); + + if (audit_fd < 0) + { + /* If kernel doesn't support audit, bail out */ + if (errno == EINVAL || errno == EPROTONOSUPPORT || errno == EAFNOSUPPORT) + return; + /* If user bus, bail out */ + if (errno == EPERM && getuid() != 0) + return; + _dbus_warn ("Failed opening connection to the audit subsystem"); + } +#endif /* HAVE_LIBAUDIT */ +} + static void log_callback (const char *fmt, ...) { va_list ap; + va_start(ap, fmt); + +#ifdef HAVE_LIBAUDIT + if (audit_fd >= 0) + { + char buf[PATH_MAX*2]; + + /* FIXME: need to change this to show real user */ + vsnprintf(buf, sizeof(buf), fmt, ap); + audit_log_user_avc_message(audit_fd, AUDIT_USER_AVC, buf, NULL, NULL, + NULL, getuid()); + return; + } +#endif /* HAVE_LIBAUDIT */ + vsyslog (LOG_INFO, fmt, ap); va_end(ap); } @@ -303,6 +345,8 @@ bus_selinux_full_init (void) freecon (bus_context); + audit_init (); + return TRUE; #else return TRUE; @@ -925,12 +969,18 @@ bus_selinux_shutdown (void) { sidput (bus_sid); bus_sid = SECSID_WILD; - + #ifdef DBUS_ENABLE_VERBOSE_MODE - bus_avc_print_stats (); + + if (_dbus_is_verbose()) + bus_avc_print_stats (); + #endif /* DBUS_ENABLE_VERBOSE_MODE */ avc_destroy (); +#ifdef HAVE_LIBAUDIT + audit_close (audit_fd); +#endif /* HAVE_LIBAUDIT */ } #endif /* HAVE_SELINUX */ } Index: dbus/dbus-sysdeps-util-unix.c =================================================================== RCS file: /cvs/dbus/dbus/dbus/dbus-sysdeps-util-unix.c,v retrieving revision 1.16 diff -u -p -r1.16 dbus-sysdeps-util-unix.c --- dbus/dbus-sysdeps-util-unix.c 9 Jun 2007 23:41:33 -0000 1.16 +++ dbus/dbus-sysdeps-util-unix.c 13 Jun 2007 16:27:37 -0000 @@ -43,6 +43,11 @@ #include #include #include +#ifdef HAVE_LIBAUDIT +#include +#include +#include +#endif /* HAVE_LIBAUDIT */ #ifdef HAVE_SYS_SYSLIMITS_H #include @@ -273,7 +278,11 @@ _dbus_change_to_daemon_user (const char dbus_uid_t uid; dbus_gid_t gid; DBusString u; - +#ifdef HAVE_LIBAUDIT + dbus_bool_t we_were_root; + cap_t new_caps; +#endif + _dbus_string_init_const (&u, user); if (!_dbus_get_user_id_and_primary_group (&u, &uid, &gid)) @@ -284,6 +293,58 @@ _dbus_change_to_daemon_user (const char return FALSE; } +#ifdef HAVE_LIBAUDIT + we_were_root = _dbus_getuid () == 0; + new_caps = NULL; + /* have a tmp set of caps that we use to transition to the usr/grp dbus should + * run as ... doesn't really help. But keeps people happy. + */ + + if (!we_were_root) + { + cap_value_t new_cap_list[] = { CAP_AUDIT_WRITE }; + cap_value_t tmp_cap_list[] = { CAP_AUDIT_WRITE, CAP_SETUID, CAP_SETGID }; + cap_t tmp_caps = cap_init(); + + if (!tmp_caps || !(new_caps = cap_init ())) + { + dbus_set_error (error, DBUS_ERROR_FAILED, + "Failed to initialize drop of capabilities: %s\n", + _dbus_strerror (errno)); + + if (tmp_caps) + cap_free (tmp_caps); + + return FALSE; + } + + /* assume these work... */ + cap_set_flag (new_caps, CAP_PERMITTED, 1, new_cap_list, CAP_SET); + cap_set_flag (new_caps, CAP_EFFECTIVE, 1, new_cap_list, CAP_SET); + cap_set_flag (tmp_caps, CAP_PERMITTED, 3, tmp_cap_list, CAP_SET); + cap_set_flag (tmp_caps, CAP_EFFECTIVE, 3, tmp_cap_list, CAP_SET); + + if (prctl (PR_SET_KEEPCAPS, 1, 0, 0, 0) == -1) + { + dbus_set_error (error, _dbus_error_from_errno (errno), + "Failed to set keep-capabilities: %s\n", + _dbus_strerror (errno)); + cap_free (tmp_caps); + goto fail; + } + + if (cap_set_proc (tmp_caps) == -1) + { + dbus_set_error (error, DBUS_ERROR_FAILED, + "Failed to drop capabilities: %s\n", + _dbus_strerror (errno)); + cap_free (tmp_caps); + goto fail; + } + cap_free (tmp_caps); + } +#endif /* HAVE_LIBAUDIT */ + /* setgroups() only works if we are a privileged process, * so we don't return error on failure; the only possible * failure is that we don't have perms to do it. @@ -303,7 +364,7 @@ _dbus_change_to_daemon_user (const char dbus_set_error (error, _dbus_error_from_errno (errno), "Failed to set GID to %lu: %s", gid, _dbus_strerror (errno)); - return FALSE; + goto fail; } if (setuid (uid) < 0) @@ -311,10 +372,45 @@ _dbus_change_to_daemon_user (const char dbus_set_error (error, _dbus_error_from_errno (errno), "Failed to set UID to %lu: %s", uid, _dbus_strerror (errno)); - return FALSE; + goto fail; } - return TRUE; +#ifdef HAVE_LIBAUDIT + if (!we_were_root) + { + if (cap_set_proc (new_caps)) + { + dbus_set_error (error, DBUS_ERROR_FAILED, + "Failed to drop capabilities: %s\n", + _dbus_strerror (errno)); + goto fail; + } + cap_free (new_caps); + + /* should always work, if it did above */ + if (prctl (PR_SET_KEEPCAPS, 0, 0, 0, 0) == -1) + { + dbus_set_error (error, _dbus_error_from_errno (errno), + "Failed to unset keep-capabilities: %s\n", + _dbus_strerror (errno)); + return FALSE; + } + } +#endif + + return TRUE; + + fail: +#ifdef HAVE_LIBAUDIT + if (!we_were_root) + { + /* should always work, if it did above */ + prctl (PR_SET_KEEPCAPS, 0, 0, 0, 0); + cap_free (new_caps); + } +#endif + + return FALSE; } /** Installs a UNIX signal handler Index: dbus/dbus-transport.c =================================================================== RCS file: /cvs/dbus/dbus/dbus/dbus-transport.c,v retrieving revision 1.57 diff -u -p -r1.57 dbus-transport.c --- dbus/dbus-transport.c 12 Jun 2007 18:36:19 -0000 1.57 +++ dbus/dbus-transport.c 13 Jun 2007 16:27:39 -0000 @@ -516,9 +516,9 @@ auth_via_unix_user_function (DBusTranspo connection = transport->connection; unix_user_function = transport->unix_user_function; unix_user_data = transport->unix_user_data; - uid = _dbus_credentials_get_unix_uid (auth_identity), + uid = _dbus_credentials_get_unix_uid (auth_identity); - _dbus_verbose ("unlock %s\n", _DBUS_FUNCTION_NAME); + _dbus_verbose ("unlock %s\n", _DBUS_FUNCTION_NAME); _dbus_connection_unlock (connection); allow = (* unix_user_function) (connection,