* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
*/
+
+#include <config.h>
#include <dbus/dbus-internals.h>
#include <dbus/dbus-string.h>
+#ifndef DBUS_WIN
+#include <dbus/dbus-userdb.h>
+#endif
#include "selinux.h"
#include "services.h"
#include "policy.h"
#include "utils.h"
#include "config-parser.h"
-#ifdef HAVE_SELINUX
-#include <sys/types.h>
-#include <unistd.h>
#ifdef HAVE_ERRNO_H
#include <errno.h>
#endif
+#ifdef HAVE_SELINUX
+#include <sys/types.h>
+#include <unistd.h>
#include <limits.h>
#include <pthread.h>
#include <syslog.h>
#include <signal.h>
#include <stdarg.h>
#include <stdio.h>
+#include <grp.h>
+#endif /* HAVE_SELINUX */
#ifdef HAVE_LIBAUDIT
+#include <cap-ng.h>
#include <libaudit.h>
#endif /* HAVE_LIBAUDIT */
-#endif /* HAVE_SELINUX */
#define BUS_SID_FROM_SELINUX(sid) ((BusSELinuxID*) (sid))
#define SELINUX_SID_FROM_BUS(sid) ((security_id_t) (sid))
#ifdef HAVE_LIBAUDIT
if (audit_fd >= 0)
{
- char buf[PATH_MAX*2];
+ capng_get_caps_process();
+ if (capng_have_capability(CAPNG_EFFECTIVE, CAP_AUDIT_WRITE))
+ {
+ 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,
+ /* 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;
+ return;
+ }
}
#endif /* HAVE_LIBAUDIT */
#endif /* HAVE_SELINUX */
}
+/* The !HAVE_LIBAUDIT case lives in dbus-sysdeps-util-unix.c */
+#ifdef HAVE_LIBAUDIT
+/**
+ * Changes the user and group the bus is running as.
+ *
+ * @param user the user to become
+ * @param error return location for errors
+ * @returns #FALSE on failure
+ */
+dbus_bool_t
+_dbus_change_to_daemon_user (const char *user,
+ DBusError *error)
+{
+ dbus_uid_t uid;
+ dbus_gid_t gid;
+ DBusString u;
+
+ _dbus_string_init_const (&u, user);
+
+ if (!_dbus_get_user_id_and_primary_group (&u, &uid, &gid))
+ {
+ dbus_set_error (error, DBUS_ERROR_FAILED,
+ "User '%s' does not appear to exist?",
+ user);
+ return FALSE;
+ }
+
+ /* If we were root */
+ if (_dbus_geteuid () == 0)
+ {
+ int rc;
+
+ capng_clear (CAPNG_SELECT_BOTH);
+ capng_update (CAPNG_ADD, CAPNG_EFFECTIVE | CAPNG_PERMITTED,
+ CAP_AUDIT_WRITE);
+ rc = capng_change_id (uid, gid, 0);
+ if (rc)
+ {
+ switch (rc) {
+ default:
+ dbus_set_error (error, DBUS_ERROR_FAILED,
+ "Failed to drop capabilities: %s\n",
+ _dbus_strerror (errno));
+ break;
+ case -4:
+ dbus_set_error (error, _dbus_error_from_errno (errno),
+ "Failed to set GID to %lu: %s", gid,
+ _dbus_strerror (errno));
+ break;
+ case -5:
+ _dbus_warn ("Failed to drop supplementary groups: %s\n",
+ _dbus_strerror (errno));
+ break;
+ case -6:
+ dbus_set_error (error, _dbus_error_from_errno (errno),
+ "Failed to set UID to %lu: %s", uid,
+ _dbus_strerror (errno));
+ break;
+ case -7:
+ dbus_set_error (error, _dbus_error_from_errno (errno),
+ "Failed to unset keep-capabilities: %s\n",
+ _dbus_strerror (errno));
+ break;
+ }
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+#endif