chiark / gitweb /
utmp: turn systemd-update-utmp-shutdown.service into a normal runtime service
[elogind.git] / src / update-utmp / update-utmp.c
index ec07b921256b1a0ad97f91cbd0b0e90ba85ba5e2..202aa987675b459b1b960b17f0e666c6f591ca4f 100644 (file)
@@ -48,38 +48,26 @@ typedef struct Context {
 static usec_t get_startup_time(Context *c) {
         const char
                 *interface = "org.freedesktop.systemd1.Manager",
-                *property = "StartupTimestamp";
+                *property = "UserspaceTimestamp";
 
-        DBusError error;
         usec_t t = 0;
-        DBusMessage *m = NULL, *reply = NULL;
+        DBusMessage *reply = NULL;
         DBusMessageIter iter, sub;
 
-        dbus_error_init(&error);
-
         assert(c);
 
-        if (!(m = dbus_message_new_method_call(
-                              "org.freedesktop.systemd1",
-                              "/org/freedesktop/systemd1",
-                              "org.freedesktop.DBus.Properties",
-                              "Get"))) {
-                log_error("Could not allocate message.");
-                goto finish;
-        }
-
-        if (!dbus_message_append_args(m,
-                                      DBUS_TYPE_STRING, &interface,
-                                      DBUS_TYPE_STRING, &property,
-                                      DBUS_TYPE_INVALID)) {
-                log_error("Could not append arguments to message.");
-                goto finish;
-        }
-
-        if (!(reply = dbus_connection_send_with_reply_and_block(c->bus, m, -1, &error))) {
-                log_error("Failed to send command: %s", bus_error_message(&error));
+        if (bus_method_call_with_reply (
+                        c->bus,
+                        "org.freedesktop.systemd1",
+                        "/org/freedesktop/systemd1",
+                        "org.freedesktop.DBus.Properties",
+                        "Get",
+                        &reply,
+                        NULL,
+                        DBUS_TYPE_STRING, &interface,
+                        DBUS_TYPE_STRING, &property,
+                        DBUS_TYPE_INVALID))
                 goto finish;
-        }
 
         if (!dbus_message_iter_init(reply, &iter) ||
             dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT)  {
@@ -97,14 +85,8 @@ static usec_t get_startup_time(Context *c) {
         dbus_message_iter_get_basic(&sub, &t);
 
 finish:
-        if (m)
-                dbus_message_unref(m);
-
         if (reply)
                 dbus_message_unref(reply);
-
-        dbus_error_free(&error);
-
         return t;
 }
 
@@ -122,13 +104,13 @@ static int get_current_runlevel(Context *c) {
                 { '3', SPECIAL_RUNLEVEL3_TARGET },
                 { '4', SPECIAL_RUNLEVEL4_TARGET },
                 { '2', SPECIAL_RUNLEVEL2_TARGET },
-                { 'S', SPECIAL_RESCUE_TARGET },
+                { '1', SPECIAL_RESCUE_TARGET },
         };
         const char
                 *interface = "org.freedesktop.systemd1.Unit",
                 *property = "ActiveState";
 
-        DBusMessage *m = NULL, *reply = NULL;
+        DBusMessage *reply = NULL;
         int r = 0;
         unsigned i;
         DBusError error;
@@ -141,28 +123,20 @@ static int get_current_runlevel(Context *c) {
                 const char *path = NULL, *state;
                 DBusMessageIter iter, sub;
 
-                if (!(m = dbus_message_new_method_call(
-                                      "org.freedesktop.systemd1",
-                                      "/org/freedesktop/systemd1",
-                                      "org.freedesktop.systemd1.Manager",
-                                      "GetUnit"))) {
-                        log_error("Could not allocate message.");
-                        r = -ENOMEM;
+                r = bus_method_call_with_reply (
+                                c->bus,
+                                "org.freedesktop.systemd1",
+                                "/org/freedesktop/systemd1",
+                                "org.freedesktop.systemd1.Manager",
+                                "GetUnit",
+                                &reply,
+                                NULL,
+                                DBUS_TYPE_STRING, &table[i].special,
+                                DBUS_TYPE_INVALID);
+                if (r == -ENOMEM)
                         goto finish;
-                }
-
-                if (!dbus_message_append_args(m,
-                                              DBUS_TYPE_STRING, &table[i].special,
-                                              DBUS_TYPE_INVALID)) {
-                        log_error("Could not append arguments to message.");
-                        r = -ENOMEM;
-                        goto finish;
-                }
-
-                if (!(reply = dbus_connection_send_with_reply_and_block(c->bus, m, -1, &error))) {
-                        dbus_error_free(&error);
+                if (r)
                         continue;
-                }
 
                 if (!dbus_message_get_args(reply, &error,
                                            DBUS_TYPE_OBJECT_PATH, &path,
@@ -172,32 +146,20 @@ static int get_current_runlevel(Context *c) {
                         goto finish;
                 }
 
-                dbus_message_unref(m);
-                if (!(m = dbus_message_new_method_call(
-                                      "org.freedesktop.systemd1",
-                                      path,
-                                      "org.freedesktop.DBus.Properties",
-                                      "Get"))) {
-                        log_error("Could not allocate message.");
-                        r = -ENOMEM;
-                        goto finish;
-                }
-
-                if (!dbus_message_append_args(m,
-                                              DBUS_TYPE_STRING, &interface,
-                                              DBUS_TYPE_STRING, &property,
-                                              DBUS_TYPE_INVALID)) {
-                        log_error("Could not append arguments to message.");
-                        r = -ENOMEM;
-                        goto finish;
-                }
-
                 dbus_message_unref(reply);
-                if (!(reply = dbus_connection_send_with_reply_and_block(c->bus, m, -1, &error))) {
-                        log_error("Failed to send command: %s", bus_error_message(&error));
-                        r = -EIO;
+                r = bus_method_call_with_reply (
+                                c->bus,
+                                "org.freedesktop.systemd1",
+                                path,
+                                "org.freedesktop.DBus.Properties",
+                                "Get",
+                                &reply,
+                                NULL,
+                                DBUS_TYPE_STRING, &interface,
+                                DBUS_TYPE_STRING, &property,
+                                DBUS_TYPE_INVALID);
+                if (r)
                         goto finish;
-                }
 
                 if (!dbus_message_iter_init(reply, &iter) ||
                     dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT)  {
@@ -219,18 +181,14 @@ static int get_current_runlevel(Context *c) {
                 if (streq(state, "active") || streq(state, "reloading"))
                         r = table[i].runlevel;
 
-                dbus_message_unref(m);
                 dbus_message_unref(reply);
-                m = reply = NULL;
+                reply = NULL;
 
                 if (r)
                         break;
         }
 
 finish:
-        if (m)
-                dbus_message_unref(m);
-
         if (reply)
                 dbus_message_unref(reply);
 
@@ -250,7 +208,8 @@ static int on_reboot(Context *c) {
 
 #ifdef HAVE_AUDIT
         if (c->audit_fd >= 0)
-                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_BOOT, "init", NULL, NULL, NULL, 1) < 0) {
+                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_BOOT, "init", NULL, NULL, NULL, 1) < 0 &&
+                    errno != EPERM) {
                         log_error("Failed to send audit message: %m");
                         r = -errno;
                 }
@@ -278,7 +237,8 @@ static int on_shutdown(Context *c) {
 
 #ifdef HAVE_AUDIT
         if (c->audit_fd >= 0)
-                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_SHUTDOWN, "init", NULL, NULL, NULL, 1) < 0) {
+                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_SHUTDOWN, "init", NULL, NULL, NULL, 1) < 0 &&
+                    errno != EPERM) {
                         log_error("Failed to send audit message: %m");
                         r = -errno;
                 }
@@ -330,7 +290,8 @@ static int on_runlevel(Context *c) {
                              runlevel > 0 ? runlevel : 'N') < 0)
                         return -ENOMEM;
 
-                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_RUNLEVEL, s, NULL, NULL, NULL, 1) < 0) {
+                if (audit_log_user_message(c->audit_fd, AUDIT_SYSTEM_RUNLEVEL, s, NULL, NULL, NULL, 1) < 0 &&
+                    errno != EPERM) {
                         log_error("Failed to send audit message: %m");
                         r = -errno;
                 }
@@ -340,8 +301,10 @@ static int on_runlevel(Context *c) {
 #endif
 
         if ((q = utmp_put_runlevel(runlevel, previous)) < 0) {
-                log_error("Failed to write utmp record: %s", strerror(-q));
-                r = q;
+                if (q != -ESRCH && q != -ENOENT) {
+                        log_error("Failed to write utmp record: %s", strerror(-q));
+                        r = q;
+                }
         }
 
         return r;
@@ -350,11 +313,10 @@ static int on_runlevel(Context *c) {
 int main(int argc, char *argv[]) {
         int r;
         DBusError error;
-        Context c;
+        Context c = {};
 
         dbus_error_init(&error);
 
-        zero(c);
 #ifdef HAVE_AUDIT
         c.audit_fd = -1;
 #endif