diff --git a/external-layers/meta-efibootguard b/external-layers/meta-efibootguard index c65743e..e3581b1 160000 --- a/external-layers/meta-efibootguard +++ b/external-layers/meta-efibootguard @@ -1 +1 @@ -Subproject commit c65743e5dcaecce38383b23782c063bdbc73c404 +Subproject commit e3581b11d30d91d0363acb48a6aee47043b7e0bc diff --git a/layers/meta-belden-coreos-bsp/conf/machine/include/coreos-generic-features/partitions.inc b/layers/meta-belden-coreos-bsp/conf/machine/include/coreos-generic-features/partitions.inc index e062876..d2aa1a4 100644 --- a/layers/meta-belden-coreos-bsp/conf/machine/include/coreos-generic-features/partitions.inc +++ b/layers/meta-belden-coreos-bsp/conf/machine/include/coreos-generic-features/partitions.inc @@ -2,8 +2,8 @@ # Variable used in WKS file WKS_PART_EFI ??= 'part --source efibootguard-efi --label efi --part-type=EF00' -WKS_PART_EFIBOOTGUARD_A ??= 'part --source efibootguard-boot --label ebg0 --part-type=0700 --sourceparams "watchdog=${EFIBOOTGUARD_TIMEOUT},revision=2,kernel=kernel0-${MACHINE}.efi;KERNEL.EFI"' -WKS_PART_EFIBOOTGUARD_B ??= 'part --source efibootguard-boot --label ebg1 --part-type=0700 --sourceparams "watchdog=${EFIBOOTGUARD_TIMEOUT},revision=1,kernel=kernel1-${MACHINE}.efi;KERNEL.EFI"' +WKS_PART_EFIBOOTGUARD_A ??= 'part --source efibootguard-boot --label ebg0 --part-type=0700 --sourceparams "args=coreos.root=rootfs0,watchdog=${EFIBOOTGUARD_TIMEOUT},revision=2,kernel=kernel-${MACHINE}.efi;KERNEL.EFI"' +WKS_PART_EFIBOOTGUARD_B ??= 'part --source efibootguard-boot --label ebg1 --part-type=0700 --sourceparams "args=coreos.root=rootfs1,watchdog=${EFIBOOTGUARD_TIMEOUT},revision=1,kernel=kernel-${MACHINE}.efi;KERNEL.EFI"' WKS_PART_ROOT_A ??= 'part / --source rootfs --fstype=ext4 --label rootfs0' WKS_PART_ROOT_B ??= 'part --fstype=ext4 --label rootfs1' WKS_PART_ROOT_SIZE ??= '2G' diff --git a/layers/meta-belden-coreos/classes/coreos-image-ci.bbclass b/layers/meta-belden-coreos/classes/coreos-image-ci.bbclass index 7e073e8..890cbd9 100644 --- a/layers/meta-belden-coreos/classes/coreos-image-ci.bbclass +++ b/layers/meta-belden-coreos/classes/coreos-image-ci.bbclass @@ -46,8 +46,7 @@ def get_coreos_ci_artifacts(d): artifacts.append(kernel_imagetype + '-' + machine + kernel_image_bin_ext) if d.getVar('COREOS_IMAGE_GENERATE_UKI') == '1': - artifacts.append(d.getVar('COREOS_KERNEL0_FILENAME')) - artifacts.append(d.getVar('COREOS_KERNEL1_FILENAME')) + artifacts.append(d.getVar('COREOS_KERNEL_FILENAME')) # Bootloaders # ========================================================================== diff --git a/layers/meta-belden-coreos/classes/coreos-image-swupdate.bbclass b/layers/meta-belden-coreos/classes/coreos-image-swupdate.bbclass index 56cfd4d..11dd9c6 100644 --- a/layers/meta-belden-coreos/classes/coreos-image-swupdate.bbclass +++ b/layers/meta-belden-coreos/classes/coreos-image-swupdate.bbclass @@ -16,21 +16,19 @@ python () { inherit swupdate-image # Ensure than variable used in the sw-description files are watched for change -do_swuimage[vardeps] += "COREOS_KERNEL0_FILENAME COREOS_KERNEL1_FILENAME EFIBOOTGUARD_TIMEOUT EFIDIR EFI_BOOT_IMAGE COREOS_EFIBOOTGUARD_FILENAME" +do_swuimage[vardeps] += "COREOS_KERNEL_FILENAME EFIBOOTGUARD_TIMEOUT EFIDIR EFI_BOOT_IMAGE COREOS_EFIBOOTGUARD_FILENAME" do_swuimage[deptask] += "do_bundle_uki" COREOS_EFIBOOTGUARD_NAME ?= "efibootguard${EFI_ARCH}" COREOS_EFIBOOTGUARD_EXT ?= ".efi" COREOS_EFIBOOTGUARD_FILENAME = "${COREOS_EFIBOOTGUARD_NAME}${COREOS_EFIBOOTGUARD_EXT}" -SWUPDATE_IMAGES += "${COREOS_KERNEL0_NAME} ${COREOS_KERNEL1_NAME} ${COREOS_EFIBOOTGUARD_NAME}" +SWUPDATE_IMAGES += "${COREOS_KERNEL_NAME} ${COREOS_EFIBOOTGUARD_NAME}" python () { - kernel0 = d.getVar('COREOS_KERNEL0_NAME') - kernel1 = d.getVar('COREOS_KERNEL1_NAME') + kernel = d.getVar('COREOS_KERNEL_NAME') kernelext = d.getVar('COREOS_KERNEL_EXT') - d.setVarFlag("SWUPDATE_IMAGES_FSTYPES", kernel0, kernelext) - d.setVarFlag("SWUPDATE_IMAGES_FSTYPES", kernel1, kernelext) + d.setVarFlag("SWUPDATE_IMAGES_FSTYPES", kernel, kernelext) efibootguard = d.getVar('COREOS_EFIBOOTGUARD_NAME') efibootguardext = d.getVar('COREOS_EFIBOOTGUARD_EXT') diff --git a/layers/meta-belden-coreos/classes/coreos-image-uki.bbclass b/layers/meta-belden-coreos/classes/coreos-image-uki.bbclass index 59646d4..4867fd2 100644 --- a/layers/meta-belden-coreos/classes/coreos-image-uki.bbclass +++ b/layers/meta-belden-coreos/classes/coreos-image-uki.bbclass @@ -10,20 +10,17 @@ inherit coreos-efi-sbsign # ============================================================================== COREOS_KERNEL_EXT ??= ".efi" -COREOS_KERNEL0_NAME ??= "kernel0-${MACHINE}" -COREOS_KERNEL1_NAME ??= "kernel1-${MACHINE}" -COREOS_KERNEL0_FILENAME ??= "${COREOS_KERNEL0_NAME}${COREOS_KERNEL_EXT}" -COREOS_KERNEL0 ??= "${DEPLOY_DIR_IMAGE}/${COREOS_KERNEL0_FILENAME}" -COREOS_KERNEL1_FILENAME ??= "${COREOS_KERNEL1_NAME}${COREOS_KERNEL_EXT}" -COREOS_KERNEL1 ??= "${DEPLOY_DIR_IMAGE}/${COREOS_KERNEL1_FILENAME}" +COREOS_KERNEL_NAME ??= "kernel-${MACHINE}" +COREOS_KERNEL_FILENAME ??= "${COREOS_KERNEL_NAME}${COREOS_KERNEL_EXT}" +COREOS_KERNEL ??= "${DEPLOY_DIR_IMAGE}/${COREOS_KERNEL_FILENAME}" # Kernel command line # ============================================================================== -COREOS_ROOTFS0_ROOT ??= "PARTLABEL=rootfs0" -COREOS_ROOTFS1_ROOT ??= "PARTLABEL=rootfs1" -COREOS_KERNEL0_CMDLINE ??= "root=${COREOS_ROOTFS0_ROOT} ${APPEND} rootwait" -COREOS_KERNEL1_CMDLINE ??= "root=${COREOS_ROOTFS1_ROOT} ${APPEND} rootwait" +# AUTOLABEL will be replaced by the right PARTLABEL (rootfs0 or rootfs1) at +# runtime in the efibootguard UKI stub +COREOS_ROOTFS_ROOT ??= "PARTLABEL=AUTOLABEL" +COREOS_KERNEL_CMDLINE ??= "root=${COREOS_ROOTFS_ROOT} ${APPEND} rootwait" COREOS_UKI_PART_KERNEL_FILENAME ??= "${KERNEL_IMAGETYPE}-${MACHINE}${KERNEL_IMAGE_BIN_EXT}" COREOS_UKI_PART_KERNEL ??= "${DEPLOY_DIR_IMAGE}/${COREOS_UKI_PART_KERNEL_FILENAME}" @@ -48,8 +45,7 @@ do_image_uki() { echo "kernel: ${COREOS_UKI_PART_KERNEL_FILENAME}" echo "dtb: ${DTB_PARAMS}" - echo "cmdline0: ${COREOS_KERNEL0_CMDLINE}" - echo "cmdline1: ${COREOS_KERNEL1_CMDLINE}" + echo "cmdline: ${COREOS_KERNEL_CMDLINE}" echo "initramfs: ${COREOS_UKI_PART_INITRAMFS}" if [ ! -z "${COREOS_UKI_PART_INITRAMFS}" ]; then @@ -61,19 +57,11 @@ do_image_uki() { bg_gen_unified_kernel \ "${COREOS_UKI_PART_STUB}" \ "${COREOS_UKI_PART_KERNEL}" \ - "${COREOS_KERNEL0}" \ - --cmdline "${COREOS_KERNEL0_CMDLINE}" \ + "${COREOS_KERNEL}" \ + --cmdline "${COREOS_KERNEL_CMDLINE}" \ ${DTB_PARAMS} - bg_gen_unified_kernel \ - "${COREOS_UKI_PART_STUB}" \ - "${COREOS_UKI_PART_KERNEL}" \ - "${COREOS_KERNEL1}" \ - --cmdline "${COREOS_KERNEL1_CMDLINE}" \ - ${DTB_PARAMS} - - coreos_efi_secureboot_sign_app "${deployDir}/${COREOS_KERNEL0_FILENAME}" - coreos_efi_secureboot_sign_app "${deployDir}/${COREOS_KERNEL1_FILENAME}" + coreos_efi_secureboot_sign_app "${deployDir}/${COREOS_KERNEL_FILENAME}" } do_image_uki[depends] += "virtual/kernel:do_deploy efibootguard-native:do_populate_sysroot efibootguard:do_populate_sysroot" diff --git a/layers/meta-belden-coreos/files/sw-description b/layers/meta-belden-coreos/files/sw-description index 0603369..cbe8f14 100644 --- a/layers/meta-belden-coreos/files/sw-description +++ b/layers/meta-belden-coreos/files/sw-description @@ -23,11 +23,11 @@ software = files: ( { - filename = "@@COREOS_KERNEL0_FILENAME@@"; + filename = "@@COREOS_KERNEL_FILENAME@@"; path = "/KERNEL.EFI"; device = "/dev/disk/by-partlabel/ebg0"; filesystem = "vfat"; - sha256 = "$swupdate_get_sha256(@@COREOS_KERNEL0_FILENAME@@)"; + sha256 = "$swupdate_get_sha256(@@COREOS_KERNEL_FILENAME@@)"; }, { filename = "@@COREOS_EFIBOOTGUARD_FILENAME@@"; @@ -44,7 +44,7 @@ software = bootenv: ( { name = "kernelparams"; - value = ""; + value = "coreos.root=rootfs0"; }, { name = "watchdog_timeout_sec"; @@ -80,11 +80,11 @@ software = files: ( { - filename = "@@COREOS_KERNEL1_FILENAME@@"; + filename = "@@COREOS_KERNEL_FILENAME@@"; path = "/KERNEL.EFI"; device = "/dev/disk/by-partlabel/ebg1"; filesystem = "vfat"; - sha256 = "$swupdate_get_sha256(@@COREOS_KERNEL1_FILENAME@@)"; + sha256 = "$swupdate_get_sha256(@@COREOS_KERNEL_FILENAME@@)"; }, { filename = "@@COREOS_EFIBOOTGUARD_FILENAME@@"; @@ -100,7 +100,7 @@ software = bootenv: ( { name = "kernelparams"; - value = ""; + value = "coreos.root=rootfs1"; }, { name = "watchdog_timeout_sec"; diff --git a/layers/meta-belden-coreos/lib/devtool/coreos-efibootguard.py b/layers/meta-belden-coreos/lib/devtool/coreos-efibootguard.py index 91e6c88..5199e90 100644 --- a/layers/meta-belden-coreos/lib/devtool/coreos-efibootguard.py +++ b/layers/meta-belden-coreos/lib/devtool/coreos-efibootguard.py @@ -272,40 +272,24 @@ def efibootguard_generate_uki(args, config, basepath, workspace): keydir = os.path.relpath(rd.getVar("COREOS_EFI_SECUREBOOT_KEYDIR")) - uki0 = UKIGeneratorArgs( + uki = UKIGeneratorArgs( kernel=kernel, - output=os.path.relpath(rd.getVar("COREOS_KERNEL0")), - cmdline=rd.getVar("COREOS_KERNEL0_CMDLINE"), + output=os.path.relpath(rd.getVar("COREOS_KERNEL")), + cmdline=rd.getVar("COREOS_KERNEL_CMDLINE"), dtb=dtb, stub=stub, - root=rd.getVar("COREOS_ROOTFS0_ROOT"), - build_binary=build_binary, - keydir=keydir, - ) - uki1 = UKIGeneratorArgs( - kernel=kernel, - output=os.path.relpath(rd.getVar("COREOS_KERNEL1")), - cmdline=rd.getVar("COREOS_KERNEL1_CMDLINE"), - dtb=dtb, - stub=stub, - root=rd.getVar("COREOS_ROOTFS1_ROOT"), + root=rd.getVar("COREOS_ROOTFS_ROOT"), build_binary=build_binary, keydir=keydir, ) print(f"Applying passed parameters...") - uki0.process_args(args) - uki1.process_args(args) + uki.process_args(args) - print(f"KERNEL0 image will be generated with the following settings:") - printi(f"{uki0}", 1) - print() - print(f"KERNEL1 image will be generated with the following settings:") - printi(f"{uki1}", 1) + print(f"KERNEL image will be generated with the following settings:") + printi(f"{uki}", 1) print() print(f"Generating the files...") - r = uki0.build_and_sign() - r += uki1.build_and_sign() + return uki0.build_and_sign() - return r diff --git a/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard/0001-coreos-add-a-coreos-specific-rootfs-switch-to-the-UK.patch b/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard/0001-coreos-add-a-coreos-specific-rootfs-switch-to-the-UK.patch new file mode 100644 index 0000000..736ef25 --- /dev/null +++ b/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard/0001-coreos-add-a-coreos-specific-rootfs-switch-to-the-UK.patch @@ -0,0 +1,93 @@ +From 2e8b73826c6ecaf5168002a18282ba7e4ac95e76 Mon Sep 17 00:00:00 2001 +From: Samuel Dolt +Date: Mon, 12 Jun 2023 16:29:49 +0200 +Subject: [PATCH] coreos: add a coreos specific rootfs switch to the UKI stub + +The unified kernel stub can now replace the substring "AUTOLABEL" +in the built-in kernel command line by either rootfs0 and rootfs1 +by looking the LoadOption string passed by ther firmware: +- LoadOptions contain "coreos.root=rootfs0", all occurences of + "AUTOLABEL" are replaced by "rootfs0" +- LoadOptions contain "coreos.root=rootfs1", all occurences of + "AUTOLABEL" are replaced by "rootfs1". +- LoadOptions is empty, the kernel command line will be used as is. + +In all other case, the stub will exist without booting the kernel +with a INVALID PARAMETER error. +--- + kernel-stub/main.c | 55 +++++++++++++++++++++++++++++++++++++++++----- + 1 file changed, 50 insertions(+), 5 deletions(-) + +diff --git a/kernel-stub/main.c b/kernel-stub/main.c +index c0be1f6..6f456d3 100644 +--- a/kernel-stub/main.c ++++ b/kernel-stub/main.c +@@ -128,11 +128,6 @@ EFI_STATUS efi_main(EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *system_table) + error_exit(L"Error getting LoadedImageProtocol", status); + } + +- /* consider zero-termination for string length */ +- if (stub_image->LoadOptionsSize > sizeof(CHAR16)) { +- info(L"WARNING: Passed command line options ignored, only built-in used"); +- } +- + pe_header = get_pe_header(stub_image->ImageBase); + for (n = 0, section = get_sections(pe_header); + n < pe_header->Coff.NumberOfSections; +@@ -161,6 +156,56 @@ EFI_STATUS efi_main(EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *system_table) + kernel_image.LoadOptions = (UINT8 *) stub_image->ImageBase + + cmdline_section->VirtualAddress; + kernel_image.LoadOptionsSize = cmdline_section->VirtualSize; ++ ++ /* CoreOS utilize the option passed from efibootguard to customize the kernel ++ * command line. ++ * ++ * Allowed option are: ++ * 'coreos.root=rootfs0' => replace "AUTOLABEL" with "rootfs0 " in place in the kernel CLI ++ * 'coreos.root=rootfs1' => replace "AUTOLABEL" with "rootfs1 " in place in the kernel CLI ++ * '' => no option passed ++ * ++ * Using another option string will return without booting the kernel ++ * ++ * hint: LoadOptions is a null-terminated wide string ++ * hint: sizeof return the number of byte. StrLen the number of characters ++ */ ++ if (stub_image->LoadOptionsSize > sizeof(CHAR16)) { ++ ++ // !!! symbol and rootfs must have the same length !!! ++ const CHAR16 symbol[] = L"AUTOLABEL"; ++ CHAR16 rootfs[] = L"rootfsX "; ++ ++ if (StrnCmp(L"coreos.root=rootfs0", stub_image->LoadOptions, stub_image->LoadOptionsSize) == 0) { ++ rootfs[6] = L'0'; ++ } else if (StrnCmp(L"coreos.root=rootfs1", stub_image->LoadOptions, stub_image->LoadOptionsSize) == 0) { ++ rootfs[6] = L'1'; ++ } else { ++ error_exit(L"LoadOptions is not valid", EFI_INVALID_PARAMETER); ++ } ++ ++ /* Replace symbol by rootfs (AUTOLABEL by either rootfs0 or rootfs1) */ ++ CHAR16 * str = kernel_image.LoadOptions; ++ UINTN len = kernel_image.LoadOptionsSize; ++ while (*str && len) { ++ ++ /* Ensure that the string still contains enough char for the symbol */ ++ if(len < sizeof(symbol)) { ++ break; ++ } ++ ++ if(StrnCmp(str, &symbol, StrLen(symbol)) == 0) { ++ /* Replace symbol by rootfs, works because symbole and rootfs has the same length */ ++ StrnCpy(str, rootfs, StrLen(rootfs)); ++ } ++ ++ str += 1; ++ len -= sizeof(CHAR16); ++ } ++ ++ } ++ ++ Print(L"Unified kernel stub: Kernel Options: %s\n", kernel_image.LoadOptions); + } + + if (initrd_section) { diff --git a/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard_%.bbappend b/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard_%.bbappend new file mode 100644 index 0000000..682574a --- /dev/null +++ b/layers/meta-belden-coreos/recipes-bsp/efibootguard/efibootguard_%.bbappend @@ -0,0 +1,4 @@ +FILESEXTRAPATHS:prepend := "${THISDIR}/${PN}:" + +SRC_URI += "file://0001-coreos-add-a-coreos-specific-rootfs-switch-to-the-UK.patch" + diff --git a/layers/meta-belden-coreos/recipes-core/images/coreos-image-installer.bb b/layers/meta-belden-coreos/recipes-core/images/coreos-image-installer.bb index f5c4b5c..9db6cc3 100644 --- a/layers/meta-belden-coreos/recipes-core/images/coreos-image-installer.bb +++ b/layers/meta-belden-coreos/recipes-core/images/coreos-image-installer.bb @@ -17,7 +17,7 @@ IMAGE_FSTYPES = "cpio.gz" COREOS_INSTALLER_WKS_FILE ??= "" WKS_FILE = "${COREOS_INSTALLER_WKS_FILE}" IMAGE_FSTYPES += "${@'wic.xz wic.bmap' if d.getVar('COREOS_INSTALLER_WKS_FILE') else ''}" -IMAGE_BOOT_FILES = "${COREOS_KERNEL0_FILENAME};EFI/BOOT/${EFI_BOOT_IMAGE}" +IMAGE_BOOT_FILES = "${COREOS_KERNEL_FILENAME};EFI/BOOT/${EFI_BOOT_IMAGE}" COREOS_IMAGE_GENERATE_UKI = "1" @@ -30,13 +30,10 @@ COREOS_IMAGE_GENERATE_INSTALLER = "0" COREOS_UKI_PART_INITRAMFS = "${IMGDEPLOYDIR}/${IMAGE_BASENAME}-${MACHINE}.cpio.gz" COREOS_IMAGE_GENERATE_SWU = "0" -# Change generated UKI filename and bundled command line -# Having the same name to KERNEL0 and KERNEL1 means that KERNEL1 will overwrite -# KERNEL0. -COREOS_KERNEL0_NAME ?= "coreos-installer-${MACHINE}" -COREOS_KERNEL1_NAME ?= "coreos-installer-${MACHINE}" -COREOS_KERNEL0_CMDLINE ?= "${APPEND}" -COREOS_KERNEL1_CMDLINE ?= "${APPEND}" +# Change generated UKI filename and reset the bundled command line to "APPEND" +# to ensure that root is not set in the kernel command line +COREOS_KERNEL_NAME ?= "coreos-installer-${MACHINE}" +COREOS_KERNEL_CMDLINE ?= "${APPEND}" inherit coreos-image