Skip to content

Commit 82afcbd

Browse files
DaanDeMeyerbluca
authored andcommitted
shutdown: Send EXIT_STATUS before final sync
There's a race condition where the EXIT_STATUS= message we send just before shutting down the VM doesn't arrive on the host, presumably because the VM is shut down before the kernel has had a chance to forward the message to the host. Since there's no obvious way to wait until the message has been flushed to the host, let's send the message before we execute the final sync() instead of after executing the final sync(). In my testing, this seems to either guarantee the message is sent or introduces sufficient delay that the kernel always has time to flush its socket buffers to the host. (cherry picked from commit c88753d)
1 parent 6da5ca9 commit 82afcbd

File tree

1 file changed

+7
-4
lines changed

1 file changed

+7
-4
lines changed

src/shutdown/shutdown.c

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -387,6 +387,13 @@ int main(int argc, char *argv[]) {
387387
goto error;
388388
}
389389

390+
/* This is primarily useful when running systemd in a VM, as it provides the user running the VM with
391+
* a mechanism to pick up systemd's exit status in the VM. Note that we execute this as early as
392+
* possible since otherwise we might shut down the VM before the AF_VSOCK buffers have been flushed.
393+
* While this doesn't guarantee the message will arrive, in practice we do enough work after this
394+
* that the message should always arrive on the host */
395+
(void) sd_notifyf(0, "EXIT_STATUS=%i", arg_exit_code);
396+
390397
(void) cg_get_root_path(&cgroup);
391398
bool in_container = detect_container() > 0;
392399

@@ -582,10 +589,6 @@ int main(int argc, char *argv[]) {
582589
if (!in_container)
583590
sync_with_progress();
584591

585-
/* This is primarily useful when running systemd in a VM, as it provides the user running the VM with
586-
* a mechanism to pick up systemd's exit status in the VM. */
587-
(void) sd_notifyf(0, "EXIT_STATUS=%i", arg_exit_code);
588-
589592
if (streq(arg_verb, "exit")) {
590593
if (in_container) {
591594
log_info("Exiting container.");

0 commit comments

Comments
 (0)