chiark / gitweb /
bus: make sd_bus_request_name() and sd_bus_release_name() behave more like other...
[elogind.git] / src / timedate / timedated.c
index 61f8fc55b5cd026d06045d9e5030604ef510b3bb..0641f3955167e0f008d5967848f977a1d9007ff9 100644 (file)
@@ -45,8 +45,8 @@
 typedef struct Context {
         char *zone;
         bool local_rtc;
-        int can_ntp;
-        int use_ntp;
+        unsigned can_ntp;
+        unsigned use_ntp;
         Hashmap *polkit_registry;
 } Context;
 
@@ -458,8 +458,8 @@ static int property_get_rtc_time(
                 const char *interface,
                 const char *property,
                 sd_bus_message *reply,
-                sd_bus_error *error,
-                void *userdata) {
+                void *userdata,
+                sd_bus_error *error) {
 
         struct tm tm;
         usec_t t;
@@ -467,18 +467,15 @@ static int property_get_rtc_time(
 
         zero(tm);
         r = hwclock_get_time(&tm);
-        if (r < 0) {
-                sd_bus_error_set_errnof(error, -r, "Failed to read RTC: %s", strerror(-r));
-                return r;
-        }
-
-        t = (usec_t) mktime(&tm) * USEC_PER_SEC;
-
-        r = sd_bus_message_append(reply, "t", t);
-        if (r < 0)
-                return r;
+        if (r == -EBUSY) {
+                log_warning("/dev/rtc is busy, is somebody keeping it open continously? That's not a good idea... Returning a bogus RTC timestamp.");
+                t = 0;
+        } else if (r < 0)
+                return sd_bus_error_set_errnof(error, r, "Failed to read RTC: %s", strerror(-r));
+        else
+                t = (usec_t) timegm(&tm) * USEC_PER_SEC;
 
-        return 1;
+        return sd_bus_message_append(reply, "t", t);
 }
 
 static int property_get_time(
@@ -487,16 +484,10 @@ static int property_get_time(
                 const char *interface,
                 const char *property,
                 sd_bus_message *reply,
-                sd_bus_error *error,
-                void *userdata) {
+                void *userdata,
+                sd_bus_error *error) {
 
-        int r;
-
-        r = sd_bus_message_append(reply, "t", now(CLOCK_REALTIME));
-        if (r < 0)
-                return r;
-
-        return 1;
+        return sd_bus_message_append(reply, "t", now(CLOCK_REALTIME));
 }
 
 static int property_get_ntp_sync(
@@ -505,23 +496,16 @@ static int property_get_ntp_sync(
                 const char *interface,
                 const char *property,
                 sd_bus_message *reply,
-                sd_bus_error *error,
-                void *userdata) {
-
-        int r;
+                void *userdata,
+                sd_bus_error *error) {
 
-        r = sd_bus_message_append(reply, "b", ntp_synced());
-        if (r < 0)
-                return r;
-
-        return 1;
+        return sd_bus_message_append(reply, "b", ntp_synced());
 }
 
-static int method_set_timezone(sd_bus *bus, sd_bus_message *m, void *userdata) {
-        _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
+static int method_set_timezone(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *error) {
         Context *c = userdata;
         const char *z;
-        bool interactive;
+        int interactive;
         char *t;
         int r;
 
@@ -531,23 +515,23 @@ static int method_set_timezone(sd_bus *bus, sd_bus_message *m, void *userdata) {
 
         r = sd_bus_message_read(m, "sb", &z, &interactive);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, NULL);
+                return r;
 
         if (!valid_timezone(z))
-                return sd_bus_reply_method_errorf(bus, m, SD_BUS_ERROR_INVALID_ARGS, "Invalid time zone '%s'", z);
+                return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid time zone '%s'", z);
 
         if (streq_ptr(z, c->zone))
-                return sd_bus_reply_method_return(bus, m, NULL);
+                return sd_bus_reply_method_return(m, NULL);
 
-        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-timezone", interactive, &error, method_set_timezone, c);
+        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-timezone", interactive, error, method_set_timezone, c);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
         if (r == 0)
                 return 1; /* No authorization for now, but the async polkit stuff will call us again when it has it */
 
         t = strdup(z);
         if (!t)
-                return log_oom();
+                return -ENOMEM;
 
         free(c->zone);
         c->zone = t;
@@ -556,7 +540,7 @@ static int method_set_timezone(sd_bus *bus, sd_bus_message *m, void *userdata) {
         r = context_write_data_timezone(c);
         if (r < 0) {
                 log_error("Failed to set timezone: %s", strerror(-r));
-                return sd_bus_reply_method_errnof(bus, m, r, "Failed to set timezone: %s", strerror(-r));
+                return sd_bus_error_set_errnof(error, r, "Failed to set timezone: %s", strerror(-r));
         }
 
         /* 2. Tell the kernel our timezone */
@@ -580,12 +564,11 @@ static int method_set_timezone(sd_bus *bus, sd_bus_message *m, void *userdata) {
 
         sd_bus_emit_properties_changed(bus, "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "Timezone", NULL);
 
-        return sd_bus_reply_method_return(bus, m, NULL);
+        return sd_bus_reply_method_return(m, NULL);
 }
 
-static int method_set_local_rtc(sd_bus *bus, sd_bus_message *m, void *userdata) {
-        _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
-        bool lrtc, fix_system, interactive;
+static int method_set_local_rtc(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *error) {
+        int lrtc, fix_system, interactive;
         Context *c = userdata;
         struct timespec ts;
         int r;
@@ -596,14 +579,14 @@ static int method_set_local_rtc(sd_bus *bus, sd_bus_message *m, void *userdata)
 
         r = sd_bus_message_read(m, "bbb", &lrtc, &fix_system, &interactive);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, NULL);
+                return r;
 
         if (lrtc == c->local_rtc)
-                return sd_bus_reply_method_return(bus, m, NULL);
+                return sd_bus_reply_method_return(m, NULL);
 
-        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-local-rtc", interactive, &error, method_set_local_rtc, c);
+        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-local-rtc", interactive, error, method_set_local_rtc, c);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
         if (r == 0)
                 return 1;
 
@@ -613,7 +596,7 @@ static int method_set_local_rtc(sd_bus *bus, sd_bus_message *m, void *userdata)
         r = context_write_data_local_rtc(c);
         if (r < 0) {
                 log_error("Failed to set RTC to local/UTC: %s", strerror(-r));
-                return sd_bus_reply_method_errnof(bus, m, r, "Failed to set RTC to local/UTC: %s", strerror(-r));
+                return sd_bus_error_set_errnof(error, r, "Failed to set RTC to local/UTC: %s", strerror(-r));
         }
 
         /* 2. Tell the kernel our timezone */
@@ -664,12 +647,11 @@ static int method_set_local_rtc(sd_bus *bus, sd_bus_message *m, void *userdata)
 
         sd_bus_emit_properties_changed(bus, "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "LocalRTC", NULL);
 
-        return sd_bus_reply_method_return(bus, m, NULL);
+        return sd_bus_reply_method_return(m, NULL);
 }
 
-static int method_set_time(sd_bus *bus, sd_bus_message *m, void *userdata) {
-        _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
-        bool relative, interactive;
+static int method_set_time(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *error) {
+        int relative, interactive;
         Context *c = userdata;
         int64_t utc;
         struct timespec ts;
@@ -682,13 +664,13 @@ static int method_set_time(sd_bus *bus, sd_bus_message *m, void *userdata) {
 
         r = sd_bus_message_read(m, "xbb", &utc, &relative, &interactive);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, NULL);
+                return r;
 
         if (!relative && utc <= 0)
-                return sd_bus_reply_method_errorf(bus, m, SD_BUS_ERROR_INVALID_ARGS, "Invalid absolute time");
+                return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Invalid absolute time");
 
         if (relative && utc == 0)
-                return sd_bus_reply_method_return(bus, m, NULL);
+                return sd_bus_reply_method_return(m, NULL);
 
         if (relative) {
                 usec_t n, x;
@@ -698,22 +680,22 @@ static int method_set_time(sd_bus *bus, sd_bus_message *m, void *userdata) {
 
                 if ((utc > 0 && x < n) ||
                     (utc < 0 && x > n))
-                        return sd_bus_reply_method_errorf(bus, m, SD_BUS_ERROR_INVALID_ARGS, "Time value overflow");
+                        return sd_bus_error_setf(error, SD_BUS_ERROR_INVALID_ARGS, "Time value overflow");
 
                 timespec_store(&ts, x);
         } else
                 timespec_store(&ts, (usec_t) utc);
 
-        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-time", interactive, &error, method_set_time, c);
+        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-time", interactive, error, method_set_time, c);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
         if (r == 0)
                 return 1;
 
         /* Set system clock */
         if (clock_settime(CLOCK_REALTIME, &ts) < 0) {
                 log_error("Failed to set local time: %m");
-                return sd_bus_reply_method_errnof(bus, m, errno, "Failed to set local time: %m");
+                return sd_bus_error_set_errnof(error, errno, "Failed to set local time: %m");
         }
 
         /* Sync down to RTC */
@@ -730,43 +712,42 @@ static int method_set_time(sd_bus *bus, sd_bus_message *m, void *userdata) {
                    "MESSAGE=Changed local time to %s", ctime(&ts.tv_sec),
                    NULL);
 
-        return sd_bus_reply_method_return(bus, m, NULL);
+        return sd_bus_reply_method_return(m, NULL);
 }
 
-static int method_set_ntp(sd_bus *bus, sd_bus_message *m, void *userdata) {
-        _cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
-        bool ntp, interactive;
+static int method_set_ntp(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *error) {
+        int ntp, interactive;
         Context *c = userdata;
         int r;
 
         r = sd_bus_message_read(m, "bb", &ntp, &interactive);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, NULL);
+                return r;
 
-        if (ntp == c->use_ntp)
-                return sd_bus_reply_method_return(bus, m, NULL);
+        if ((bool)ntp == c->use_ntp)
+                return sd_bus_reply_method_return(m, NULL);
 
-        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-ntp", interactive, &error, method_set_ntp, c);
+        r = bus_verify_polkit_async(bus, &c->polkit_registry, m, "org.freedesktop.timedate1.set-ntp", interactive, error, method_set_ntp, c);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
         if (r == 0)
                 return 1;
 
         c->use_ntp = ntp;
 
-        r = context_enable_ntp(c, bus, &error);
+        r = context_enable_ntp(c, bus, error);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
 
-        r = context_start_ntp(c, bus, &error);
+        r = context_start_ntp(c, bus, error);
         if (r < 0)
-                return sd_bus_reply_method_errno(bus, m, r, &error);
+                return r;
 
         log_info("Set NTP to %s", c->use_ntp ? "enabled" : "disabled");
 
         sd_bus_emit_properties_changed(bus, "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "NTP", NULL);
 
-        return sd_bus_reply_method_return(bus, m, NULL);
+        return sd_bus_reply_method_return(m, NULL);
 }
 
 static const sd_bus_vtable timedate_vtable[] = {
@@ -793,7 +774,7 @@ static int connect_bus(Context *c, sd_event *event, sd_bus **_bus) {
         assert(event);
         assert(_bus);
 
-        r = sd_bus_open_system(&bus);
+        r = sd_bus_default_system(&bus);
         if (r < 0) {
                 log_error("Failed to get system bus connection: %s", strerror(-r));
                 return r;
@@ -805,17 +786,12 @@ static int connect_bus(Context *c, sd_event *event, sd_bus **_bus) {
                 return r;
         }
 
-        r = sd_bus_request_name(bus, "org.freedesktop.timedate1", SD_BUS_NAME_DO_NOT_QUEUE);
+        r = sd_bus_request_name(bus, "org.freedesktop.timedate1", SD_BUS_NAME_REPLACE_EXISTING|SD_BUS_NAME_DO_NOT_QUEUE);
         if (r < 0) {
                 log_error("Failed to register name: %s", strerror(-r));
                 return r;
         }
 
-        if (r != SD_BUS_NAME_PRIMARY_OWNER) {
-                log_error("Failed to acquire name.");
-                return -EEXIST;
-        }
-
         r = sd_bus_attach_event(bus, event, 0);
         if (r < 0) {
                 log_error("Failed to attach bus to event loop: %s", strerror(-r));
@@ -852,7 +828,7 @@ int main(int argc, char *argv[]) {
                 goto finish;
         }
 
-        r = sd_event_new(&event);
+        r = sd_event_default(&event);
         if (r < 0) {
                 log_error("Failed to allocate event loop: %s", strerror(-r));
                 goto finish;
@@ -880,7 +856,6 @@ int main(int argc, char *argv[]) {
                 goto finish;
         }
 
-        sd_bus_flush(bus);
         r = 0;
 
 finish: