Hi Richard, This is a more comprehensive description of the problem, where I respond to the specific issue and questions that you brought up during the discussion last week. I also cover the proposed solution towards the end. Kindly bear with the somewhat longish one - *[Comment 1] - Specific behaviors of the GRUB bootloader when encountering "Linux 16" versus "Linux EFI" directives.* - linux16 - Directive in GRUB boot loader to load the Linux Kernel image. It is documented in the GNU GRUB documentation - linux16 <https://doc.guix.gnu.org/grub/latest/en/grub.html#linux16> - The linux16 command forces GRUB load Linux Kernel image by using legacy *16-bit real-mode boot protocol*. - GRUB hands control to the kernel *while the CPU is still in 16-bit Real Mode*. - This allows the kernel's real-mode setup code to perform early hardware initialization using BIOS services (e.g., querying video modes, memory map)" - The Linux Kernel switches itself into 32-bit protected mode. - initrd16 loads the initramfs and is paired with linux16 - linuxefi - downstream GRUB2 bootloader directives specific to RHEL 7 for UEFI systems. Documented in RHEL 7 System Administrator Guide <https://docs.redhat.com/en/documentation/red_hat_enterprise_linux/7/html/system_administrators_guide/part-kernel_customization_with_bootloader> - Directive specific to RHEL 7. These directives are deprecated in RHEL 8 upwards which use standard GRUB directives linux, initrd instead and these work uniformly across BIOS or UEFI systems. - linuxefi and initrdefi directives use UEFI boot services to load the Linux Kernel image and initramfs respectively. - Based on the boot mode of the system - These GRUB configuration files are created using scripts in /etc/grub.d/ - primary script which generates the kernel image, initramfs boot loader commands is /etc/grub.d/10_linux. - RHEL 7.9 VM in BIOS Mode - GRUB reads the file /boot/grub2/grub.cfg which has the directives {linux16, initrd16} [root@localhost ~]# cat /boot/grub2/grub.cfg | egrep "linux16|initrd16" *linux16* /vmlinuz-3.10.0-1160.el7.x86_64 root=UUID=b635e330-0173-4866-9e5e-693086760507 ro crashkernel=auto rhgb quiet LANG=en_US.UTF-8 *initrd16* /initramfs-3.10.0-1160.el7.x86_64.img *linux16* /vmlinuz-0-rescue-bb246b817b814a44b5e960404fdc7ae3 root=UUID=b635e330-0173-4866 -9e5e-693086760507 ro crashkernel=auto rhgb quiet *initrd16* /initramfs-0-rescue-bb246b817b814a44b5e960404fdc7ae3.img - RHEL 7.9 VM in UEFI Mode - GRUB reads the file /boot/efi/EFI/redhat/grub.cfg which has the directives {linux16, initrd16} [root@localhost ~]# cat /boot/efi/EFI/redhat/grub.cfg | egrep "linuxefi|initrdefi" *linuxefi* /vmlinuz-3.10.0-1160.el7.x86_64 root=/dev/mapper/rhel-root ro crashkernel=auto rd.lvm.lv=rhel/root rd.lvm.lv=rhel/swap rhgb quiet *initrdefi* /initramfs-3.10.0-1160.el7.x86_64.img *linuxefi* /vmlinuz-0-rescue-6e4e30972e924630b169d78059b932d2 root=/dev/mapper/rhel-root ro crashkernel=auto rd.lvm.lv=rhel/root rd.lvm.lv=rhel/swap rhgb quiet *initrdefi* /initramfs-0-rescue-6e4e30972e924630b169d78059b932d2.img - Code snippet from /etc/grub.d/10_linux for RHEL9 and RHEL7. The root device UUID passed to the kernel (e.g., root=UUID=...) is dynamically queried and formatted by helper routines in /usr/share/grub/grub-mkconfig_lib using grub-probe . - Code snippet from */etc/grub.d/10_linux in RHEL9* if [ -d /sys/firmware/efi ]; then bootefi_device="`${grub_probe} --target=device /boot/efi/`" prepare_grub_to_access_device_with_variable boot ${bootefi_device} else boot_device="`${grub_probe} --target=device /boot/`" prepare_grub_to_access_device_with_variable boot ${boot_device} fi - Code snippet from */etc/grub.d/10_linux in RHEL7* if [ -d /sys/firmware/efi ]; then sed "s/^/$submenu_indentation/" << EOF ${linuxefi} ${rel_dirname}/${basename} root=${linux_root_device_thisversion} ro ${args} EOF else sed "s/^/$submenu_indentation/" << EOF linux${sixteenbit} ${rel_dirname}/${basename} root=${linux_root_device_thisversion} ro ${args} EOF fi - *[Comment 2] Confirming that the virtual machine Linux file format is fully compatible with the new directive* - Based on the analysis done for the previous comment, we can safely conclude that this problem is very specific to RHEL 7 only. Further, the problem occurs when following conditions are met - Source VM must be in UEFI boot mode - In the /etc/fstab, the /boot and /boot/efi partitions must be identified by the corresponding /dev/sd* files instead of the UUIDs (default) generated during FS creation. - The second condition forces virt-v2v conversion to configure GRUB. - As the grub configuration executes in context of libguestfs appliance (BIOS mode), it is generated with linux16, initrd16 whereas the VM is configured to boot in UEFI. - The VM powers up with UEFI firmware, but the linux16 directive switches the CPU into 16-bit real mode and look for BIOS services (/boot/grub2/i386-pc) which are absent. - *[Comment 3] Regarding the potential modification of file system table entries and disk device naming conventions, Richard Jones insisted that any statements regarding potential disk access problems must be accompanied by a detailed explanation of the "why" and "what" behind those risks* - The kernel device discovery (names /dev/sd*) is non-deterministic as it is based on order of driver initialization at the boot time. The order variation is due to asynchronous driver probe, kernel update or VM configuration changes. - By "hard-coding" the device names inside /etc/fstab, there could be a possibility of an unintended device being mounted onto an incorrect mount point, thus causing the system to fail or corrupt. - UUIDs (written into FS) are more reliable - where order of initialization would not matter making it more deterministic. - *The proposed solution* - Convert the references to /dev/sd* files to corresponding FS UUIDs *[Implemented and tested]* - Following change applicable only if OS is RHEL 7 and Boot mode is UEFI - Replace {linux16, initrd16} with {linuxefi, initrdefi} *[Work in progress to change from using sed to using APIs]* Thanks Srihari