diff --git a/SOURCES/0845-core-Detect-initial-timer-state-from-serialized-data.patch b/SOURCES/0845-core-Detect-initial-timer-state-from-serialized-data.patch new file mode 100644 index 0000000..2cfce58 --- /dev/null +++ b/SOURCES/0845-core-Detect-initial-timer-state-from-serialized-data.patch @@ -0,0 +1,140 @@ +From b9914f359690e83303ee8a2ffa4d60cdf76f2a90 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michal=20Koutn=C3=BD?= +Date: Fri, 2 Nov 2018 20:56:08 +0100 +Subject: [PATCH] core: Detect initial timer state from serialized data + +We keep a mark whether a single-shot timer was triggered in the caller's +variable initial. When such a timer elapses while we are +serializing/deserializing the inner state, we consider the timer +incorrectly as elapsed and don't trigger it later. + +This patch exploits last_trigger timestamp that we already serialize, +hence we can eliminate the argument initial completely. + +A reproducer for OnBootSec= timers: + cat >repro.c < + #include + #include + #include + #include + #include + #include + #include + + int main(int argc, char *argv[]) { + char command[1024]; + int pause; + + struct timespec now; + + while (1) { + usleep(rand() % 200000); // prevent periodic repeats + clock_gettime(CLOCK_MONOTONIC, &now); + printf("%i\n", now.tv_sec); + + system("rm -f $PWD/mark"); + snprintf(command, 1024, "systemd-run --user --on-boot=%i --timer-property=AccuracySec=100ms " + "touch $PWD/mark", now.tv_sec + 1); + system(command); + system("systemctl --user list-timers"); + pause = (1000000000 - now.tv_nsec)/1000 - 70000; // fiddle to hit the middle of reloading + usleep(pause > 0 ? pause : 0); + system("systemctl --user daemon-reload"); + sync(); + sleep(2); + if (open("./mark", 0) < 0) + if (errno == ENOENT) { + printf("mark file does not exist\n"); + break; + } + } + + return 0; + } + EOD + +(cherry picked from commit aa1f95d2647197eca84c33a0f10adaeada08467d) + +Resolves: #1764908 +--- + src/core/timer.c | 16 ++++++++-------- + 1 file changed, 8 insertions(+), 8 deletions(-) + +diff --git a/src/core/timer.c b/src/core/timer.c +index fb192d5..b36700c 100644 +--- a/src/core/timer.c ++++ b/src/core/timer.c +@@ -267,10 +267,10 @@ static void timer_set_state(Timer *t, TimerState state) { + unit_notify(UNIT(t), state_translation_table[old_state], state_translation_table[state], true); + } + +-static void timer_enter_waiting(Timer *t, bool initial); ++static void timer_enter_waiting(Timer *t); + + static int timer_enter_waiting_coldplug(Unit *u) { +- timer_enter_waiting(TIMER(u), false); ++ timer_enter_waiting(TIMER(u)); + return 0; + } + +@@ -338,7 +338,7 @@ static void add_random(Timer *t, usec_t *v) { + log_unit_debug(UNIT(t)->id, "Adding %s random time.", format_timespan(s, sizeof(s), add, 0)); + } + +-static void timer_enter_waiting(Timer *t, bool initial) { ++static void timer_enter_waiting(Timer *t) { + bool found_monotonic = false, found_realtime = false; + usec_t ts_realtime, ts_monotonic; + usec_t base = 0; +@@ -442,7 +442,7 @@ static void timer_enter_waiting(Timer *t, bool initial) { + + v->next_elapse = base + v->value; + +- if (!initial && v->next_elapse < ts_monotonic && IN_SET(v->base, TIMER_ACTIVE, TIMER_BOOT, TIMER_STARTUP)) { ++ if (dual_timestamp_is_set(&t->last_trigger) && v->next_elapse < ts_monotonic && IN_SET(v->base, TIMER_ACTIVE, TIMER_BOOT, TIMER_STARTUP)) { + /* This is a one time trigger, disable it now */ + v->disabled = true; + continue; +@@ -619,7 +619,7 @@ static int timer_start(Unit *u) { + } + + t->result = TIMER_SUCCESS; +- timer_enter_waiting(t, true); ++ timer_enter_waiting(t); + return 1; + } + +@@ -742,14 +742,14 @@ static void timer_trigger_notify(Unit *u, Unit *other) { + case TIMER_ELAPSED: + + /* Recalculate sleep time */ +- timer_enter_waiting(t, false); ++ timer_enter_waiting(t); + break; + + case TIMER_RUNNING: + + if (UNIT_IS_INACTIVE_OR_FAILED(unit_active_state(other))) { + log_unit_debug(UNIT(t)->id, "%s got notified about unit deactivation.", UNIT(t)->id); +- timer_enter_waiting(t, false); ++ timer_enter_waiting(t); + } + break; + +@@ -782,7 +782,7 @@ static void timer_time_change(Unit *u) { + return; + + log_unit_debug(u->id, "%s: time change, recalculating next elapse.", u->id); +- timer_enter_waiting(t, false); ++ timer_enter_waiting(t); + } + + static const char* const timer_state_table[_TIMER_STATE_MAX] = { +-- +2.26.2 + diff --git a/SOURCES/9999-Update-kernel-install-script-by-backporting-fedora-p.patch b/SOURCES/9999-Update-kernel-install-script-by-backporting-fedora-p.patch deleted file mode 100644 index c42f0b6..0000000 --- a/SOURCES/9999-Update-kernel-install-script-by-backporting-fedora-p.patch +++ /dev/null @@ -1,57 +0,0 @@ -From c49c37d5e26bf71a97d5194d390f80d3e71758e1 Mon Sep 17 00:00:00 2001 -From: systemd team -Date: Tue, 23 Apr 2019 10:46:19 -0300 -Subject: [PATCH] Update kernel-install script by backporting fedora patches - ---- - src/kernel-install/kernel-install | 30 +++++++++++++++++------------- - 1 file changed, 17 insertions(+), 13 deletions(-) - -diff --git a/src/kernel-install/kernel-install b/src/kernel-install/kernel-install -index f1c74de..d860701 100755 ---- a/src/kernel-install/kernel-install -+++ b/src/kernel-install/kernel-install -@@ -73,23 +73,27 @@ KERNEL_IMAGE="$2" - - if [[ -x /sbin/new-kernel-pkg ]]; then - KERNEL_DIR="${KERNEL_IMAGE%/*}" -- if [[ "${KERNEL_DIR}" != "/boot" ]]; then -- for i in \ -- "$KERNEL_IMAGE" \ -- "$KERNEL_DIR/.${KERNEL_IMAGE##*/}.hmac" \ -- "$KERNEL_DIR"/System.map \ -- "$KERNEL_DIR"/config \ -- "$KERNEL_DIR"/zImage.stub \ -- "$KERNEL_DIR"/dtb \ -- ; do -- [[ -e "$i" ]] || continue -- cp -a "$i" "/boot/${i##*/}-${KERNEL_VERSION}" -- done -- fi - - [[ "$KERNEL_VERSION" == *\+* ]] && flavor=-"${KERNEL_VERSION##*+}" - case "$COMMAND" in - add) -+ if [[ "${KERNEL_DIR}" != "/boot" ]]; then -+ for i in \ -+ "$KERNEL_IMAGE" \ -+ "$KERNEL_DIR"/System.map \ -+ "$KERNEL_DIR"/config \ -+ "$KERNEL_DIR"/zImage.stub \ -+ "$KERNEL_DIR"/dtb \ -+ ; do -+ [[ -e "$i" ]] || continue -+ cp -aT "$i" "/boot/${i##*/}-${KERNEL_VERSION}" -+ done -+ # hmac is .vmlinuz-.hmac so needs a special treatment -+ i="$KERNEL_DIR/.${KERNEL_IMAGE##*/}.hmac" -+ if [[ -e "$i" ]]; then -+ cp -aT "$i" "/boot/.${KERNEL_IMAGE##*/}-${KERNEL_VERSION}.hmac" -+ fi -+ fi - /sbin/new-kernel-pkg --package "kernel${flavor}" --install "$KERNEL_VERSION" || exit $? - /sbin/new-kernel-pkg --package "kernel${flavor}" --mkinitrd --dracut --depmod --update "$KERNEL_VERSION" || exit $? - /sbin/new-kernel-pkg --package "kernel${flavor}" --rpmposttrans "$KERNEL_VERSION" || exit $? --- -1.8.3.1 - diff --git a/SPECS/systemd.spec b/SPECS/systemd.spec index 348249f..7a4a066 100644 --- a/SPECS/systemd.spec +++ b/SPECS/systemd.spec @@ -7,7 +7,7 @@ Name: systemd Url: http://www.freedesktop.org/wiki/Software/systemd Version: 219 -Release: 78%{?dist}.2 +Release: 78%{?dist}.3 # For a breakdown of the licensing, see README License: LGPLv2+ and MIT and GPLv2+ Summary: A System and Service Manager @@ -883,7 +883,7 @@ Patch0841: 0841-device-don-t-emit-PropetiesChanged-needlessly.patch Patch0842: 0842-core-don-t-update-unit-description-if-it-is-already-.patch Patch0843: 0843-unit-don-t-emit-PropertiesChanged-signal-if-adding-a.patch Patch0844: 0844-core-fix-unnecessary-fallback-to-the-rescue-mode-cau.patch -Patch9999: 9999-Update-kernel-install-script-by-backporting-fedora-p.patch +Patch0845: 0845-core-Detect-initial-timer-state-from-serialized-data.patch %global num_patches %{lua: c=0; for i,p in ipairs(patches) do c=c+1; end; print(c);} @@ -1861,6 +1861,9 @@ fi %{_mandir}/man8/systemd-resolved.* %changelog +* Fri Jan 15 2021 systemd maintenance team - 219-78.3 +- core: Detect initial timer state from serialized data (#1764908) + * Mon Oct 19 2020 systemd maintenance team - 219-78.2 - core: don't update unit description if it is already set to the same value (#1793527) - unit: don't emit PropertiesChanged signal if adding a dependency to a unit is a no-op (#1793527)