systemctl: restore "systemctl reboot ARG" functionality
authorVesa Jääskeläinen <vesa.jaaskelainen@vaisala.com>
Sat, 9 Mar 2019 20:30:45 +0000 (22:30 +0200)
committerMichael Biebl <biebl@debian.org>
Fri, 29 Jan 2021 14:16:06 +0000 (14:16 +0000)
Commit d85515edcf9700dc068201ab9f7103f04f3b25b2 changed logic how reboot is
executed. That commit changed behavior to use emergency action reboot code path
to perform the reboot.

This inadvertently broke rebooting with argument:
$ systemctl reboot custom-reason

Restore original behavior so that if reboot service unit similar to
systemd-reboot.service is executed it is possible to override reboot reason
with "systemctl reboot ARG".

When "systemctl reboot ARG" is executed ARG is placed in file
/run/systemd/reboot-param and reboot is issued using logind's Reboot
dbus-service.

If RebootArgument is specified in systemd-reboot.service it takes precedence
over what systemctl sets.

Fixes: #11828
(cherry picked from commit 77defcf5382a557189350f928967d676510e362c)

Gbp-Pq: Name systemctl-restore-systemctl-reboot-ARG-functionality.patch

src/core/emergency-action.c
src/shared/reboot-util.c
src/shared/reboot-util.h
src/systemctl/systemctl.c

index f98b0de7925d8155660474ed37e837a49492ad6f..52edec0419ab7b955c3b285715162f8a93f6610a 100644 (file)
@@ -47,7 +47,7 @@ int emergency_action(
         case EMERGENCY_ACTION_REBOOT:
                 log_and_status(m, warn, "Rebooting", reason);
 
-                (void) update_reboot_parameter_and_warn(reboot_arg);
+                (void) update_reboot_parameter_and_warn(reboot_arg, true);
                 (void) manager_add_job_by_name_and_warn(m, JOB_START, SPECIAL_REBOOT_TARGET, JOB_REPLACE_IRREVERSIBLY, NULL);
 
                 break;
@@ -55,7 +55,7 @@ int emergency_action(
         case EMERGENCY_ACTION_REBOOT_FORCE:
                 log_and_status(m, warn, "Forcibly rebooting", reason);
 
-                (void) update_reboot_parameter_and_warn(reboot_arg);
+                (void) update_reboot_parameter_and_warn(reboot_arg, true);
                 m->objective = MANAGER_REBOOT;
 
                 break;
index ca40159b96631d98cbcf9c15617a7ada5d7dddb4..6d5eee031734b287ea8103d8801620725c030236 100644 (file)
 #include "umask-util.h"
 #include "virt.h"
 
-int update_reboot_parameter_and_warn(const char *parameter) {
+int update_reboot_parameter_and_warn(const char *parameter, bool keep) {
         int r;
 
         if (isempty(parameter)) {
+                if (keep)
+                        return 0;
+
                 if (unlink("/run/systemd/reboot-param") < 0) {
                         if (errno == ENOENT)
                                 return 0;
index d459333efccb39de210c3e59235f13c703d4f171..ac59b7d79c68fcb279eaf7e0b5e55d55695f5cf9 100644 (file)
@@ -1,7 +1,7 @@
 /* SPDX-License-Identifier: LGPL-2.1+ */
 #pragma once
 
-int update_reboot_parameter_and_warn(const char *parameter);
+int update_reboot_parameter_and_warn(const char *parameter, bool keep);
 
 typedef enum RebootFlags {
         REBOOT_LOG      = 1 << 0, /* log about what we are going to do and all errors */
index 63dae2c87285667bc833206bacb83989b4d22fe1..d05219d924cb69e841602a7f0e824d0f0b20a4af 100644 (file)
@@ -3634,7 +3634,7 @@ static int start_special(int argc, char *argv[], void *userdata) {
                 return r;
 
         if (a == ACTION_REBOOT && argc > 1) {
-                r = update_reboot_parameter_and_warn(argv[1]);
+                r = update_reboot_parameter_and_warn(argv[1], false);
                 if (r < 0)
                         return r;
 
@@ -8005,7 +8005,7 @@ static int halt_parse_argv(int argc, char *argv[]) {
                 }
 
         if (arg_action == ACTION_REBOOT && (argc == optind || argc == optind + 1)) {
-                r = update_reboot_parameter_and_warn(argc == optind + 1 ? argv[optind] : NULL);
+                r = update_reboot_parameter_and_warn(argc == optind + 1 ? argv[optind] : NULL, false);
                 if (r < 0)
                         return r;
         } else if (optind < argc)