Skip to content

Commit

Permalink
Fix different behaviour between usb and cd in efi (#135)
Browse files Browse the repository at this point in the history
* Use the efi image directly and set efi_boot_part

this supposedly increases compatibility when booting from usb

Mark the current El Torito boot image (see options -b and -e) in an actually invalid GPT as partition of type Basic Data. This works only with -isohybrid-mbr and has the same impact on the system area as -efi-boot-part. It cannot be combined with -efi-boot-part or -hfsplus.
The first three boot images which are marked by GPT will also show up as partition entries in MBR. The MBR partition of type 0xEF is what actually is used by EFI firmware for booting from USB stick. The MBR partition for PC-BIOS gets type 0x00 rather than 0x17 in this case. Often the further MBR entries are the ones which actually get used by EFI.

Signed-off-by: Itxaka <itxaka@kairos.io>

* Make it work for livecd and usb

Signed-off-by: Itxaka <itxaka@kairos.io>

* Review comments

Signed-off-by: Itxaka <itxaka@kairos.io>

* Apply suggestions from code review

Co-authored-by: Mauro Morales <mauro.morales@spectrocloud.com>

* Move dir creation to function

Signed-off-by: Itxaka <itxaka@kairos.io>

---------

Signed-off-by: Itxaka <itxaka@kairos.io>
Co-authored-by: Mauro Morales <mauro.morales@spectrocloud.com>
  • Loading branch information
Itxaka and mauromorales authored Dec 11, 2024
1 parent ea77e08 commit c0d7450
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 9 deletions.
5 changes: 2 additions & 3 deletions pkg/constants/constants.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import (
_ "embed"
"fmt"
"os"
"path/filepath"
)

// Eltorito image is basically a grub cdboot.img + grub core image
Expand Down Expand Up @@ -107,11 +106,11 @@ func GetXorrisoBooloaderArgs(root string) []string {
"-boot_image", "any", "platform_id=0x00",
"-boot_image", "any", "emul_type=no_emulation",
"-boot_image", "any", "load_size=2048",
"-append_partition", "2", "0xef", filepath.Join(root, IsoEFIPath),
"-boot_image", "any", "next",
"-boot_image", "any", "efi_path=--interval:appended_partition_2:all::",
"-boot_image", "any", "platform_id=0xef",
"-boot_image", "any", "emul_type=no_emulation",
"-boot_image", "any", "efi_path=" + IsoEFIPath, // Tell where the efi path is
"-boot_image", "any", "efi_boot_part=--efi-boot-image", // Tell where the efi path is for booting
}
return args
}
Expand Down
36 changes: 30 additions & 6 deletions pkg/ops/iso.go
Original file line number Diff line number Diff line change
Expand Up @@ -368,6 +368,7 @@ func (b BuildISOAction) createEFI(rootdir string, isoDir string) error {

// rootfs /efi dir
img := filepath.Join(isoDir, constants.IsoEFIPath)
// Temp dir is where we will build the EFI image from
temp, _ := utils.TempDir(b.cfg.Fs, "", "auroraboot-iso")
err = utils.MkdirAll(b.cfg.Fs, filepath.Join(temp, constants.EfiBootPath), constants.DirPerm)
if err != nil {
Expand All @@ -394,8 +395,16 @@ func (b BuildISOAction) createEFI(rootdir string, isoDir string) error {
// Its read from the root of the livecd, so we need to copy it into /EFI/BOOT/grub.cfg
// This is due to the hybrid bios/efi boot mode of the livecd
// the uefi.img is loaded into memory and run, but grub only sees the livecd root
err = b.cfg.Fs.WriteFile(filepath.Join(isoDir, constants.EfiBootPath, constants.GrubCfg), []byte(constants.GrubEfiCfg), constants.FilePerm)
if err != nil {
// WARNING: If we load the image into an usb stick, grub will not use the livecd root as the grub root, so it cannot find the grub.cfg
// So we copy in 2 places, into the livecd and into the img

// This is used when booting from usb
if err = b.writeDefaultGrubEfiCfg(temp); err != nil {
b.cfg.Logger.Errorf("Failed writing grub.cfg: %v", err)
return err
}
// This is used when booting from cdrom
if err = b.writeDefaultGrubEfiCfg(isoDir); err != nil {
b.cfg.Logger.Errorf("Failed writing grub.cfg: %v", err)
return err
}
Expand All @@ -415,13 +424,12 @@ func (b BuildISOAction) createEFI(rootdir string, isoDir string) error {
b.cfg.Logger.Infof("Detected Flavor: %s", flavor)
if strings.Contains(strings.ToLower(flavor), "ubuntu") {
b.cfg.Logger.Infof("Ubuntu based ISO detected, copying grub.cfg to /EFI/ubuntu/grub.cfg")
err = utils.MkdirAll(b.cfg.Fs, filepath.Join(isoDir, "EFI/ubuntu/"), constants.DirPerm)
if err != nil {

if err = b.writeUbuntuGrubEfiCfg(temp); err != nil {
b.cfg.Logger.Errorf("Failed writing grub.cfg: %v", err)
return err
}
err = b.cfg.Fs.WriteFile(filepath.Join(isoDir, "EFI/ubuntu/", constants.GrubCfg), []byte(constants.GrubEfiCfg), constants.FilePerm)
if err != nil {
if err = b.writeUbuntuGrubEfiCfg(isoDir); err != nil {
b.cfg.Logger.Errorf("Failed writing grub.cfg: %v", err)
return err
}
Expand Down Expand Up @@ -465,6 +473,22 @@ func (b BuildISOAction) createEFI(rootdir string, isoDir string) error {
return nil
}

// writeDefaultGrubEfiCfg writes the default grub.cfg for the EFI image in teh given path
func (b *BuildISOAction) writeDefaultGrubEfiCfg(path string) error {
calculatedPath := filepath.Join(path, constants.EfiBootPath, constants.GrubCfg)
return b.cfg.Fs.WriteFile(calculatedPath, []byte(constants.GrubEfiCfg), constants.FilePerm)
}

func (b *BuildISOAction) writeUbuntuGrubEfiCfg(path string) error {
calculatedPath := filepath.Join(path, "EFI/ubuntu/", constants.GrubCfg)
err := utils.MkdirAll(b.cfg.Fs, calculatedPath, constants.DirPerm)
if err != nil {
b.cfg.Logger.Errorf("Failed writing grub.cfg: %v", err)
return err
}
return b.cfg.Fs.WriteFile(calculatedPath, []byte(constants.GrubEfiCfg), constants.FilePerm)
}

// copyShim copies the shim files into the EFI partition
// tempdir is the temp dir where the EFI image is generated from
// rootdir is the rootfs where the shim files are searched for
Expand Down

0 comments on commit c0d7450

Please sign in to comment.