bootman: Automatically determine if the target system is GPT or not

The primary difference between our "core" bootloaders and the upcoming GRUB2
support, is that in terms of legacy, syslinux is only used to support a GPT
disk.

As such our inspection of the root checks if one of the boot-grab methods
actually succeeded, and if so, enforce the GPT mask. This is because both
of the probe methods are GPT-specific, with the legacy method erroring out
in the absence of a proper PTUUID, and our UEFI method checking the XDG
bootloader protocol, before using /dev/disk/by-partuuid. This is only
supported on GPT.

This change unlocks the addition of a simplistic GRUB2 implementation because
it will have the LEGACY flags but not the GPT flags, thus the syslinux loader
will never be selected, as long as the GRUB loader is placed *first* in the
array. Likewise, the GRUB loader will never be able to be loaded for the
other configurations because it will never have the GPT flag set.

Signed-off-by: Ikey Doherty <michael.i.doherty@intel.com>
This commit is contained in:
Ikey Doherty
2017-03-26 11:15:28 -07:00
committed by William Douglas
parent c024ea3930
commit 6526a0446a
4 changed files with 14 additions and 12 deletions
+1 -8
View File
@@ -97,16 +97,9 @@ void boot_manager_free(BootManager *self)
static bool boot_manager_select_bootloader(BootManager *self)
{
int wanted_boot_mask = 0;
const BootLoader *selected = NULL;
int selected_boot_mask = 0;
/* Find legacy */
if (self->sysconfig->legacy) {
wanted_boot_mask |= BOOTLOADER_CAP_LEGACY;
} else {
wanted_boot_mask |= BOOTLOADER_CAP_UEFI;
}
int wanted_boot_mask = self->sysconfig->wanted_boot_mask;
/* Select a bootloader based on the capabilities */
for (size_t i = 0; i < ARRAY_SIZE(bootman_known_loaders); i++) {
+1 -1
View File
@@ -84,7 +84,7 @@ typedef struct SystemConfig {
char *prefix; /**<Prefix for all operations */
CbmDeviceProbe *root_device; /**<The physical root device */
char *boot_device; /**<The physical boot device */
bool legacy; /**<Legacy or UEFI */
int wanted_boot_mask; /**<The required bootloader mask */
} SystemConfig;
/**
+11 -2
View File
@@ -56,17 +56,21 @@ SystemConfig *cbm_inspect_root(const char *path)
return NULL;
}
c->prefix = realp;
c->wanted_boot_mask = 0;
/* Find legacy relative to root */
/* Find legacy relative to root, on GPT */
boot = get_legacy_boot_device(realp);
if (boot) {
c->boot_device = boot;
c->legacy = true;
c->wanted_boot_mask |= BOOTLOADER_CAP_LEGACY;
LOG_INFO("Discovered legacy boot device: %s", boot);
} else {
/* Discover UEFI boot */
c->boot_device = get_boot_device();
c->wanted_boot_mask |= BOOTLOADER_CAP_UEFI;
}
/* Our probe methods are GPT only. If we found one, it's definitely GPT */
if (c->boot_device) {
rel = realpath(c->boot_device, NULL);
if (!rel) {
@@ -78,7 +82,12 @@ SystemConfig *cbm_inspect_root(const char *path)
c->boot_device = rel;
LOG_INFO("Discovered boot device: %s", rel);
}
c->wanted_boot_mask |= BOOTLOADER_CAP_GPT;
} else {
/* Legacy boot, non-GPT */
c->wanted_boot_mask = BOOTLOADER_CAP_LEGACY;
}
c->root_device = cbm_probe_path(realp);
return c;
+1 -1
View File
@@ -59,7 +59,7 @@ bool boot_manager_update(BootManager *self)
/* TODO: decide how legacy device detection works */
/* For now legacy means /boot is on the / partition */
if (self->sysconfig->legacy) {
if ((self->sysconfig->wanted_boot_mask & BOOTLOADER_CAP_LEGACY) == BOOTLOADER_CAP_LEGACY) {
LOG_DEBUG("Skipping to legacy-native-install (no mount)");
goto perform;
}