core: introduce "poweroff" as new failure action types

Also, change the default action on a system start-up timeout to powering off.
This commit is contained in:
Lennart Poettering 2014-08-22 16:59:46 +02:00
parent c4147df156
commit f07756bfe2
8 changed files with 70 additions and 21 deletions

View File

@ -298,7 +298,7 @@
setting, see
<citerefentry><refentrytitle>systemd.service</refentrytitle><manvolnum>5</manvolnum></citerefentry>
for details. Defaults to
<option>reboot-force</option>. <varname>StartTimeoutRebootArgument=</varname>
<option>poweroff-force</option>. <varname>StartTimeoutRebootArgument=</varname>
configures an optional reboot string
to pass to the
<citerefentry><refentrytitle>reboot</refentrytitle><manvolnum>2</manvolnum></citerefentry>

View File

@ -1131,26 +1131,35 @@ ExecStart=/bin/echo $ONE $TWO ${TWO}</programlisting>
hit. Takes one of
<option>none</option>,
<option>reboot</option>,
<option>reboot-force</option>, or
<option>reboot-immediate</option>. If
<option>none</option> is set,
hitting the rate limit will trigger no
action besides that the start will not
be permitted. <option>reboot</option>
<option>reboot-force</option>,
<option>reboot-immediate</option>,
<option>poweroff</option>,
<option>poweroff-force</option> or
<option>poweroff-immediate</option>. If
<option>none</option> is set, hitting
the rate limit will trigger no action
besides that the start will not be
permitted. <option>reboot</option>
causes a reboot following the normal
shutdown procedure (i.e. equivalent to
<command>systemctl reboot</command>).
<option>reboot-force</option> causes
a forced reboot which will terminate
all processes forcibly but should
cause no dirty file systems on reboot
<option>reboot-force</option> causes a
forced reboot which will terminate all
processes forcibly but should cause no
dirty file systems on reboot
(i.e. equivalent to <command>systemctl
reboot -f</command>) and
<option>reboot-immediate</option>
causes immediate execution of the
<citerefentry><refentrytitle>reboot</refentrytitle><manvolnum>2</manvolnum></citerefentry>
system call, which might result in
data loss. Defaults to
data loss. Similar,
<option>poweroff</option>,
<option>poweroff-force</option>,
<option>poweroff-immediate</option>
have the effect of powering down the
system with similar
semantics. Defaults to
<option>none</option>.</para></listitem>
</varlistentry>

View File

@ -40,10 +40,19 @@ int failure_action(
assert(action >= 0);
assert(action < _FAILURE_ACTION_MAX);
switch (action) {
if (action == FAILURE_ACTION_NONE)
return -ECANCELED;
case FAILURE_ACTION_NONE:
break;
if (m->running_as == SYSTEMD_USER) {
/* Downgrade all options to simply exiting if we run
* in user mode */
log_warning("Exiting as result of failure.");
m->exit_code = MANAGER_EXIT;
return -ECANCELED;
}
switch (action) {
case FAILURE_ACTION_REBOOT: {
_cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
@ -78,6 +87,32 @@ int failure_action(
reboot(RB_AUTOBOOT);
break;
case FAILURE_ACTION_POWEROFF: {
_cleanup_bus_error_free_ sd_bus_error error = SD_BUS_ERROR_NULL;
log_warning("Powering off as result of failure.");
r = manager_add_job_by_name(m, JOB_START, SPECIAL_POWEROFF_TARGET, JOB_REPLACE, true, &error, NULL);
if (r < 0)
log_error("Failed to poweroff: %s.", bus_error_message(&error, r));
break;
}
case FAILURE_ACTION_POWEROFF_FORCE:
log_warning("Forcibly powering off as result of failure.");
m->exit_code = MANAGER_POWEROFF;
break;
case FAILURE_ACTION_POWEROFF_IMMEDIATE:
log_warning("Powering off immediately as result of failure.");
sync();
log_info("Powering off.");
reboot(RB_POWER_OFF);
break;
default:
assert_not_reached("Unknown failure action");
}
@ -89,6 +124,9 @@ static const char* const failure_action_table[_FAILURE_ACTION_MAX] = {
[FAILURE_ACTION_NONE] = "none",
[FAILURE_ACTION_REBOOT] = "reboot",
[FAILURE_ACTION_REBOOT_FORCE] = "reboot-force",
[FAILURE_ACTION_REBOOT_IMMEDIATE] = "reboot-immediate"
[FAILURE_ACTION_REBOOT_IMMEDIATE] = "reboot-immediate",
[FAILURE_ACTION_POWEROFF] = "poweroff",
[FAILURE_ACTION_POWEROFF_FORCE] = "poweroff-force",
[FAILURE_ACTION_POWEROFF_IMMEDIATE] = "poweroff-immediate"
};
DEFINE_STRING_TABLE_LOOKUP(failure_action, FailureAction);

View File

@ -27,6 +27,9 @@ typedef enum FailureAction {
FAILURE_ACTION_REBOOT,
FAILURE_ACTION_REBOOT_FORCE,
FAILURE_ACTION_REBOOT_IMMEDIATE,
FAILURE_ACTION_POWEROFF,
FAILURE_ACTION_POWEROFF_FORCE,
FAILURE_ACTION_POWEROFF_IMMEDIATE,
_FAILURE_ACTION_MAX,
_FAILURE_ACTION_INVALID = -1
} FailureAction;

View File

@ -117,7 +117,7 @@ static bool arg_default_cpu_accounting = false;
static bool arg_default_blockio_accounting = false;
static bool arg_default_memory_accounting = false;
static usec_t arg_start_timeout_usec = DEFAULT_MANAGER_START_TIMEOUT_USEC;
static FailureAction arg_start_timeout_action = FAILURE_ACTION_REBOOT_FORCE;
static FailureAction arg_start_timeout_action = FAILURE_ACTION_POWEROFF_FORCE;
static char *arg_start_timeout_reboot_arg = NULL;
static void nop_handler(int sig) {}

View File

@ -436,7 +436,7 @@ int manager_new(SystemdRunningAs running_as, bool test_run, Manager **_m) {
m->exit_code = _MANAGER_EXIT_CODE_INVALID;
m->default_timer_accuracy_usec = USEC_PER_MINUTE;
m->start_timeout_usec = DEFAULT_MANAGER_START_TIMEOUT_USEC;
m->start_timeout_action = FAILURE_ACTION_REBOOT_FORCE;
m->start_timeout_action = FAILURE_ACTION_POWEROFF_FORCE;
m->idle_pipe[0] = m->idle_pipe[1] = m->idle_pipe[2] = m->idle_pipe[3] = -1;

View File

@ -435,8 +435,7 @@ int main(int argc, char *argv[]) {
if (read_one_line_file(REBOOT_PARAM_FILE, &param) >= 0) {
log_info("Rebooting with argument '%s'.", param);
syscall(SYS_reboot, LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2,
LINUX_REBOOT_CMD_RESTART2, param);
syscall(SYS_reboot, LINUX_REBOOT_MAGIC1, LINUX_REBOOT_MAGIC2, LINUX_REBOOT_CMD_RESTART2, param);
}
}

View File

@ -24,7 +24,7 @@
#SystemCallArchitectures=
#TimerSlackNSec=
#StartTimeoutSec=15min
#StartTimeoutAction=reboot-force
#StartTimeoutAction=poweroff-force
#StartTimeoutRebootArgument=
#DefaultTimerAccuracySec=1min
#DefaultStandardOutput=journal