summaryrefslogtreecommitdiffstats
path: root/meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch
diff options
context:
space:
mode:
Diffstat (limited to 'meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch')
-rw-r--r--meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch179
1 files changed, 179 insertions, 0 deletions
diff --git a/meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch b/meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch
new file mode 100644
index 000000000..a43c36b33
--- /dev/null
+++ b/meta-phosphor/recipes-core/systemd/systemd/0001-timedate-defer-the-property-changed-signal-until-job.patch
@@ -0,0 +1,179 @@
+From 3af0a96c0fcc623bd16649fc3640396a657cf9ef Mon Sep 17 00:00:00 2001
+From: Yu Watanabe <watanabe.yu+github@gmail.com>
+Date: Sun, 22 Jul 2018 23:10:02 +0900
+Subject: [PATCH] timedate: defer the property changed signal until job of
+ starting/stopping NTP service is finished
+
+Before this, the property changed signal is emitted immediately after
+StartUnit/StopUnit method is called. So, the running state of the NTP
+client service may not updated.
+This makes the timing of emitting property changed signal is deferred
+until job of starting/stopping NTP client service is completed.
+
+Fixes #9672.
+---
+ src/timedate/timedated.c | 78 ++++++++++++++++++++++++++++++++++++++++--------
+ 1 file changed, 65 insertions(+), 13 deletions(-)
+
+diff --git a/src/timedate/timedated.c b/src/timedate/timedated.c
+index 6c95764..012cbe0 100644
+--- a/src/timedate/timedated.c
++++ b/src/timedate/timedated.c
+@@ -46,6 +46,9 @@ typedef struct Context {
+ Hashmap *polkit_registry;
+ sd_bus_message *cache;
+
++ sd_bus_slot *slot_job_removed;
++ char *path_ntp_unit;
++
+ LIST_HEAD(UnitStatusInfo, units);
+ } Context;
+
+@@ -74,6 +77,9 @@ static void context_free(Context *c) {
+ bus_verify_polkit_async_registry_free(c->polkit_registry);
+ sd_bus_message_unref(c->cache);
+
++ sd_bus_slot_unref(c->slot_job_removed);
++ free(c->path_ntp_unit);
++
+ while ((p = c->units)) {
+ LIST_REMOVE(units, c->units, p);
+ unit_status_info_free(p);
+@@ -345,17 +351,55 @@ static int context_update_ntp_status(Context *c, sd_bus *bus, sd_bus_message *m)
+ return 0;
+ }
+
+-static int unit_start_or_stop(UnitStatusInfo *u, sd_bus *bus, sd_bus_error *error, bool start) {
++static int match_job_removed(sd_bus_message *m, void *userdata, sd_bus_error *error) {
++ const char *path;
++ Context *c = userdata;
++ int r;
++
++ assert(c);
++ assert(m);
++
++ r = sd_bus_message_read(m, "uoss", NULL, &path, NULL, NULL);
++ if (r < 0) {
++ bus_log_parse_error(r);
++ return 0;
++ }
++
++ if (!streq_ptr(path, c->path_ntp_unit))
++ return 0;
++
++ (void) sd_bus_emit_properties_changed(sd_bus_message_get_bus(m), "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "NTP", NULL);
++
++ c->slot_job_removed = sd_bus_slot_unref(c->slot_job_removed);
++ c->path_ntp_unit = mfree(c->path_ntp_unit);
++
++ return 0;
++}
++
++static int unit_start_or_stop(Context *c, UnitStatusInfo *u, sd_bus *bus, sd_bus_error *error, bool start) {
++ _cleanup_(sd_bus_message_unrefp) sd_bus_message *reply = NULL;
++ _cleanup_(sd_bus_slot_unrefp) sd_bus_slot *slot = NULL;
++ const char *path;
+ int r;
+
++ assert(c);
+ assert(u);
+ assert(bus);
+ assert(error);
+
+- /* Call context_update_ntp_status() to update UnitStatusInfo before calling this. */
++ /* This method may be called frequently. Forget the previous job if it has not completed yet. */
++ c->slot_job_removed = sd_bus_slot_unref(c->slot_job_removed);
+
+- if (streq(u->active_state, "active") == start)
+- return 0;
++ r = sd_bus_match_signal_async(
++ bus,
++ &slot,
++ "org.freedesktop.systemd1",
++ "/org/freedesktop/systemd1",
++ "org.freedesktop.systemd1.Manager",
++ "JobRemoved",
++ match_job_removed, NULL, c);
++ if (r < 0)
++ return r;
+
+ r = sd_bus_call_method(
+ bus,
+@@ -364,13 +408,22 @@ static int unit_start_or_stop(UnitStatusInfo *u, sd_bus *bus, sd_bus_error *erro
+ "org.freedesktop.systemd1.Manager",
+ start ? "StartUnit" : "StopUnit",
+ error,
+- NULL,
++ &reply,
+ "ss",
+ u->name,
+ "replace");
+ if (r < 0)
+ return r;
+
++ r = sd_bus_message_read(reply, "o", &path);
++ if (r < 0)
++ return bus_log_parse_error(r);
++
++ r = free_and_strdup(&c->path_ntp_unit, path);
++ if (r < 0)
++ return log_oom();
++
++ c->slot_job_removed = TAKE_PTR(slot);
+ return 0;
+ }
+
+@@ -422,8 +475,9 @@ static int unit_enable_or_disable(UnitStatusInfo *u, sd_bus *bus, sd_bus_error *
+ error,
+ NULL,
+ NULL);
+- if (r < 0)
+- return r;
++ if (r < 0)
++ return r;
++
+ return 0;
+ }
+
+@@ -813,7 +867,7 @@ static int method_set_ntp(sd_bus_message *m, void *userdata, sd_bus_error *error
+ if (q < 0)
+ r = q;
+
+- q = unit_start_or_stop(u, bus, error, enable);
++ q = unit_start_or_stop(c, u, bus, error, enable);
+ if (q < 0)
+ r = q;
+ }
+@@ -827,17 +881,17 @@ static int method_set_ntp(sd_bus_message *m, void *userdata, sd_bus_error *error
+ if (r < 0)
+ continue;
+
+- r = unit_start_or_stop(u, bus, error, enable);
++ r = unit_start_or_stop(c, u, bus, error, enable);
+ break;
+ }
+
+- else if (context_ntp_service_is_active(c) <= 0)
++ else
+ LIST_FOREACH(units, u, c->units) {
+ if (!streq(u->load_state, "loaded") ||
+ !streq(u->unit_file_state, "enabled"))
+ continue;
+
+- r = unit_start_or_stop(u, bus, error, enable);
++ r = unit_start_or_stop(c, u, bus, error, enable);
+ break;
+ }
+
+@@ -846,8 +900,6 @@ static int method_set_ntp(sd_bus_message *m, void *userdata, sd_bus_error *error
+
+ log_info("Set NTP to %sd", enable_disable(enable));
+
+- (void) sd_bus_emit_properties_changed(bus, "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "NTP", NULL);
+-
+ return sd_bus_reply_method_return(m, NULL);
+ }
+
+--
+2.7.4
+
OpenPOWER on IntegriCloud