run: reject waiting for remain-after-exit services

Reproducer:
  unit=run-wait-rae-$(date +%s)
  sudo timeout 3s systemd-run --wait --remain-after-exit \
      --unit="$unit" /bin/true
  echo $?
  systemctl is-active "$unit.service"

Before, the command timed out with exit status 124 while the service
stayed active. --wait waits for deactivation, but RemainAfterExit=yes
keeps the service active after the command exits.

Follow-up for 2a453c2ee3
This commit is contained in:
dongshengyuan
2026-07-14 12:03:22 +08:00
parent 7e76e93142
commit 06247b0804
3 changed files with 16 additions and 3 deletions
+6 -3
View File
@@ -216,7 +216,9 @@
<listitem><para>After the service process has terminated, keep the service around until it is explicitly <listitem><para>After the service process has terminated, keep the service around until it is explicitly
stopped. This is useful to collect runtime information about the service after it finished running. Also see stopped. This is useful to collect runtime information about the service after it finished running. Also see
<varname>RemainAfterExit=</varname> in <varname>RemainAfterExit=</varname> in
<citerefentry><refentrytitle>systemd.service</refentrytitle><manvolnum>5</manvolnum></citerefentry>. <citerefentry><refentrytitle>systemd.service</refentrytitle><manvolnum>5</manvolnum></citerefentry>. This
option may not be combined with <option>--wait</option>, <option>--scope</option>, <option>--pty</option>,
<option>--pty-late</option>, or <option>--pipe</option>.
</para> </para>
<xi:include href="version-info.xml" xpointer="v207"/> <xi:include href="version-info.xml" xpointer="v207"/>
@@ -529,8 +531,9 @@
completed). On exit, terse information about the unit's runtime is shown, including total runtime (as well as completed). On exit, terse information about the unit's runtime is shown, including total runtime (as well as
CPU, memory, IO, and IP accounting data, if the corresponding cgroup accounting settings are enabled) CPU, memory, IO, and IP accounting data, if the corresponding cgroup accounting settings are enabled)
and the exit code and status of the main process. This output may be suppressed with <option>--quiet</option>. and the exit code and status of the main process. This output may be suppressed with <option>--quiet</option>.
This option may not be combined with <option>--no-block</option>, <option>--scope</option> or the various This option may not be combined with <option>--no-block</option>,
path, socket, or timer options.</para> <option>--remain-after-exit</option>, <option>--scope</option> or the various path, socket, or timer
options.</para>
<xi:include href="version-info.xml" xpointer="v232"/></listitem> <xi:include href="version-info.xml" xpointer="v232"/></listitem>
</varlistentry> </varlistentry>
+8
View File
@@ -717,6 +717,10 @@ static int parse_argv(int argc, char *argv[]) {
if (arg_no_block) if (arg_no_block)
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--pty/--pty-late/--pipe is not compatible with --no-block."); "--pty/--pty-late/--pipe is not compatible with --no-block.");
if (arg_remain_after_exit)
return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--pty/--pty-late/--pipe is not compatible with --remain-after-exit.");
} }
if (arg_stdio == ARG_STDIO_PTY && arg_pty_late && streq_ptr(arg_service_type, "oneshot")) if (arg_stdio == ARG_STDIO_PTY && arg_pty_late && streq_ptr(arg_service_type, "oneshot"))
@@ -761,6 +765,10 @@ static int parse_argv(int argc, char *argv[]) {
if (arg_scope) if (arg_scope)
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--wait may not be combined with --scope."); "--wait may not be combined with --scope.");
if (arg_remain_after_exit)
return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--wait may not be combined with --remain-after-exit.");
} }
if (arg_scope && arg_root_directory) if (arg_scope && arg_root_directory)
+2
View File
@@ -72,6 +72,8 @@ systemctl cat "$UNIT"
grep -q "^Type=oneshot" "/run/systemd/transient/$UNIT.service" grep -q "^Type=oneshot" "/run/systemd/transient/$UNIT.service"
systemctl stop "$UNIT" systemctl stop "$UNIT"
(! systemctl cat "$UNIT") (! systemctl cat "$UNIT")
(! systemd-run --wait --remain-after-exit true)
(! systemd-run --pipe --remain-after-exit true)
: "Transient service (user daemon)" : "Transient service (user daemon)"
systemd-run --wait --pipe --user --machine=testuser@ \ systemd-run --wait --pipe --user --machine=testuser@ \