Skip to content

Commit

Permalink
drivers/efi: add optional ESRT-friently coreboot table tag
Browse files Browse the repository at this point in the history
New CONFIG_DRIVERS_EFI_FW_INFO is off by default, enabling it adds
DRIVERS_EFI_FW_{GUID,VERSION,LSV} to be used to specify firmware
version/update information.

Existing forms of versions woudn't be sufficient because there is no
universal way of conversion to 32-bit unsigned integers and there are no
GUIDs or lowest supported versions.

Change-Id: Ic1b768d7bed43edf7ca8e41552087734054de033
Signed-off-by: Sergii Dmytruk <[email protected]>
  • Loading branch information
SergiiDmytruk committed Jun 24, 2024
1 parent 51f3e3a commit 00bebe0
Show file tree
Hide file tree
Showing 6 changed files with 87 additions and 0 deletions.
19 changes: 19 additions & 0 deletions src/commonlib/include/commonlib/coreboot_tables.h
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ enum {
LB_TAG_TYPE_C_INFO = 0x0042,
LB_TAG_ACPI_RSDP = 0x0043,
LB_TAG_PCIE = 0x0044,
LB_TAG_EFI_FW_INFO = 0x0046,
LB_TAG_LOGO = 0x00a0,
/* The following options are CMOS-related */
LB_TAG_CMOS_OPTION_TABLE = 0x00c8,
Expand Down Expand Up @@ -587,4 +588,22 @@ struct bootlogo_header {
uint64_t size;
} __packed;

/*
* Machine-friendly version of a system firmware component. A component is
* identified by a GUID. coreboot is an obvious main component but there could
* be others (like EC) which should get their own instances of the tag.
*
* The main consumer of this information is UEFI firmware but something else
* could reuse it too.
*
* Larger number in version fields correspond to more recent versions.
*/
struct lb_efi_fw_info {
uint32_t tag;
uint32_t size;
uint8_t guid[16]; /* Called "firmware class" in UEFI */
uint32_t version; /* Current version */
uint32_t lowest_supported_version; /* Lowest allowed version for downgrades */
} __packed;

#endif
32 changes: 32 additions & 0 deletions src/drivers/efi/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,35 @@ config DRIVERS_EFI_VARIABLE_STORE
help
Adds a driver that is able to read and write an EFI formatted
VariableStore as used by tianocore.

config DRIVERS_EFI_FW_INFO
bool "Expose firmware version in a EFI-friendly form"
depends on UDK_BASE
help
Adds firmware version information to coreboot table in a form similar to
EFI System Resource Table (ESRT) that can be used for firmware updates.

config DRIVERS_EFI_FW_GUID
string "GUID of the firmware"
default "00112233-4455-6677-8899-aabbccddeeff"
depends on DRIVERS_EFI_FW_INFO
help
GUID used to identify firmware kind for the purposes of updates.

config DRIVERS_EFI_FW_VERSION
hex "Version of the firmware"
range 0x00000000 0xFFFFFFFF
default 0x00000000
depends on DRIVERS_EFI_FW_INFO
help
32-bit unsigned integer representing current firmware's version.

config DRIVERS_EFI_FW_LSV
hex "Lowest supported firmware version"
range 0x00000000 0xFFFFFFFF
default 0x00000000
depends on DRIVERS_EFI_FW_INFO
help
32-bit unsigned integer representing lowest firmware version number
that is allowed to replace the current one. Can be used to forbid
bugged versions.
2 changes: 2 additions & 0 deletions src/drivers/efi/Makefile.mk
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,5 @@ smm-$(CONFIG_DRIVERS_EFI_VARIABLE_STORE) += efivars.c

all-$(CONFIG_USE_UEFI_VARIABLE_STORE) += option.c
smm-$(CONFIG_USE_UEFI_VARIABLE_STORE) += option.c

ramstage-$(CONFIG_DRIVERS_EFI_FW_INFO) += info.c
27 changes: 27 additions & 0 deletions src/drivers/efi/info.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/* SPDX-License-Identifier: GPL-2.0-only */

#include <boot/coreboot_tables.h>
#include <console/console.h>
#include <stdint.h>
#include <string.h>
#include <uuid.h>

void lb_efi_fw_info(struct lb_header *header)
{
uint8_t guid[16];
struct lb_efi_fw_info *fw_info;

if (parse_uuid(guid, CONFIG_DRIVERS_EFI_FW_GUID)) {
printk(BIOS_ERR, "%s(): failed to parse firmware's GUID: '%s'\n", __func__,
CONFIG_DRIVERS_EFI_FW_GUID);
return;
}

fw_info = (struct lb_efi_fw_info *)lb_new_record(header);
fw_info->tag = LB_TAG_EFI_FW_INFO;
fw_info->size = sizeof(*fw_info);

memcpy(fw_info->guid, guid, sizeof(guid));
fw_info->version = CONFIG_DRIVERS_EFI_FW_VERSION;
fw_info->lowest_supported_version = CONFIG_DRIVERS_EFI_FW_LSV;
}
3 changes: 3 additions & 0 deletions src/include/boot/coreboot_tables.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ enum cb_err fill_lb_pcie(struct lb_pcie *pcie);
/* Define this in mainboard.c to add board-specific table entries. */
void lb_board(struct lb_header *header);

/* Adds LB_TAG_EFI_FW_INFO table entry (or entries). */
void lb_efi_fw_info(struct lb_header *header);

/* Define this function to fill in the frame buffer returning 0 on success and
< 0 on error. */
int fill_lb_framebuffer(struct lb_framebuffer *framebuffer);
Expand Down
4 changes: 4 additions & 0 deletions src/lib/coreboot_table.c
Original file line number Diff line number Diff line change
Expand Up @@ -572,6 +572,10 @@ static uintptr_t write_coreboot_table(uintptr_t rom_table_end)
/* Add board-specific table entries, if any. */
lb_board(head);

/* Add information about firmware in form suitable for EFI updates. */
if (CONFIG(DRIVERS_EFI_FW_INFO))
lb_efi_fw_info(head);

if (CONFIG(CHROMEOS_RAMOOPS))
lb_ramoops(head);

Expand Down

0 comments on commit 00bebe0

Please sign in to comment.