summaryrefslogtreecommitdiffstats
path: root/OvmfPkg/QemuKernelLoaderFsDxe
diff options
context:
space:
mode:
authorGerd Hoffmann <kraxel@redhat.com>2025-01-15 00:29:52 +0100
committerArd Biesheuvel <workofard@gmail.com>2025-01-21 13:45:46 +0100
commit20df7c42bd446fe725bfc78cdb40577456c421d8 (patch)
tree5a51f7cc90b51039d74ca9c03f4d0e00cef7f97b /OvmfPkg/QemuKernelLoaderFsDxe
parent459f5ffa24ae8574657c4105af0ff7dc30ac428d (diff)
downloadedk2-20df7c42bd446fe725bfc78cdb40577456c421d8.tar.gz
OvmfPkg/QemuKernelLoaderFsDxe: add support for named blobs
Load all named fw_cfg blobs with "etc/boot/" prefix into the pseudo filesystem. Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
Diffstat (limited to 'OvmfPkg/QemuKernelLoaderFsDxe')
-rw-r--r--OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.c94
-rw-r--r--OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.inf1
2 files changed, 84 insertions, 11 deletions
diff --git a/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.c b/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.c
index 7ad1b3828f..1f63adda0b 100644
--- a/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.c
+++ b/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.c
@@ -21,6 +21,7 @@
#include <Library/DebugLib.h>
#include <Library/DevicePathLib.h>
#include <Library/MemoryAllocationLib.h>
+#include <Library/PrintLib.h>
#include <Library/QemuFwCfgLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include <Library/UefiRuntimeServicesTableLib.h>
@@ -32,12 +33,12 @@
// Static data that hosts the fw_cfg blobs and serves file requests.
//
typedef struct {
- CONST CHAR16 Name[8];
+ CHAR16 Name[8];
struct {
- FIRMWARE_CONFIG_ITEM CONST SizeKey;
- FIRMWARE_CONFIG_ITEM CONST DataKey;
- UINT32 Size;
- } FwCfgItem[2];
+ FIRMWARE_CONFIG_ITEM SizeKey;
+ FIRMWARE_CONFIG_ITEM DataKey;
+ UINT32 Size;
+ } FwCfgItem[2];
} KERNEL_BLOB_ITEMS;
typedef struct KERNEL_BLOB KERNEL_BLOB;
@@ -989,15 +990,23 @@ QemuKernelFetchBlob (
//
// Read blob size.
+ // Size != 0 -> use size as-is
+ // SizeKey != 0 -> read size from fw_cfg
+ // both are 0 -> unused entry
//
for (Size = 0, Idx = 0; Idx < ARRAY_SIZE (BlobItems->FwCfgItem); Idx++) {
- if (BlobItems->FwCfgItem[Idx].SizeKey == 0) {
+ if ((BlobItems->FwCfgItem[Idx].SizeKey == 0) &&
+ (BlobItems->FwCfgItem[Idx].Size == 0))
+ {
break;
}
- QemuFwCfgSelectItem (BlobItems->FwCfgItem[Idx].SizeKey);
- BlobItems->FwCfgItem[Idx].Size = QemuFwCfgRead32 ();
- Size += BlobItems->FwCfgItem[Idx].Size;
+ if (BlobItems->FwCfgItem[Idx].SizeKey) {
+ QemuFwCfgSelectItem (BlobItems->FwCfgItem[Idx].SizeKey);
+ BlobItems->FwCfgItem[Idx].Size = QemuFwCfgRead32 ();
+ }
+
+ Size += BlobItems->FwCfgItem[Idx].Size;
}
if (Size == 0) {
@@ -1083,6 +1092,55 @@ QemuKernelVerifyBlob (
return Status;
}
+STATIC
+EFI_STATUS
+QemuKernelFetchNamedBlobs (
+ VOID
+ )
+{
+ struct {
+ UINT32 FileSize;
+ UINT16 FileSelect;
+ UINT16 Reserved;
+ CHAR8 FileName[QEMU_FW_CFG_FNAME_SIZE];
+ } *DirEntry;
+ KERNEL_BLOB_ITEMS Items;
+ EFI_STATUS Status;
+ EFI_STATUS FetchStatus;
+ UINT32 Count;
+ UINT32 Idx;
+
+ QemuFwCfgSelectItem (QemuFwCfgItemFileDir);
+ Count = SwapBytes32 (QemuFwCfgRead32 ());
+
+ DirEntry = AllocatePool (sizeof (*DirEntry) * Count);
+ QemuFwCfgReadBytes (sizeof (*DirEntry) * Count, DirEntry);
+
+ for (Idx = 0; Idx < Count; ++Idx) {
+ if (AsciiStrnCmp (DirEntry[Idx].FileName, "etc/boot/", 9) != 0) {
+ continue;
+ }
+
+ ZeroMem (&Items, sizeof (Items));
+ UnicodeSPrint (Items.Name, sizeof (Items.Name), L"%a", DirEntry[Idx].FileName + 9);
+ Items.FwCfgItem[0].DataKey = SwapBytes16 (DirEntry[Idx].FileSelect);
+ Items.FwCfgItem[0].Size = SwapBytes32 (DirEntry[Idx].FileSize);
+
+ FetchStatus = QemuKernelFetchBlob (&Items);
+ Status = QemuKernelVerifyBlob (
+ (CHAR16 *)Items.Name,
+ FetchStatus
+ );
+ if (EFI_ERROR (Status)) {
+ FreePool (DirEntry);
+ return Status;
+ }
+ }
+
+ FreePool (DirEntry);
+ return EFI_SUCCESS;
+}
+
//
// The entry point of the feature.
//
@@ -1126,10 +1184,24 @@ QemuKernelLoaderFsDxeEntrypoint (
}
//
- // Fetch all blobs.
+ // Fetch named blobs.
//
+ DEBUG ((DEBUG_INFO, "%a: named blobs (etc/boot/*)\n", __func__));
+ Status = QemuKernelFetchNamedBlobs ();
+ if (EFI_ERROR (Status)) {
+ goto FreeBlobs;
+ }
+
+ //
+ // Fetch traditional blobs.
+ //
+ DEBUG ((DEBUG_INFO, "%a: traditional blobs\n", __func__));
for (BlobIdx = 0; BlobIdx < ARRAY_SIZE (mKernelBlobItems); ++BlobIdx) {
- BlobItems = &mKernelBlobItems[BlobIdx];
+ BlobItems = &mKernelBlobItems[BlobIdx];
+ if (FindKernelBlob (BlobItems->Name)) {
+ continue;
+ }
+
FetchStatus = QemuKernelFetchBlob (BlobItems);
Status = QemuKernelVerifyBlob (
diff --git a/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.inf b/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.inf
index 7b35adb8e0..a2f44bbca1 100644
--- a/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.inf
+++ b/OvmfPkg/QemuKernelLoaderFsDxe/QemuKernelLoaderFsDxe.inf
@@ -30,6 +30,7 @@
DebugLib
DevicePathLib
MemoryAllocationLib
+ PrintLib
QemuFwCfgLib
UefiBootServicesTableLib
UefiDriverEntryPoint