Bug 1924587

Summary: RFE: Harden the shutdown phase to avoid dropping into the emergency prompt
Product: Red Hat Enterprise Linux 8 Reporter: Renaud Métrich <rmetrich>
Component: dracutAssignee: Pavel Valena <pvalena>
Status: CLOSED ERRATA QA Contact: Frantisek Sumsal <fsumsal>
Severity: high Docs Contact:
Priority: high    
Version: 8.3CC: cbesson, chuhu, dracut-maint-list, dtardon, fkrska, fsumsal, lijgopin, md, myamazak, pskhedekar, pvalena
Target Milestone: rcKeywords: FutureFeature, Reproducer, Triaged
Target Release: 8.0   
Hardware: All   
OS: Linux   
Whiteboard:
Fixed In Version: dracut-049-209.git20220815.el8 Doc Type: If docs needed, set a value
Doc Text:
Story Points: ---
Clone Of: Environment:
Last Closed: 2022-11-08 10:48:46 UTC Type: Bug
Regression: --- Mount Type: ---
Documentation: --- CRM:
Verified Versions: Category: ---
oVirt Team: --- RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: --- Target Upstream Version:
Embargoed:

Description Renaud Métrich 2021-02-03 09:18:28 UTC
Description of problem:

Currently the shutdown phase executes dracut-shutdown.service which unpacks the initramfs into /run/initramfs. Then plymouth-switch-root-initramfs.service executes and switches root to /run/initramfs and final shutdown operations execute.

Sometimes, the initramfs couldn't be unpacked properly, which leads to dropping into the following prompt (executed by "shutdown" binary once switch-root happened):
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
/shutdown: line 115: reboot: command not found
[  145.951127] dracut Warning: reboot failed!
dracut Warning: reboot failed!


[  145.953007] dracut Warning: 
dracut Warning: 


Generating "/run/initramfs/rdsosreport.txt"
You might want to save "/run/initramfs/rdsosreport.txt" to a USB stick or /boot
after mounting them and attach it to a bug report.

To get more debug information in the report,
reboot with "rd.debug" added to the kernel command line.

Dropping to debug shell.

shutdown:/# 
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

So far we got some customers hitting this or something similar (e.g. /usr/bin/multipath: command no found) in different scenarios:

1. Upon installation with a virtual DVD mounted on the iLO with low bandwidth between the ISO image and the iLO

  In this scenario, the issue is due to low bandwidth: dracut-shutdown has only 90 seconds to complete and this may not be enough, causing systemd to kill the cpio command executing and having missing binaries in /run/initramfs, causing the issue after switching root

2. Upon restarting VMWare guests: it's unclear which condition effectively happens here but it's very likely related to unpacking being killed as well on 90 seconds timeout


Version-Release number of selected component (if applicable):

dracut-049-95.git20200804.el8.x86_64 / plymouth-0.9.4-7.20200615git1e36e30.el8.x86_64


How reproducible:

ALWAYS with a "slow" DVD during installation
ALWAYS using the hack below

Steps to Reproduce:
1. Edit /usr/lib/dracut/dracut-initramfs-restore to delete "reboot" binary after extraction happens

Replace "exit 0" at the end of the script by this:
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
rm /run/initramfs/usr/sbin/reboot
exit 1
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

This mimics a timeout while cpio is running (binaries in /usr/sbin are the last ones being extracted).

2. Reboot the system

Actual results:

Emergency prompt

Expected results:

Automatic reboot if possible

Comment 1 Renaud Métrich 2021-02-03 09:27:03 UTC
Hardening can be easily implemented as shown  below:

1. dracut-shutdown failure needs to be detected (exit 1 is not sufficient) and cleanup must be really done, specially on timeout

  This can be achieve by a new "dracut-shutdown-onfailure.service" unit that will cleanup some extracted files (/run/initramfs/shutdown is sufficient, as already done when cpio fails in the script):

  dracut-shutdown-onfailure.service:
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
  [Unit]
  Description=Service executing upon dracut-shutdown failure to perform cleanup
  DefaultDependencies=no
  
  [Service]
  Type=oneshot
  ExecStart=/bin/sh -c '/bin/rm /run/initramfs/shutdown 2>/dev/null || true'
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

  dracut-shutdown.service:
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
  [Unit]
  OnFailure=dracut-shutdown-onfailure.service
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

2. plymouth-switch-root-initramfs.service should have a After dependency on dracut-shutdown-onfailure.service to check for the new condition on "shutdown" script

  plymouth-switch-root-initramfs.service:
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
  [Unit]
  After=dracut-shutdown-onfailure.service
  ConditionPathExists=/run/initramfs/shutdown
  -------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

  The After=dracut-shutdown-onfailure.service is required to make sure the cleanup of the initramfs extraction is performed before attempting to switch root.

With this in place, plymouth-switch-root-initramfs will *not* execute anymore if critical files in /run/initramfs are missing, indicating the initramfs extraction failed somehow.

Comment 2 David Tardon 2021-02-04 15:48:40 UTC
*** Bug 1631740 has been marked as a duplicate of this bug. ***

Comment 4 Renaud Métrich 2021-05-18 12:32:26 UTC
See also BZ #1961659.

Comment 5 Renaud Métrich 2022-01-13 15:57:47 UTC
See also BZ #2023665.

Comment 6 David Tardon 2022-07-14 08:52:23 UTC
*** Bug 1961659 has been marked as a duplicate of this bug. ***

Comment 10 errata-xmlrpc 2022-11-08 10:48:46 UTC
Since the problem described in this bug report should be
resolved in a recent advisory, it has been closed with a
resolution of ERRATA.

For information on the advisory (dracut bug fix and enhancement update), and where to find the updated
files, follow the link below.

If the solution does not work for you, open a new bug report.

https://access.redhat.com/errata/RHBA-2022:7725

Comment 12 Maksym Domin 2024-05-09 16:14:40 UTC
(In reply to Renaud Métrich from comment #1)
> Hardening can be easily implemented as shown  below:
> 
> 1. dracut-shutdown failure needs to be detected (exit 1 is not sufficient)
> and cleanup must be really done, specially on timeout
> 
>   This can be achieve by a new "dracut-shutdown-onfailure.service" unit that
> will cleanup some extracted files (/run/initramfs/shutdown is sufficient, as
> already done when cpio fails in the script):
> 
>   dracut-shutdown-onfailure.service:
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
>   [Unit]
>   Description=Service executing upon dracut-shutdown failure to perform
> cleanup
>   DefaultDependencies=no
>   
>   [Service]
>   Type=oneshot
>   ExecStart=/bin/sh -c '/bin/rm /run/initramfs/shutdown 2>/dev/null || true'
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
> 
>   dracut-shutdown.service:
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
>   [Unit]
>   OnFailure=dracut-shutdown-onfailure.service
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
> 
> 2. plymouth-switch-root-initramfs.service should have a After dependency on
> dracut-shutdown-onfailure.service to check for the new condition on
> "shutdown" script
> 
>   plymouth-switch-root-initramfs.service:
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
>   [Unit]
>   After=dracut-shutdown-onfailure.service
>   ConditionPathExists=/run/initramfs/shutdown
>   -------- 8< ---------------- 8< ---------------- 8< ---------------- 8<
> --------
> 
>   The After=dracut-shutdown-onfailure.service is required to make sure the
> cleanup of the initramfs extraction is performed before attempting to switch
> root.
> 
> With this in place, plymouth-switch-root-initramfs will *not* execute
> anymore if critical files in /run/initramfs are missing, indicating the
> initramfs extraction failed somehow.

Is this a fix for the issue with /shutdown: line 162: reboot: command not found? I have the same symptoms after upgrade of Fedora 39 to 40.