* [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols
@ 2025-10-07 0:59 chalianis1
2025-10-07 0:59 ` [PATCH v2 02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool chalianis1
` (9 more replies)
0 siblings, 10 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Ahmad Fatoum, Chali Anis
From: Ahmad Fatoum <a.fatoum@barebox.org>
We are already keeping different directories for payload and common EFI
support. In preparation for adding more payload-specific config options,
move the existing ones into their own Kconfig file.
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
efi/Kconfig | 20 +-------------------
efi/payload/Kconfig | 27 +++++++++++++++++++++++++++
2 files changed, 28 insertions(+), 19 deletions(-)
create mode 100644 efi/payload/Kconfig
diff --git a/efi/Kconfig b/efi/Kconfig
index 84f670fd23d3..35850b20ef50 100644
--- a/efi/Kconfig
+++ b/efi/Kconfig
@@ -2,21 +2,7 @@
menu "EFI (Extensible Firmware Interface) Support"
-config HAVE_EFI_PAYLOAD
- bool
-
-config EFI_PAYLOAD
- bool "Build as EFI payload" if COMPILE_TEST
- depends on HAVE_EFI_PAYLOAD
- select PBL_FULLY_PIC if ARM64
- select EFI
- select EFI_GUID
- select EFI_DEVICEPATH
- select PRINTF_UUID
- select PRINTF_WCHAR
- select BLOCK
- select PARTITION_DISK
- select HW_HAS_PCI
+source "efi/payload/Kconfig"
config EFI
bool
@@ -26,10 +12,6 @@ config HAVE_EFI_STUB
if EFI
-config EFI_STUB
- def_bool EFI_PAYLOAD
- depends on HAVE_EFI_STUB
-
config EFI_GUID
bool
help
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
new file mode 100644
index 000000000000..9263d59de94a
--- /dev/null
+++ b/efi/payload/Kconfig
@@ -0,0 +1,27 @@
+# SPDX-License-Identifier: GPL-2.0-only
+
+config HAVE_EFI_PAYLOAD
+ bool
+
+config EFI_PAYLOAD
+ bool "Build as EFI payload" if COMPILE_TEST
+ depends on HAVE_EFI_PAYLOAD
+ select PBL_FULLY_PIC if ARM64
+ select EFI
+ select EFI_GUID
+ select EFI_DEVICEPATH
+ select PRINTF_UUID
+ select PRINTF_WCHAR
+ select BLOCK
+ select PARTITION_DISK
+ select HW_HAS_PCI
+
+config HAVE_EFI_STUB
+ bool
+
+if EFI_PAYLOAD
+
+config EFI_STUB
+ def_bool HAVE_EFI_STUB
+
+endif
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store chalianis1
` (8 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Ahmad Fatoum, Chali Anis
From: Ahmad Fatoum <a.fatoum@barebox.org>
Unallocated memory is poisoned by default to catch heap overflows.
Its control data can also be poisoned by default as the code takes care
to unpoison it on access.
Move the poisoning thus tlsf_add_pool(), so users need not worry about
it.
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
common/tlsf.c | 7 +++++--
common/tlsf_malloc.c | 2 --
2 files changed, 5 insertions(+), 4 deletions(-)
diff --git a/common/tlsf.c b/common/tlsf.c
index 8666b94ea387..4ee53a9b2f20 100644
--- a/common/tlsf.c
+++ b/common/tlsf.c
@@ -814,6 +814,7 @@ size_t tlsf_alloc_overhead(void)
pool_t tlsf_add_pool(tlsf_t tlsf, void* mem, size_t bytes)
{
+ control_t* control = tlsf_cast(control_t*, tlsf);
block_header_t* block;
block_header_t* next;
@@ -844,7 +845,7 @@ pool_t tlsf_add_pool(tlsf_t tlsf, void* mem, size_t bytes)
block_set_size(block, pool_bytes);
block_set_free(block);
block_set_prev_used(block);
- block_insert(tlsf_cast(control_t*, tlsf), block);
+ block_insert(control, block);
/* Split the block to create a zero-size sentinel block. */
next = block_link_next(block);
@@ -852,6 +853,9 @@ pool_t tlsf_add_pool(tlsf_t tlsf, void* mem, size_t bytes)
block_set_used(next);
block_set_prev_free(next);
+ kasan_poison_shadow(mem, bytes, KASAN_TAG_INVALID);
+ kasan_poison_shadow(control, sizeof(control), KASAN_TAG_INVALID);
+
return mem;
}
@@ -927,7 +931,6 @@ tlsf_t tlsf_create_with_pool(void* mem, size_t bytes)
{
tlsf_t tlsf = tlsf_create(mem);
tlsf_add_pool(tlsf, (char*)mem + tlsf_size(), bytes - tlsf_size());
- kasan_poison_shadow(mem, bytes, KASAN_TAG_INVALID);
return tlsf;
}
diff --git a/common/tlsf_malloc.c b/common/tlsf_malloc.c
index 6e9d48af26bb..74089fe7f390 100644
--- a/common/tlsf_malloc.c
+++ b/common/tlsf_malloc.c
@@ -115,8 +115,6 @@ void *malloc_add_pool(void *mem, size_t bytes)
if (!new_pool)
return NULL;
- kasan_poison_shadow(mem, bytes, KASAN_TAG_INVALID);
-
new_pool_entry = malloc(sizeof(*new_pool_entry));
if (!new_pool_entry)
return NULL;
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
2025-10-07 0:59 ` [PATCH v2 02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 13:42 ` Sascha Hauer
2025-10-07 0:59 ` [PATCH v2 04/10] efi: payload: add support for EFI initrd media protocol chalianis1
` (7 subsequent siblings)
9 siblings, 1 reply; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis, Ahmad Fatoum
From: Chali Anis <chalianis1@gmail.com>
barebox running under an operating system (or nearly one like UEFI) does
not have control over all the memory and should not hog too much memory
upfront as that can interfere with other applications, e.g. EFI drivers
or the EFI firmware itself.
To accommodate this use case, allow TLSF to dynamically request more
memory from an external store via tlsf_register_store().
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
common/tlsf.c | 29 ++++++++++++++++++++++++++++-
include/tlsf.h | 1 +
2 files changed, 29 insertions(+), 1 deletion(-)
diff --git a/common/tlsf.c b/common/tlsf.c
index 4ee53a9b2f20..636b57b1c642 100644
--- a/common/tlsf.c
+++ b/common/tlsf.c
@@ -159,6 +159,9 @@ typedef struct control_t
/* Empty lists point at this block to indicate they are free. */
block_header_t block_null;
+ void (*request_store)(tlsf_t, size_t);
+
+
/* Bitmaps for free lists. */
unsigned int fl_bitmap;
unsigned int sl_bitmap[FL_INDEX_COUNT];
@@ -568,7 +571,7 @@ static block_header_t* block_trim_free_leading(control_t* control, block_header_
return remaining_block;
}
-static block_header_t* block_locate_free(control_t* control, size_t size)
+static block_header_t* __block_locate_free(control_t* control, size_t size)
{
int fl = 0, sl = 0;
block_header_t* block = 0;
@@ -598,6 +601,23 @@ static block_header_t* block_locate_free(control_t* control, size_t size)
return block;
}
+static block_header_t* block_locate_free(control_t* control, size_t size)
+{
+ block_header_t *block;
+
+ block = __block_locate_free(control, size);
+ if (block)
+ return block;
+
+ if (!control->request_store || !size)
+ return NULL;
+
+ control->request_store(tlsf_cast(tlsf_t, control),
+ size + tlsf_pool_overhead());
+
+ return __block_locate_free(control, size);
+}
+
static void* block_prepare_used(control_t* control, block_header_t* block,
size_t size, size_t used)
{
@@ -934,6 +954,13 @@ tlsf_t tlsf_create_with_pool(void* mem, size_t bytes)
return tlsf;
}
+void tlsf_register_store(tlsf_t tlsf, void (*cb)(tlsf_t tlsf, size_t bytes))
+{
+ control_t* control = tlsf_cast(control_t*, tlsf);
+
+ control->request_store = cb;
+}
+
void tlsf_destroy(tlsf_t tlsf)
{
/* Nothing to do. */
diff --git a/include/tlsf.h b/include/tlsf.h
index e0dcdac1e7ab..ea86b0600c49 100644
--- a/include/tlsf.h
+++ b/include/tlsf.h
@@ -63,6 +63,7 @@ tlsf_t tlsf_create(void* mem);
tlsf_t tlsf_create_with_pool(void* mem, size_t bytes);
void tlsf_destroy(tlsf_t tlsf);
pool_t tlsf_get_pool(tlsf_t tlsf);
+void tlsf_register_store(tlsf_t tlsf, void (*cb)(tlsf_t tlsf, size_t bytes));
/* Add/remove memory pools. */
pool_t tlsf_add_pool(tlsf_t tlsf, void* mem, size_t bytes);
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 04/10] efi: payload: add support for EFI initrd media protocol
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
2025-10-07 0:59 ` [PATCH v2 02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool chalianis1
2025-10-07 0:59 ` [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 05/10] efi: payload: earlymem: allocate only the barebox needs in term of memory chalianis1
` (6 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis, Ahmad Fatoum
From: Chali Anis <chalianis1@gmail.com>
Implement the EFI initrd media protocol, which allows registering an
initramfs data to be loaded by the linux after vi EFI Initrd Media
protocol.
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
efi/guid.c | 4 ++
efi/payload/Makefile | 1 +
efi/payload/efi-initrd.c | 104 ++++++++++++++++++++++++++++++++++++++
include/efi.h | 4 ++
include/efi/efi-payload.h | 3 ++
5 files changed, 116 insertions(+)
create mode 100644 efi/payload/efi-initrd.c
diff --git a/efi/guid.c b/efi/guid.c
index ef230a2b2403..46440c9f3328 100644
--- a/efi/guid.c
+++ b/efi/guid.c
@@ -44,6 +44,7 @@ const efi_guid_t efi_load_file_protocol_guid = EFI_LOAD_FILE_PROTOCOL_GUID;
const efi_guid_t efi_load_file2_protocol_guid = EFI_LOAD_FILE2_PROTOCOL_GUID;
const efi_guid_t efi_device_path_utilities_protocol_guid =
EFI_DEVICE_PATH_UTILITIES_PROTOCOL_GUID;
+const efi_guid_t efi_linux_initrd_media_guid = EFI_LINUX_INITRD_MEDIA_GUID;
#define EFI_GUID_STRING(guid, short, long) do { \
if (!efi_guidcmp(guid, *g)) \
@@ -128,5 +129,8 @@ const char *efi_guid_string(efi_guid_t *g)
EFI_GUID_STRING(EFI_ISCSIDXE_INF_GUID, "IScsiDxe.inf", "EFI IScsiDxe.inf File GUID");
EFI_GUID_STRING(EFI_VLANCONFIGDXE_INF_GUID, "VlanConfigDxe.inf", "EFI VlanConfigDxe.inf File GUID");
+ /* Ramdisk */
+ EFI_GUID_STRING(EFI_LINUX_INITRD_MEDIA_GUID, "Initrd Media", "EFI Linux Initrd Media GUID");
+
return "unknown";
}
diff --git a/efi/payload/Makefile b/efi/payload/Makefile
index a4a0332a8288..1250535302d3 100644
--- a/efi/payload/Makefile
+++ b/efi/payload/Makefile
@@ -2,6 +2,7 @@
obj-y += init.o
obj-y += image.o
+obj-y += efi-initrd.o
obj-$(CONFIG_OFTREE) += fdt.o
bbenv-y += env-efi
obj-$(CONFIG_CMD_IOMEM) += iomem.o
diff --git a/efi/payload/efi-initrd.c b/efi/payload/efi-initrd.c
new file mode 100644
index 000000000000..7a9317fa070e
--- /dev/null
+++ b/efi/payload/efi-initrd.c
@@ -0,0 +1,104 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * efi-initrd.c - barebox EFI payload support
+ *
+ * Copyright (c) 2025 Anis Chali <chalianis1@gmail.com>
+ * Copyright (C) 2025 Ahmad Fatoum <a.fatoum@pengutronix.de>
+ */
+#include <common.h>
+#include <driver.h>
+#include <init.h>
+#include <linux/hw_random.h>
+#include <efi.h>
+#include <efi/efi-device.h>
+#include <efi/device-path.h>
+#include <efi/efi-payload.h>
+
+static efi_status_t EFIAPI efi_initrd_load_file2(
+ struct efi_load_file_protocol *this, struct efi_device_path *file_path,
+ bool boot_policy, unsigned long *buffer_size, void *buffer);
+
+static const struct {
+ struct efi_device_path_vendor vendor;
+ struct efi_device_path end;
+} __packed initrd_dev_path = {
+ { {
+ DEVICE_PATH_TYPE_MEDIA_DEVICE,
+ DEVICE_PATH_SUB_TYPE_VENDOR_PATH,
+ sizeof(initrd_dev_path.vendor),
+ },
+ EFI_LINUX_INITRD_MEDIA_GUID },
+ { DEVICE_PATH_TYPE_END, DEVICE_PATH_SUB_TYPE_END,
+ DEVICE_PATH_END_LENGTH }
+};
+
+static struct linux_initrd {
+ struct efi_load_file_protocol base;
+ void *start;
+ size_t size;
+ efi_handle_t lf2_handle;
+} initrd;
+
+#define to_linux_initrd(x) container_of(x, struct linux_initrd, base)
+
+static efi_status_t EFIAPI efi_initrd_load_file2(
+ struct efi_load_file_protocol *this, struct efi_device_path *file_path,
+ bool boot_policy, unsigned long *buffer_size, void *buffer)
+{
+
+ struct linux_initrd *initrd = to_linux_initrd(this);
+
+ if (!this || this != &initrd->base || !buffer_size)
+ return EFI_INVALID_PARAMETER;
+
+ if (file_path->type != initrd_dev_path.end.type ||
+ file_path->sub_type != initrd_dev_path.end.sub_type)
+ return EFI_INVALID_PARAMETER;
+
+ if (boot_policy)
+ return EFI_UNSUPPORTED;
+
+ if (!buffer || *buffer_size < initrd->size) {
+ *buffer_size = initrd->size;
+ return EFI_BUFFER_TOO_SMALL;
+ } else {
+ memcpy(buffer, initrd->start, initrd->size);
+ *buffer_size = initrd->size;
+ }
+
+ return EFI_SUCCESS;
+}
+
+int efi_initrd_register(void *initrd_base, size_t initrd_sz)
+{
+ efi_status_t efiret;
+ int ret;
+
+ initrd.base.load_file = efi_initrd_load_file2;
+ initrd.start = initrd_base;
+ initrd.size = initrd_sz;
+
+ efiret = BS->install_multiple_protocol_interfaces(
+ &initrd.lf2_handle, &efi_load_file2_protocol_guid, &initrd.base,
+ &efi_device_path_protocol_guid, &initrd_dev_path, NULL);
+ if (EFI_ERROR(efiret)) {
+ pr_err("Failed to install protocols for INITRD %s\n",
+ efi_strerror(efiret));
+ ret = -efi_errno(efiret);
+ return ret;
+ }
+
+ return 0;
+}
+
+void efi_initrd_unregister(void)
+{
+ if (!initrd.base.load_file)
+ return;
+
+ BS->uninstall_multiple_protocol_interfaces(
+ initrd.lf2_handle, &efi_device_path_protocol_guid, &initrd_dev_path,
+ &efi_load_file2_protocol_guid, &initrd.base, NULL);
+
+ initrd.base.load_file = NULL;
+}
\ No newline at end of file
diff --git a/include/efi.h b/include/efi.h
index 40b69fdb0188..bd339ea097c3 100644
--- a/include/efi.h
+++ b/include/efi.h
@@ -558,6 +558,9 @@ extern struct efi_runtime_services *RT;
#define EFI_DRIVER_BINDING_PROTOCOL_GUID \
EFI_GUID(0x18a031ab, 0xb443, 0x4d1a, 0xa5, 0xc0, 0x0c, 0x09, 0x26, 0x1e, 0x9f, 0x71)
+#define EFI_LINUX_INITRD_MEDIA_GUID \
+ EFI_GUID(0x5568e427, 0x68fc, 0x4f3d, 0xac, 0x74, 0xca, 0x55, 0x52, 0x31, 0xcc, 0x68)
+
struct efi_driver_binding_protocol {
efi_status_t (EFIAPI * supported)(
struct efi_driver_binding_protocol *this,
@@ -603,6 +606,7 @@ extern const efi_guid_t efi_guid_event_group_reset_system;
extern const efi_guid_t efi_load_file_protocol_guid;
extern const efi_guid_t efi_load_file2_protocol_guid;
extern const efi_guid_t efi_device_path_utilities_protocol_guid;
+extern const efi_guid_t efi_linux_initrd_media_guid;
struct efi_config_table {
efi_guid_t guid;
diff --git a/include/efi/efi-payload.h b/include/efi/efi-payload.h
index fe45864dd8a7..d8e66a187a87 100644
--- a/include/efi/efi-payload.h
+++ b/include/efi/efi-payload.h
@@ -34,4 +34,7 @@ int efi_set_variable_usec(char *name, efi_guid_t *vendor, uint64_t usec);
void *efi_earlymem_alloc(const struct efi_system_table *sys_table,
size_t *memsize, enum efi_memory_type mem_type);
+int efi_initrd_register(void *initrd, size_t initrd_size);
+void efi_initrd_unregister(void);
+
#endif
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 05/10] efi: payload: earlymem: allocate only the barebox needs in term of memory
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (2 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 04/10] efi: payload: add support for EFI initrd media protocol chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 06/10] efi: payload: split image handling from legacy handover boot and add linux x86 image filetype chalianis1
` (5 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis, Ahmad Fatoum
From: Chali Anis <chalianis1@gmail.com>
With TLSF now able to invoke a callback to request additional memory on
demand, limit early allocations to what barebox strictly requires and have
everything handled via the request callback. This ensures more deterministic
behavior and reduces the risk of OOM conditions.
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
common/tlsf_malloc.c | 18 ++++++++++++++++++
efi/payload/Kconfig | 1 +
efi/payload/early-mem.c | 19 ++++---------------
efi/payload/entry-multi.c | 5 ++---
efi/payload/entry-single.c | 5 ++---
efi/payload/init.c | 15 +++++++++++++++
include/efi/efi-payload.h | 2 +-
include/malloc.h | 1 +
8 files changed, 44 insertions(+), 22 deletions(-)
diff --git a/common/tlsf_malloc.c b/common/tlsf_malloc.c
index 74089fe7f390..d3b665a2fc40 100644
--- a/common/tlsf_malloc.c
+++ b/common/tlsf_malloc.c
@@ -11,11 +11,14 @@
#include <stdio.h>
#include <module.h>
#include <tlsf.h>
+#include <linux/sizes.h>
+#include <linux/log2.h>
#include <linux/kasan.h>
#include <linux/list.h>
tlsf_t tlsf_mem_pool;
+static void (*malloc_request_store)(size_t bytes);
struct pool_entry {
pool_t pool;
@@ -124,3 +127,18 @@ void *malloc_add_pool(void *mem, size_t bytes)
return (void *)new_pool;
}
+
+static void tlsf_request_store(tlsf_t tlsf, size_t bytes)
+{
+ size_t size;
+
+ size = __roundup_pow_of_two(bytes + sizeof(struct pool_entry));
+
+ malloc_request_store(max_t(size_t, SZ_8M, size));
+}
+
+void malloc_register_store(void (*cb)(size_t bytes))
+{
+ malloc_request_store = cb;
+ tlsf_register_store(tlsf_mem_pool, tlsf_request_store);
+}
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
index 9263d59de94a..a403acc81a93 100644
--- a/efi/payload/Kconfig
+++ b/efi/payload/Kconfig
@@ -15,6 +15,7 @@ config EFI_PAYLOAD
select BLOCK
select PARTITION_DISK
select HW_HAS_PCI
+ select MALLOC_TLSF
config HAVE_EFI_STUB
bool
diff --git a/efi/payload/early-mem.c b/efi/payload/early-mem.c
index 0f79a8c30694..c5e94b33a756 100644
--- a/efi/payload/early-mem.c
+++ b/efi/payload/early-mem.c
@@ -6,28 +6,17 @@
#include <efi/efi-payload.h>
void *efi_earlymem_alloc(const struct efi_system_table *sys_table,
- size_t *memsize, enum efi_memory_type mem_type)
+ size_t memsize, enum efi_memory_type mem_type)
{
struct efi_boot_services *bs = sys_table->boottime;
- enum efi_allocate_type alloc_type = EFI_ALLOCATE_ANY_PAGES;
efi_physical_addr_t mem;
efi_status_t efiret;
- if (IS_ENABLED(CONFIG_X86)) {
- /* Try to stay clear of memory mapped devices */
- alloc_type = EFI_ALLOCATE_MAX_ADDRESS;
- mem = SZ_1G - 1;
- }
-
- for (*memsize = SZ_256M; *memsize >= SZ_8M; *memsize /= 2) {
- efiret = bs->allocate_pages(alloc_type, mem_type,
- *memsize / EFI_PAGE_SIZE, &mem);
- if (!EFI_ERROR(efiret) || efiret != EFI_OUT_OF_RESOURCES)
- break;
- }
+ efiret = bs->allocate_pages(EFI_ALLOCATE_ANY_PAGES, mem_type,
+ memsize / EFI_PAGE_SIZE, &mem);
if (EFI_ERROR(efiret))
panic("failed to allocate %zu byte memory pool: 0x%lx\n",
- *memsize, efiret);
+ memsize, efiret);
return efi_phys_to_virt(mem);
}
diff --git a/efi/payload/entry-multi.c b/efi/payload/entry-multi.c
index d5d54cdf70a1..82f3dfffe870 100644
--- a/efi/payload/entry-multi.c
+++ b/efi/payload/entry-multi.c
@@ -23,7 +23,6 @@ static void efi_putc(void *ctx, int ch)
void __efistub_efi_pe_entry(void *image, struct efi_system_table *sys_table)
{
- size_t memsize;
void *mem;
static struct barebox_efi_data efidata;
@@ -37,7 +36,7 @@ void __efistub_efi_pe_entry(void *image, struct efi_system_table *sys_table)
handoff_data_add(HANDOFF_DATA_EFI, &efidata, sizeof(efidata));
- mem = efi_earlymem_alloc(sys_table, &memsize, EFI_LOADER_CODE);
+ mem = efi_earlymem_alloc(sys_table, SZ_16M, EFI_BOOT_SERVICES_CODE);
- barebox_pbl_entry((uintptr_t)mem, memsize, NULL);
+ barebox_pbl_entry((uintptr_t)mem, SZ_16M, NULL);
}
diff --git a/efi/payload/entry-single.c b/efi/payload/entry-single.c
index 8600bd845c49..f481d0942ba5 100644
--- a/efi/payload/entry-single.c
+++ b/efi/payload/entry-single.c
@@ -17,7 +17,6 @@
void efi_main(efi_handle_t image, struct efi_system_table *sys_table)
{
efi_status_t efiret;
- size_t memsize;
void *mem;
#ifdef DEBUG
@@ -37,9 +36,9 @@ void efi_main(efi_handle_t image, struct efi_system_table *sys_table)
BS->handle_protocol(efi_loaded_image->device_handle,
&efi_device_path_protocol_guid, (void **)&efi_device_path);
- mem = efi_earlymem_alloc(sys_table, &memsize, EFI_LOADER_DATA);
+ mem = efi_earlymem_alloc(sys_table, SZ_16M, EFI_BOOT_SERVICES_DATA);
- mem_malloc_init(mem, mem + memsize - 1);
+ mem_malloc_init(mem, mem + SZ_16M - 1);
start_barebox();
}
diff --git a/efi/payload/init.c b/efi/payload/init.c
index 239c5ce9ec18..5b827c57ed1f 100644
--- a/efi/payload/init.c
+++ b/efi/payload/init.c
@@ -270,11 +270,26 @@ static int efi_init(void)
}
device_efi_initcall(efi_init);
+static void efi_request_mem(size_t bytes)
+{
+ efi_status_t efiret;
+ efi_physical_addr_t mem;
+ size_t pages;
+
+ pages = DIV_ROUND_UP(bytes, EFI_PAGE_SIZE);
+ efiret = BS->allocate_pages(EFI_ALLOCATE_ANY_PAGES, EFI_LOADER_DATA,
+ pages, &mem);
+ if (!EFI_ERROR(efiret))
+ malloc_add_pool(efi_phys_to_virt(mem), pages * EFI_PAGE_SIZE);
+}
+
static int efi_core_init(void)
{
struct device *dev;
int ret;
+ malloc_register_store(efi_request_mem);
+
dev = device_alloc("efi-cs", DEVICE_ID_SINGLE);
ret = platform_device_register(dev);
if (ret)
diff --git a/include/efi/efi-payload.h b/include/efi/efi-payload.h
index d8e66a187a87..337471117d5a 100644
--- a/include/efi/efi-payload.h
+++ b/include/efi/efi-payload.h
@@ -32,7 +32,7 @@ int efi_set_variable(char *name, efi_guid_t *vendor, uint32_t attributes,
int efi_set_variable_usec(char *name, efi_guid_t *vendor, uint64_t usec);
void *efi_earlymem_alloc(const struct efi_system_table *sys_table,
- size_t *memsize, enum efi_memory_type mem_type);
+ size_t memsize, enum efi_memory_type mem_type);
int efi_initrd_register(void *initrd, size_t initrd_size);
void efi_initrd_unregister(void);
diff --git a/include/malloc.h b/include/malloc.h
index 35551250324e..69ff23b4a058 100644
--- a/include/malloc.h
+++ b/include/malloc.h
@@ -23,6 +23,7 @@
#ifdef CONFIG_MALLOC_TLSF
void *malloc_add_pool(void *mem, size_t bytes);
+void malloc_register_store(void (*cb)(size_t bytes));
#endif
#if IN_PROPER
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 06/10] efi: payload: split image handling from legacy handover boot and add linux x86 image filetype
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (3 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 05/10] efi: payload: earlymem: allocate only the barebox needs in term of memory chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 07/10] efi: payload: bootm: add support for efi stub boot chalianis1
` (4 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis, Ahmad Fatoum
From: Chali Anis <chalianis1@gmail.com>
The handover boot support is Linux-specific and can be disabled
with CONFIG_EFI_HANDOVER_PROTOCOL. In preparation for adding a compliant
boot method, move the handover-specific parts into their own file.
Introduce a new filetype for x86 Linux kernel images by checking for
the "HdrS" magic (0x53726448) at offset 0x202 in the setup header.
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
common/filetype.c | 3 +
efi/payload/Kconfig | 5 +
efi/payload/Makefile | 1 +
efi/payload/handover.c | 154 +++++++++++++++++++++++++++++
efi/payload/image.c | 192 +++++--------------------------------
efi/payload/image.h | 14 +++
| 63 ++++++++++++
include/filetype.h | 6 ++
8 files changed, 269 insertions(+), 169 deletions(-)
create mode 100644 efi/payload/handover.c
create mode 100644 efi/payload/image.h
create mode 100644 efi/payload/setup_header.h
diff --git a/common/filetype.c b/common/filetype.c
index eb397a175cb6..72f84442cae9 100644
--- a/common/filetype.c
+++ b/common/filetype.c
@@ -87,6 +87,7 @@ static const struct filetype_str filetype_str[] = {
[filetype_zstd_compressed] = { "ZSTD compressed", "zstd" },
[filetype_rockchip_rkss_image] = { "Rockchip signed boot image",
"rk-image" },
+ [filetype_x86_linux_image] = { "x86 Linux image", "x86-linux" },
};
static const char *file_type_to_nr_string(enum filetype f)
@@ -435,6 +436,8 @@ enum filetype file_detect_type(const void *_buf, size_t bufsize)
return is_dos_exe(buf8) ? filetype_riscv_efi_linux_image : filetype_riscv_linux_image;
if (is_riscv_linux_bootimage(buf) && !memcmp(&buf[12], "barebox", 8))
return filetype_riscv_barebox_image;
+ if (bufsize > 0x206 && is_x86_linux_bootimage(buf))
+ return filetype_x86_linux_image;
if (le32_to_cpu(buf[5]) == 0x504d5453)
return filetype_mxs_bootstream;
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
index a403acc81a93..d0a46704a6b9 100644
--- a/efi/payload/Kconfig
+++ b/efi/payload/Kconfig
@@ -25,4 +25,9 @@ if EFI_PAYLOAD
config EFI_STUB
def_bool HAVE_EFI_STUB
+config EFI_HANDOVER_PROTOCOL
+ bool "EFI Handover protocol"
+ default y
+ depends on X86
+
endif
diff --git a/efi/payload/Makefile b/efi/payload/Makefile
index 1250535302d3..d8b577bf3e23 100644
--- a/efi/payload/Makefile
+++ b/efi/payload/Makefile
@@ -2,6 +2,7 @@
obj-y += init.o
obj-y += image.o
+obj-$(CONFIG_EFI_HANDOVER_PROTOCOL) += handover.o
obj-y += efi-initrd.o
obj-$(CONFIG_OFTREE) += fdt.o
bbenv-y += env-efi
diff --git a/efi/payload/handover.c b/efi/payload/handover.c
new file mode 100644
index 000000000000..82f4cb4f5286
--- /dev/null
+++ b/efi/payload/handover.c
@@ -0,0 +1,154 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * handover.c - legacy x86 EFI handover protocol
+ *
+ * Copyright (c) 2014 Sascha Hauer <s.hauer@pengutronix.de>, Pengutronix
+ */
+
+#define pr_fmt(fmt) "efi-handover: " fmt
+
+#include <clock.h>
+#include <common.h>
+#include <linux/sizes.h>
+#include <linux/ktime.h>
+#include <memory.h>
+#include <command.h>
+#include <magicvar.h>
+#include <init.h>
+#include <driver.h>
+#include <io.h>
+#include <efi.h>
+#include <malloc.h>
+#include <string.h>
+#include <linux/err.h>
+#include <boot.h>
+#include <bootm.h>
+#include <fs.h>
+#include <libfile.h>
+#include <binfmt.h>
+#include <wchar.h>
+#include <efi/efi-payload.h>
+#include <efi/efi-device.h>
+
+#include "image.h"
+#include "setup_header.h"
+
+static int efi_do_execute_image(enum filetype filetype, const char *file)
+{
+ efi_handle_t handle;
+ struct efi_loaded_image *loaded_image;
+ int ret;
+
+ ret = efi_load_image(file, &loaded_image, &handle);
+ if (ret)
+ return ret;
+
+ return efi_execute_image(handle, loaded_image, filetype);
+}
+
+typedef void(*handover_fn)(void *image, struct efi_system_table *table,
+ struct x86_setup_header *header);
+
+static inline void linux_efi_handover(efi_handle_t handle,
+ struct x86_setup_header *header)
+{
+ handover_fn handover;
+ uintptr_t addr;
+
+ addr = header->code32_start + header->handover_offset;
+ if (IS_ENABLED(CONFIG_X86_64))
+ addr += 512;
+
+ handover = efi_phys_to_virt(addr);
+ handover(handle, efi_sys_table, header);
+}
+
+static int do_bootm_efi(struct image_data *data)
+{
+ void *tmp;
+ void *initrd = NULL;
+ size_t size;
+ efi_handle_t handle;
+ int ret;
+ const char *options;
+ struct efi_loaded_image *loaded_image;
+ struct x86_setup_header *image_header, *boot_header;
+
+ ret = efi_load_image(data->os_file, &loaded_image, &handle);
+ if (ret)
+ return ret;
+
+ image_header = (struct x86_setup_header *)loaded_image->image_base;
+
+ if (!is_x86_setup_header(image_header) ||
+ image_header->version < 0x20b ||
+ !image_header->relocatable_kernel) {
+ pr_err("Not a valid kernel image!\n");
+ BS->unload_image(handle);
+ return -EINVAL;
+ }
+
+ boot_header = xmalloc(0x4000);
+ memset(boot_header, 0, 0x4000);
+ memcpy(boot_header, image_header, sizeof(*image_header));
+
+ /* Refer to Linux kernel commit a27e292b8a54
+ * ("Documentation/x86/boot: Reserve type_of_loader=13 for barebox")
+ */
+ boot_header->type_of_loader = 0x13;
+
+ if (data->initrd_file) {
+ tmp = read_file(data->initrd_file, &size);
+ initrd = xmemalign(PAGE_SIZE, PAGE_ALIGN(size));
+ memcpy(initrd, tmp, size);
+ memset(initrd + size, 0, PAGE_ALIGN(size) - size);
+ free(tmp);
+ boot_header->ramdisk_image = efi_virt_to_phys(initrd);
+ boot_header->ramdisk_size = PAGE_ALIGN(size);
+ }
+
+ options = linux_bootargs_get();
+ if (options) {
+ boot_header->cmd_line_ptr = efi_virt_to_phys(options);
+ boot_header->cmdline_size = strlen(options);
+ }
+
+ boot_header->code32_start = efi_virt_to_phys(loaded_image->image_base +
+ (image_header->setup_sects+1) * 512);
+
+ if (bootm_verbose(data)) {
+ printf("\nStarting kernel at 0x%p", loaded_image->image_base);
+ if (data->initrd_file)
+ printf(", initrd at 0x%08x",
+ boot_header->ramdisk_image);
+ printf("...\n");
+ }
+
+ if (data->dryrun) {
+ BS->unload_image(handle);
+ free(boot_header);
+ free(initrd);
+ return 0;
+ }
+
+ efi_set_variable_usec("LoaderTimeExecUSec", &efi_systemd_vendor_guid,
+ ktime_to_us(ktime_get()));
+
+ shutdown_barebox();
+ linux_efi_handover(handle, boot_header);
+
+ return 0;
+}
+
+static struct image_handler efi_handle_tr = {
+ .name = "EFI Application",
+ .bootm = do_bootm_efi,
+ .filetype = filetype_exe,
+};
+
+static int efi_register_handover_handler(void)
+{
+ register_image_handler(&efi_handle_tr);
+ return 0;
+}
+late_efi_initcall(efi_register_handover_handler);
diff --git a/efi/payload/image.c b/efi/payload/image.c
index 33c5e18dac27..ae7678188d84 100644
--- a/efi/payload/image.c
+++ b/efi/payload/image.c
@@ -5,13 +5,12 @@
* Copyright (c) 2014 Sascha Hauer <s.hauer@pengutronix.de>, Pengutronix
*/
+#define pr_fmt(fmt) "efi-image: " fmt
+
#include <clock.h>
#include <common.h>
#include <linux/sizes.h>
-#include <linux/ktime.h>
#include <memory.h>
-#include <command.h>
-#include <magicvar.h>
#include <init.h>
#include <driver.h>
#include <io.h>
@@ -19,7 +18,7 @@
#include <malloc.h>
#include <string.h>
#include <linux/err.h>
-#include <boot.h>
+#include <bootargs.h>
#include <bootm.h>
#include <fs.h>
#include <libfile.h>
@@ -28,54 +27,8 @@
#include <efi/efi-payload.h>
#include <efi/efi-device.h>
-struct linux_kernel_header {
- /* first sector of the image */
- uint8_t code1[0x0020];
- uint16_t cl_magic; /**< Magic number 0xA33F */
- uint16_t cl_offset; /**< The offset of command line */
- uint8_t code2[0x01F1 - 0x0020 - 2 - 2];
- uint8_t setup_sects; /**< The size of the setup in sectors */
- uint16_t root_flags; /**< If the root is mounted readonly */
- uint16_t syssize; /**< obsolete */
- uint16_t swap_dev; /**< obsolete */
- uint16_t ram_size; /**< obsolete */
- uint16_t vid_mode; /**< Video mode control */
- uint16_t root_dev; /**< Default root device number */
- uint16_t boot_flag; /**< 0xAA55 magic number */
-
- /* second sector of the image */
- uint16_t jump; /**< Jump instruction (this is code!) */
- uint32_t header; /**< Magic signature "HdrS" */
- uint16_t version; /**< Boot protocol version supported */
- uint32_t realmode_swtch; /**< Boot loader hook */
- uint16_t start_sys; /**< The load-low segment (obsolete) */
- uint16_t kernel_version; /**< Points to kernel version string */
- uint8_t type_of_loader; /**< Boot loader identifier */
- uint8_t loadflags; /**< Boot protocol option flags */
- uint16_t setup_move_size; /**< Move to high memory size */
- uint32_t code32_start; /**< Boot loader hook */
- uint32_t ramdisk_image; /**< initrd load address */
- uint32_t ramdisk_size; /**< initrd size */
- uint32_t bootsect_kludge; /**< obsolete */
- uint16_t heap_end_ptr; /**< Free memory after setup end */
- uint8_t ext_loader_ver; /**< boot loader's extension of the version number */
- uint8_t ext_loader_type; /**< boot loader's extension of its type */
- uint32_t cmd_line_ptr; /**< Points to the kernel command line */
- uint32_t initrd_addr_max; /**< Highest address for initrd */
- uint32_t kernel_alignment; /**< Alignment unit required by the kernel */
- uint8_t relocatable_kernel; /** */
- uint8_t min_alignment; /** */
- uint16_t xloadflags; /** */
- uint32_t cmdline_size; /** */
- uint32_t hardware_subarch; /** */
- uint64_t hardware_subarch_data; /** */
- uint32_t payload_offset; /** */
- uint32_t payload_length; /** */
- uint64_t setup_data; /** */
- uint64_t pref_address; /** */
- uint32_t init_size; /** */
- uint32_t handover_offset; /** */
-} __attribute__ ((packed));
+#include "image.h"
+#include "setup_header.h"
static void *efi_read_file(const char *file, size_t *size)
{
@@ -85,10 +38,6 @@ static void *efi_read_file(const char *file, size_t *size)
char *buf;
ssize_t ret;
- buf = read_file(file, size);
- if (buf || errno != ENOMEM)
- return buf;
-
ret = stat(file, &s);
if (ret)
return NULL;
@@ -122,8 +71,8 @@ static void efi_free_file(void *_mem, size_t size)
BS->free_pages(mem, DIV_ROUND_UP(size, EFI_PAGE_SIZE));
}
-static int efi_load_image(const char *file, struct efi_loaded_image **loaded_image,
- efi_handle_t *h)
+int efi_load_image(const char *file, struct efi_loaded_image **loaded_image,
+ efi_handle_t *h)
{
void *exe;
size_t size;
@@ -158,10 +107,7 @@ static int efi_load_image(const char *file, struct efi_loaded_image **loaded_ima
static bool is_linux_image(enum filetype filetype, const void *base)
{
- const struct linux_kernel_header *hdr = base;
-
- if (IS_ENABLED(CONFIG_X86) &&
- hdr->boot_flag == 0xAA55 && hdr->header == 0x53726448)
+ if (IS_ENABLED(CONFIG_X86) && is_x86_setup_header(base))
return true;
if (IS_ENABLED(CONFIG_ARM64) &&
@@ -171,18 +117,13 @@ static bool is_linux_image(enum filetype filetype, const void *base)
return false;
}
-static int efi_execute_image(enum filetype filetype, const char *file)
+int efi_execute_image(efi_handle_t handle,
+ struct efi_loaded_image *loaded_image,
+ enum filetype filetype)
{
- efi_handle_t handle;
- struct efi_loaded_image *loaded_image;
efi_status_t efiret;
const char *options;
bool is_driver;
- int ret;
-
- ret = efi_load_image(file, &loaded_image, &handle);
- if (ret)
- return ret;
is_driver = (loaded_image->image_code_type == EFI_BOOT_SERVICES_CODE) ||
(loaded_image->image_code_type == EFI_RUNTIME_SERVICES_CODE);
@@ -216,110 +157,17 @@ static int efi_execute_image(enum filetype filetype, const char *file)
return -efi_errno(efiret);
}
-typedef void(*handover_fn)(void *image, struct efi_system_table *table,
- struct linux_kernel_header *header);
-
-static inline void linux_efi_handover(efi_handle_t handle,
- struct linux_kernel_header *header)
-{
- handover_fn handover;
- uintptr_t addr;
-
- addr = header->code32_start + header->handover_offset;
- if (IS_ENABLED(CONFIG_X86_64))
- addr += 512;
-
- handover = efi_phys_to_virt(addr);
- handover(handle, efi_sys_table, header);
-}
-
-static int do_bootm_efi(struct image_data *data)
+static int efi_execute(struct binfmt_hook *b, char *file, int argc, char **argv)
{
- void *tmp;
- void *initrd = NULL;
- size_t size;
+ struct efi_loaded_image *loaded_image;
efi_handle_t handle;
int ret;
- const char *options;
- struct efi_loaded_image *loaded_image;
- struct linux_kernel_header *image_header, *boot_header;
- ret = efi_load_image(data->os_file, &loaded_image, &handle);
+ ret = efi_load_image(file, &loaded_image, &handle);
if (ret)
return ret;
- image_header = (struct linux_kernel_header *)loaded_image->image_base;
-
- if (image_header->boot_flag != 0xAA55 ||
- image_header->header != 0x53726448 ||
- image_header->version < 0x20b ||
- !image_header->relocatable_kernel) {
- pr_err("Not a valid kernel image!\n");
- BS->unload_image(handle);
- return -EINVAL;
- }
-
- boot_header = xmalloc(0x4000);
- memset(boot_header, 0, 0x4000);
- memcpy(boot_header, image_header, sizeof(*image_header));
-
- /* Refer to Linux kernel commit a27e292b8a54
- * ("Documentation/x86/boot: Reserve type_of_loader=13 for barebox")
- */
- boot_header->type_of_loader = 0x13;
-
- if (data->initrd_file) {
- tmp = read_file(data->initrd_file, &size);
- initrd = xmemalign(PAGE_SIZE, PAGE_ALIGN(size));
- memcpy(initrd, tmp, size);
- memset(initrd + size, 0, PAGE_ALIGN(size) - size);
- free(tmp);
- boot_header->ramdisk_image = efi_virt_to_phys(initrd);
- boot_header->ramdisk_size = PAGE_ALIGN(size);
- }
-
- options = linux_bootargs_get();
- if (options) {
- boot_header->cmd_line_ptr = efi_virt_to_phys(options);
- boot_header->cmdline_size = strlen(options);
- }
-
- boot_header->code32_start = efi_virt_to_phys(loaded_image->image_base +
- (image_header->setup_sects+1) * 512);
-
- if (bootm_verbose(data)) {
- printf("\nStarting kernel at 0x%p", loaded_image->image_base);
- if (data->initrd_file)
- printf(", initrd at 0x%08x",
- boot_header->ramdisk_image);
- printf("...\n");
- }
-
- if (data->dryrun) {
- BS->unload_image(handle);
- free(boot_header);
- free(initrd);
- return 0;
- }
-
- efi_set_variable_usec("LoaderTimeExecUSec", &efi_systemd_vendor_guid,
- ktime_to_us(ktime_get()));
-
- shutdown_barebox();
- linux_efi_handover(handle, boot_header);
-
- return 0;
-}
-
-static struct image_handler efi_handle_tr = {
- .name = "EFI Application",
- .bootm = do_bootm_efi,
- .filetype = filetype_exe,
-};
-
-static int efi_execute(struct binfmt_hook *b, char *file, int argc, char **argv)
-{
- return efi_execute_image(b->type, file);
+ return efi_execute_image(handle, loaded_image, b->type);
}
static struct binfmt_hook binfmt_efi_hook = {
@@ -352,13 +200,19 @@ static struct binfmt_hook binfmt_arm64_efi_hook = {
.hook = efi_execute,
};
+static struct binfmt_hook binfmt_x86_efi_hook = {
+ .type = filetype_x86_linux_image,
+ .hook = efi_execute,
+};
+
static int efi_register_image_handler(void)
{
- register_image_handler(&efi_handle_tr);
binfmt_register(&binfmt_efi_hook);
- if (IS_ENABLED(CONFIG_X86))
+ if (IS_ENABLED(CONFIG_X86)) {
register_image_handler(&non_efi_handle_linux_x86);
+ binfmt_register(&binfmt_x86_efi_hook);
+ }
if (IS_ENABLED(CONFIG_ARM64))
binfmt_register(&binfmt_arm64_efi_hook);
diff --git a/efi/payload/image.h b/efi/payload/image.h
new file mode 100644
index 000000000000..673b21db839a
--- /dev/null
+++ b/efi/payload/image.h
@@ -0,0 +1,14 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+#ifndef __EFI_PAYLOAD_IMAGE_H__
+#define __EFI_PAYLOAD_IMAGE_H__
+
+#include <efi/types.h>
+
+int efi_load_image(const char *file, struct efi_loaded_image **loaded_image,
+ efi_handle_t *h);
+
+int efi_execute_image(efi_handle_t handle,
+ struct efi_loaded_image *loaded_image,
+ enum filetype filetype);
+
+#endif
--git a/efi/payload/setup_header.h b/efi/payload/setup_header.h
new file mode 100644
index 000000000000..4f094b844415
--- /dev/null
+++ b/efi/payload/setup_header.h
@@ -0,0 +1,63 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+#ifndef __EFI_PAYLOAD_SETUP_HEADER_H__
+#define __EFI_PAYLOAD_SETUP_HEADER_H__
+
+#include <linux/types.h>
+
+struct x86_setup_header {
+ /* first sector of the image */
+ uint8_t code1[0x0020];
+ uint16_t cl_magic; /**< Magic number 0xA33F */
+ uint16_t cl_offset; /**< The offset of command line */
+ uint8_t code2[0x01F1 - 0x0020 - 2 - 2];
+ uint8_t setup_sects; /**< The size of the setup in sectors */
+ uint16_t root_flags; /**< If the root is mounted readonly */
+ uint16_t syssize; /**< obsolete */
+ uint16_t swap_dev; /**< obsolete */
+ uint16_t ram_size; /**< obsolete */
+ uint16_t vid_mode; /**< Video mode control */
+ uint16_t root_dev; /**< Default root device number */
+ uint16_t boot_flag; /**< 0xAA55 magic number */
+
+ /* second sector of the image */
+ uint16_t jump; /**< Jump instruction (this is code!) */
+ uint32_t header; /**< Magic signature "HdrS" */
+ uint16_t version; /**< Boot protocol version supported */
+ uint32_t realmode_swtch; /**< Boot loader hook */
+ uint16_t start_sys; /**< The load-low segment (obsolete) */
+ uint16_t kernel_version; /**< Points to kernel version string */
+ uint8_t type_of_loader; /**< Boot loader identifier */
+ uint8_t loadflags; /**< Boot protocol option flags */
+ uint16_t setup_move_size; /**< Move to high memory size */
+ uint32_t code32_start; /**< Boot loader hook */
+ uint32_t ramdisk_image; /**< initrd load address */
+ uint32_t ramdisk_size; /**< initrd size */
+ uint32_t bootsect_kludge; /**< obsolete */
+ uint16_t heap_end_ptr; /**< Free memory after setup end */
+ uint8_t ext_loader_ver; /**< boot loader's extension of the version number */
+ uint8_t ext_loader_type; /**< boot loader's extension of its type */
+ uint32_t cmd_line_ptr; /**< Points to the kernel command line */
+ uint32_t initrd_addr_max; /**< Highest address for initrd */
+ uint32_t kernel_alignment; /**< Alignment unit required by the kernel */
+ uint8_t relocatable_kernel; /** */
+ uint8_t min_alignment; /** */
+ uint16_t xloadflags; /** */
+ uint32_t cmdline_size; /** */
+ uint32_t hardware_subarch; /** */
+ uint64_t hardware_subarch_data; /** */
+ uint32_t payload_offset; /** */
+ uint32_t payload_length; /** */
+ uint64_t setup_data; /** */
+ uint64_t pref_address; /** */
+ uint32_t init_size; /** */
+ uint32_t handover_offset; /** */
+} __attribute__ ((packed));
+
+static inline bool is_x86_setup_header(const void *base)
+{
+ const struct x86_setup_header *hdr = base;
+
+ return hdr->boot_flag == 0xAA55 && hdr->header == 0x53726448;
+}
+
+#endif
diff --git a/include/filetype.h b/include/filetype.h
index 6f4a103df304..ff4d54ee3c45 100644
--- a/include/filetype.h
+++ b/include/filetype.h
@@ -67,6 +67,7 @@ enum filetype {
filetype_nxp_fspi_image,
filetype_zstd_compressed,
filetype_rockchip_rkss_image,
+ filetype_x86_linux_image,
filetype_max,
};
@@ -150,4 +151,9 @@ static inline bool is_riscv_linux_bootimage(const void *header)
return le32_to_cpup(header + 56) == 0x05435352;
}
+static inline bool is_x86_linux_bootimage(const void *header)
+{
+ return le32_to_cpup(header + 0x202) == 0x53726448;
+}
+
#endif /* __FILE_TYPE_H */
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 07/10] efi: payload: bootm: add support for efi stub boot
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (4 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 06/10] efi: payload: split image handling from legacy handover boot and add linux x86 image filetype chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 08/10] efi: payload: bootm: add support for fit image chalianis1
` (3 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis
From: Chali Anis <chalianis1@gmail.com>
Introduce support for booting Linux kernels with an EFI stub from the
barebox EFI payload. This includes:
- Loading the kernel image via EFI LoadImage/StartImage
- Installing the FDT into the EFI configuration table unless
EFI_FDT_FORCE is enabled
- Providing the initrd either through the Initrd Media GUID or
the initrd media protocol
- Registering image handlers for EFI applications, x86/ARM64 EFI
Linux kernels, and a fallback handler for non-EFI x86 Linux images
- Adding Kconfig options to control FDT forcing and initrd installation
This enables barebox EFI payloads to directly boot Linux kernels with
EFI stubs in a way compatible with the Linux EFI boot flow.
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
efi/payload/Kconfig | 6 +-
efi/payload/Makefile | 1 +
efi/payload/bootm.c | 219 +++++++++++++++++++++++++++++++++++++++++++
3 files changed, 225 insertions(+), 1 deletion(-)
create mode 100644 efi/payload/bootm.c
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
index d0a46704a6b9..e3a6a72d6a1c 100644
--- a/efi/payload/Kconfig
+++ b/efi/payload/Kconfig
@@ -27,7 +27,11 @@ config EFI_STUB
config EFI_HANDOVER_PROTOCOL
bool "EFI Handover protocol"
- default y
+ depends on !EFI_PAYLOAD_BOOTM
depends on X86
+config EFI_PAYLOAD_BOOTM
+ bool "EFI bootm protocol"
+ default !X86
+
endif
diff --git a/efi/payload/Makefile b/efi/payload/Makefile
index d8b577bf3e23..083728c53cb4 100644
--- a/efi/payload/Makefile
+++ b/efi/payload/Makefile
@@ -3,6 +3,7 @@
obj-y += init.o
obj-y += image.o
obj-$(CONFIG_EFI_HANDOVER_PROTOCOL) += handover.o
+obj-$(CONFIG_EFI_PAYLOAD_BOOTM) += bootm.o
obj-y += efi-initrd.o
obj-$(CONFIG_OFTREE) += fdt.o
bbenv-y += env-efi
diff --git a/efi/payload/bootm.c b/efi/payload/bootm.c
new file mode 100644
index 000000000000..d0e995be5d7c
--- /dev/null
+++ b/efi/payload/bootm.c
@@ -0,0 +1,219 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * image.c - barebox EFI payload support
+ *
+ * Copyright (c) 2014 Sascha Hauer <s.hauer@pengutronix.de>, Pengutronix
+ */
+
+#define pr_fmt(fmt) "efi-bootm: " fmt
+
+#include <clock.h>
+#include <common.h>
+#include <linux/sizes.h>
+#include <linux/ktime.h>
+#include <memory.h>
+#include <command.h>
+#include <magicvar.h>
+#include <init.h>
+#include <driver.h>
+#include <io.h>
+#include <efi.h>
+#include <malloc.h>
+#include <string.h>
+#include <linux/err.h>
+#include <boot.h>
+#include <bootm.h>
+#include <fs.h>
+#include <libfile.h>
+#include <binfmt.h>
+#include <wchar.h>
+#include <image-fit.h>
+#include <efi/efi-payload.h>
+#include <efi/efi-device.h>
+
+#include "image.h"
+#include "setup_header.h"
+
+static int efi_load_os(struct image_data *data,
+ struct efi_loaded_image **loaded_image,
+ efi_handle_t *handle)
+{
+ return efi_load_image(data->os_file, loaded_image, handle);
+}
+
+static int efi_load_ramdisk(struct image_data *data, void **initrd)
+{
+ unsigned long initrd_size;
+ void *initrd_mem;
+ int ret;
+
+ if (!data->initrd_file)
+ return 0;
+
+ pr_info("Loading ramdisk from '%s'\n", data->initrd_file);
+
+ initrd_mem = read_file(data->initrd_file, &initrd_size);
+ if (!initrd_mem) {
+ ret = -errno;
+ pr_err("Failed to read initrd from file '%s': %m\n",
+ data->initrd_file);
+ return ret;
+ }
+
+ ret = efi_initrd_register(initrd_mem, initrd_size);
+ if (ret) {
+ pr_err("Failed to register initrd: %pe\n", ERR_PTR(ret));
+ goto free_mem;
+ }
+
+ *initrd = initrd_mem;
+
+ return 0;
+
+free_mem:
+ free(initrd);
+
+ return ret;
+}
+
+static int efi_load_fdt(struct image_data *data, void **fdt)
+{
+ efi_physical_addr_t mem;
+ efi_status_t efiret;
+ void *of_tree, *vmem;
+ unsigned long of_size;
+ int ret;
+
+ if (!data->oftree_file)
+ return 0;
+
+ pr_info("Loading devicetree from '%s'\n", data->oftree_file);
+
+ of_tree = read_file(data->oftree_file, &of_size);
+ if (!of_tree) {
+ ret = -errno;
+ pr_err("Failed to read oftree: %m\n");
+ return ret;
+ }
+
+ efiret = BS->allocate_pages(EFI_ALLOCATE_ANY_PAGES,
+ EFI_ACPI_RECLAIM_MEMORY,
+ DIV_ROUND_UP(SZ_2M, EFI_PAGE_SIZE), &mem);
+ if (EFI_ERROR(efiret)) {
+ pr_err("Failed to allocate pages for FDT: %s\n", efi_strerror(efiret));
+ goto free_mem;
+ }
+
+ vmem = efi_phys_to_virt(mem);
+ memcpy(vmem, of_tree, of_size);
+
+ efiret = BS->install_configuration_table(&efi_fdt_guid, vmem);
+ if (EFI_ERROR(efiret)) {
+ pr_err("Failed to install FDT: %s\n", efi_strerror(efiret));
+ goto free_efi_mem;
+ }
+
+ *fdt = vmem;
+ return 0;
+
+free_efi_mem:
+ BS->free_pages(mem, DIV_ROUND_UP(SZ_2M, EFI_PAGE_SIZE));
+free_mem:
+ free(of_tree);
+ return -efi_errno(efiret);
+}
+
+static void efi_unload_fdt(void *fdt)
+{
+ if (!fdt)
+ return;
+
+ BS->install_configuration_table(&efi_fdt_guid, NULL);
+ BS->free_pages(efi_virt_to_phys(fdt), SZ_2M);
+}
+
+static int do_bootm_efi_stub(struct image_data *data)
+{
+ struct efi_loaded_image *loaded_image;
+ void *fdt = NULL, *initrd = NULL;
+ efi_handle_t handle;
+ enum filetype type;
+ int ret;
+
+ ret = efi_load_os(data, &loaded_image, &handle);
+ if (ret)
+ return ret;
+
+ ret = efi_load_fdt(data, &fdt);
+ if (ret)
+ goto unload_os;
+
+ ret = efi_load_ramdisk(data, &initrd);
+ if (ret)
+ goto unload_oftree;
+
+ type = file_detect_type(loaded_image->image_base, PAGE_SIZE);
+ ret = efi_execute_image(handle, loaded_image, type);
+ if (ret)
+ goto unload_ramdisk;
+
+ return 0;
+
+unload_ramdisk:
+ if (initrd)
+ efi_initrd_unregister();
+unload_oftree:
+ efi_unload_fdt(fdt);
+unload_os:
+ BS->unload_image(handle);
+
+ return ret;
+}
+
+static int efi_app_execute(struct image_data *data)
+{
+ struct efi_loaded_image *loaded_image;
+ efi_handle_t handle;
+ enum filetype type;
+ int ret;
+
+ ret = efi_load_image(data->os_file, &loaded_image, &handle);
+ if (ret)
+ return ret;
+
+ type = file_detect_type(loaded_image->image_base, PAGE_SIZE);
+
+ return efi_execute_image(handle, loaded_image, type);
+}
+
+static struct image_handler efi_app_handle_tr = {
+ .name = "EFI Application",
+ .bootm = efi_app_execute,
+ .filetype = filetype_exe,
+};
+
+static struct image_handler efi_x86_linux_handle_tr = {
+ .name = "EFI X86 Linux kernel",
+ .bootm = do_bootm_efi_stub,
+ .filetype = filetype_x86_linux_image,
+};
+
+static struct image_handler efi_arm64_handle_tr = {
+ .name = "EFI ARM64 Linux kernel",
+ .bootm = do_bootm_efi_stub,
+ .filetype = filetype_arm64_efi_linux_image,
+};
+
+static int efi_register_bootm_handler(void)
+{
+ register_image_handler(&efi_app_handle_tr);
+
+ if (IS_ENABLED(CONFIG_X86))
+ register_image_handler(&efi_x86_linux_handle_tr);
+
+ if (IS_ENABLED(CONFIG_ARM64))
+ register_image_handler(&efi_arm64_handle_tr);
+
+ return 0;
+}
+late_efi_initcall(efi_register_bootm_handler);
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 08/10] efi: payload: bootm: add support for fit image
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (5 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 07/10] efi: payload: bootm: add support for efi stub boot chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 09/10] efi: payload: make selectable without COMPILE_TEST chalianis1
` (2 subsequent siblings)
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Ahmad Fatoum, Chali Anis
From: Ahmad Fatoum <a.fatoum@barebox.org>
Extend the EFI payload boot flow to support loading kernel, initrd,
and devicetree directly from a FIT image. When a FIT is present,
the loader extracts the relevant subimages ("kernel", "ramdisk",
and "fdt") also support falling back to external files when possible.
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
efi/payload/Kconfig | 1 +
efi/payload/bootm.c | 125 ++++++++++++++++++++++++++++++++++++--------
2 files changed, 104 insertions(+), 22 deletions(-)
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
index e3a6a72d6a1c..4fb866210a69 100644
--- a/efi/payload/Kconfig
+++ b/efi/payload/Kconfig
@@ -32,6 +32,7 @@ config EFI_HANDOVER_PROTOCOL
config EFI_PAYLOAD_BOOTM
bool "EFI bootm protocol"
+ select BOOTM_FITIMAGE
default !X86
endif
diff --git a/efi/payload/bootm.c b/efi/payload/bootm.c
index d0e995be5d7c..3e9ccd42bf7f 100644
--- a/efi/payload/bootm.c
+++ b/efi/payload/bootm.c
@@ -34,11 +34,74 @@
#include "image.h"
#include "setup_header.h"
+static bool ramdisk_is_fit(struct image_data *data)
+{
+ struct stat st;
+
+ if (bootm_signed_images_are_forced())
+ return true;
+
+ if (data->initrd_file) {
+ if (!stat(data->initrd_file, &st) && st.st_size > 0)
+ return false;
+ }
+
+ return data->os_fit ? fit_has_image(data->os_fit,
+ data->fit_config, "ramdisk") > 0 : false;
+}
+
+static bool fdt_is_fit(struct image_data *data)
+{
+ struct stat st;
+
+ if (bootm_signed_images_are_forced())
+ return true;
+
+ if (data->oftree_file) {
+ if (!stat(data->oftree_file, &st) && st.st_size > 0)
+ return false;
+ }
+
+ return data->os_fit ? fit_has_image(data->os_fit,
+ data->fit_config, "fdt") > 0 : false;
+}
+
static int efi_load_os(struct image_data *data,
struct efi_loaded_image **loaded_image,
efi_handle_t *handle)
{
- return efi_load_image(data->os_file, loaded_image, handle);
+ efi_status_t efiret;
+ efi_handle_t h;
+
+ if (!data->os_fit)
+ return efi_load_image(data->os_file, loaded_image, handle);
+
+ if (!data->fit_kernel)
+ return -ENOENT;
+
+ efiret = BS->load_image(false, efi_parent_image, efi_device_path,
+ (void *)data->fit_kernel, data->fit_kernel_size, &h);
+ if (EFI_ERROR(efiret)) {
+ pr_err("failed to LoadImage: %s\n", efi_strerror(efiret));
+ goto out_mem;
+ };
+
+ efiret = BS->open_protocol(h, &efi_loaded_image_protocol_guid,
+ (void **)loaded_image, efi_parent_image,
+ NULL, EFI_OPEN_PROTOCOL_GET_PROTOCOL);
+ if (EFI_ERROR(efiret)) {
+ pr_err("failed to OpenProtocol: %s\n", efi_strerror(efiret));
+ goto out_unload;
+ }
+
+ *handle = h;
+
+ return 0;
+
+out_unload:
+ BS->unload_image(h);
+out_mem:
+ return -efi_errno(efiret);
}
static int efi_load_ramdisk(struct image_data *data, void **initrd)
@@ -47,17 +110,26 @@ static int efi_load_ramdisk(struct image_data *data, void **initrd)
void *initrd_mem;
int ret;
- if (!data->initrd_file)
- return 0;
-
- pr_info("Loading ramdisk from '%s'\n", data->initrd_file);
-
- initrd_mem = read_file(data->initrd_file, &initrd_size);
- if (!initrd_mem) {
- ret = -errno;
- pr_err("Failed to read initrd from file '%s': %m\n",
- data->initrd_file);
- return ret;
+ if (ramdisk_is_fit(data)) {
+ ret = fit_open_image(data->os_fit, data->fit_config, "ramdisk",
+ (const void **)&initrd_mem, &initrd_size);
+ if (ret) {
+ pr_err("Cannot open ramdisk image in FIT image: %m\n");
+ return ret;
+ }
+ } else {
+ if (!data->initrd_file)
+ return 0;
+
+ pr_info("Loading ramdisk from '%s'\n", data->initrd_file);
+
+ initrd_mem = read_file(data->initrd_file, &initrd_size);
+ if (!initrd_mem) {
+ ret = -errno;
+ pr_err("Failed to read initrd from file '%s': %m\n",
+ data->initrd_file);
+ return ret;
+ }
}
ret = efi_initrd_register(initrd_mem, initrd_size);
@@ -84,16 +156,25 @@ static int efi_load_fdt(struct image_data *data, void **fdt)
unsigned long of_size;
int ret;
- if (!data->oftree_file)
- return 0;
-
- pr_info("Loading devicetree from '%s'\n", data->oftree_file);
-
- of_tree = read_file(data->oftree_file, &of_size);
- if (!of_tree) {
- ret = -errno;
- pr_err("Failed to read oftree: %m\n");
- return ret;
+ if (fdt_is_fit(data)) {
+ ret = fit_open_image(data->os_fit, data->fit_config, "fdt",
+ (const void **)&of_tree, &of_size);
+ if (ret) {
+ pr_err("Cannot open FDT image in FIT image: %m\n");
+ return ret;
+ }
+ } else {
+ if (!data->oftree_file)
+ return 0;
+
+ pr_info("Loading devicetree from '%s'\n", data->oftree_file);
+
+ of_tree = read_file(data->oftree_file, &of_size);
+ if (!of_tree) {
+ ret = -errno;
+ pr_err("Failed to read oftree: %m\n");
+ return ret;
+ }
}
efiret = BS->allocate_pages(EFI_ALLOCATE_ANY_PAGES,
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 09/10] efi: payload: make selectable without COMPILE_TEST
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (6 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 08/10] efi: payload: bootm: add support for fit image chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 0:59 ` [PATCH v2 10/10] ARM: efi: add a generic defconfig for v8 efi payload chalianis1
2025-10-07 10:15 ` [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols Sascha Hauer
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Ahmad Fatoum, Chali Anis
From: Ahmad Fatoum <a.fatoum@barebox.org>
Now that the barebox EFI payload has support for a non-x86 boot method,
let's drop the COMPILE_TEST dependency.
Signed-off-by: Chali Anis <chalianis1@gmail.com>
Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
---
efi/payload/Kconfig | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/efi/payload/Kconfig b/efi/payload/Kconfig
index 4fb866210a69..3b4a16e1e80c 100644
--- a/efi/payload/Kconfig
+++ b/efi/payload/Kconfig
@@ -4,7 +4,7 @@ config HAVE_EFI_PAYLOAD
bool
config EFI_PAYLOAD
- bool "Build as EFI payload" if COMPILE_TEST
+ bool "Build as EFI payload"
depends on HAVE_EFI_PAYLOAD
select PBL_FULLY_PIC if ARM64
select EFI
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH v2 10/10] ARM: efi: add a generic defconfig for v8 efi payload
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (7 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 09/10] efi: payload: make selectable without COMPILE_TEST chalianis1
@ 2025-10-07 0:59 ` chalianis1
2025-10-07 10:15 ` [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols Sascha Hauer
9 siblings, 0 replies; 13+ messages in thread
From: chalianis1 @ 2025-10-07 0:59 UTC (permalink / raw)
To: s.hauer; +Cc: barebox, Chali Anis
From: Chali Anis <chalianis1@gmail.com>
The multi_v8_efi_defconfig enables a lot of drivers that are not needed
for an EFI payload. Therefore add a minimal EFI-only config.
Signed-off-by: Chali Anis <chalianis1@gmail.com>
---
arch/arm/configs/efi_v8_defconfig | 212 ++++++++++++++++++++++++++++++
1 file changed, 212 insertions(+)
create mode 100644 arch/arm/configs/efi_v8_defconfig
diff --git a/arch/arm/configs/efi_v8_defconfig b/arch/arm/configs/efi_v8_defconfig
new file mode 100644
index 000000000000..5f946dd51d4a
--- /dev/null
+++ b/arch/arm/configs/efi_v8_defconfig
@@ -0,0 +1,212 @@
+CONFIG_64BIT=y
+CONFIG_ARM_OPTIMZED_STRING_FUNCTIONS=y
+CONFIG_ARM_PSCI_CLIENT=y
+CONFIG_NAME="efi_v8_defconfig"
+CONFIG_MMU=y
+CONFIG_MALLOC_SIZE=0x0
+CONFIG_KALLSYMS=y
+CONFIG_PROMPT="barebox> "
+CONFIG_PROMPT_HUSH_PS2="y"
+CONFIG_HUSH_FANCY_PROMPT=y
+CONFIG_AUTO_COMPLETE=y
+CONFIG_MENU=y
+CONFIG_BOOTM_SHOW_TYPE=y
+CONFIG_BOOTM_VERBOSE=y
+CONFIG_BOOTM_INITRD=y
+CONFIG_BOOTM_AIMAGE=y
+CONFIG_BLSPEC=y
+CONFIG_CONSOLE_ALLOW_COLOR=y
+CONFIG_PBL_CONSOLE=y
+CONFIG_CONSOLE_RATP=y
+CONFIG_PARTITION_DISK_EFI=y
+CONFIG_DEFAULT_ENVIRONMENT_GENERIC_NEW=y
+CONFIG_STATE=y
+CONFIG_BOOTCHOOSER=y
+CONFIG_RESET_SOURCE=y
+CONFIG_MACHINE_ID=y
+CONFIG_FASTBOOT_SPARSE=y
+CONFIG_EFI_PAYLOAD=y
+CONFIG_CMD_DMESG=y
+CONFIG_LONGHELP=y
+CONFIG_CMD_IOMEM=y
+CONFIG_CMD_IMD=y
+CONFIG_CMD_MEMINFO=y
+CONFIG_CMD_ARM_MMUINFO=y
+CONFIG_CMD_REGULATOR=y
+CONFIG_CMD_BFETCH=y
+CONFIG_CMD_MMC_EXTCSD=y
+CONFIG_CMD_POLLER=y
+CONFIG_CMD_SLICE=y
+CONFIG_CMD_GO=y
+CONFIG_CMD_LOADB=y
+CONFIG_CMD_RESET=y
+CONFIG_CMD_BOOTCHOOSER=y
+CONFIG_CMD_PARTITION=y
+CONFIG_CMD_FINDMNT=y
+CONFIG_CMD_EXPORT=y
+CONFIG_CMD_DEFAULTENV=y
+CONFIG_CMD_LOADENV=y
+CONFIG_CMD_PRINTENV=y
+CONFIG_CMD_MAGICVAR=y
+CONFIG_CMD_MAGICVAR_HELP=y
+CONFIG_CMD_SAVEENV=y
+CONFIG_CMD_FILETYPE=y
+CONFIG_CMD_LN=y
+CONFIG_CMD_MD5SUM=y
+CONFIG_CMD_SHA1SUM=y
+CONFIG_CMD_SHA224SUM=y
+CONFIG_CMD_SHA256SUM=y
+CONFIG_CMD_UNCOMPRESS=y
+CONFIG_CMD_LET=y
+CONFIG_CMD_MSLEEP=y
+CONFIG_CMD_READF=y
+CONFIG_CMD_SLEEP=y
+CONFIG_CMD_DHCP=y
+CONFIG_CMD_MIITOOL=y
+CONFIG_CMD_PING=y
+CONFIG_CMD_TFTP=y
+CONFIG_CMD_ECHO_E=y
+CONFIG_CMD_EDIT=y
+CONFIG_CMD_MENU=y
+CONFIG_CMD_MENU_MANAGEMENT=y
+CONFIG_CMD_MENUTREE=y
+CONFIG_CMD_SPLASH=y
+CONFIG_CMD_FBTEST=y
+CONFIG_CMD_READLINE=y
+CONFIG_CMD_TIMEOUT=y
+CONFIG_CMD_CRC=y
+CONFIG_CMD_CRC_CMP=y
+CONFIG_CMD_MEMTEST=y
+CONFIG_CMD_MM=y
+CONFIG_CMD_CLK=y
+CONFIG_CMD_DETECT=y
+CONFIG_CMD_FLASH=y
+CONFIG_CMD_LED=y
+CONFIG_CMD_POWEROFF=y
+CONFIG_CMD_SMC=y
+CONFIG_CMD_LED_TRIGGER=y
+CONFIG_CMD_USBGADGET=y
+CONFIG_CMD_WD=y
+CONFIG_CMD_LOGIN=y
+CONFIG_CMD_PASSWD=y
+CONFIG_CMD_BAREBOX_UPDATE=y
+CONFIG_CMD_FIRMWARELOAD=y
+CONFIG_CMD_OF_DIFF=y
+CONFIG_CMD_OF_NODE=y
+CONFIG_CMD_OF_PROPERTY=y
+CONFIG_CMD_OF_DISPLAY_TIMINGS=y
+CONFIG_CMD_OF_FIXUP_STATUS=y
+CONFIG_CMD_OF_OVERLAY=y
+CONFIG_CMD_OFTREE=y
+CONFIG_CMD_TIME=y
+CONFIG_NET=y
+CONFIG_NET_NETCONSOLE=y
+CONFIG_NET_SNTP=y
+CONFIG_NET_FASTBOOT=y
+CONFIG_NET_9P=y
+CONFIG_NET_9P_VIRTIO=y
+CONFIG_DEEP_PROBE_DEFAULT=y
+CONFIG_OF_BAREBOX_DRIVERS=y
+CONFIG_OF_BAREBOX_ENV_IN_FS=y
+CONFIG_OF_OVERLAY_LIVE=y
+CONFIG_SERIAL_DEV_BUS=y
+CONFIG_SERIAL_AMBA_PL011=y
+CONFIG_DRIVER_SERIAL_EFI_STDIO=y
+CONFIG_DRIVER_SERIAL_NS16550=y
+CONFIG_DRIVER_SERIAL_CADENCE=y
+CONFIG_VIRTIO_CONSOLE=y
+CONFIG_DRIVER_NET_FSL_ENETC=y
+CONFIG_DRIVER_NET_FSL_FMAN=y
+CONFIG_DRIVER_NET_VIRTIO=y
+CONFIG_DP83867_PHY=y
+CONFIG_MICREL_PHY=y
+CONFIG_REALTEK_PHY=y
+CONFIG_SMSC_PHY=y
+CONFIG_NET_DSA_MV88E6XXX=y
+CONFIG_MDIO_BITBANG=y
+CONFIG_NET_USB=y
+CONFIG_NET_USB_ASIX=y
+CONFIG_USB_NET_AX88179_178A=y
+CONFIG_NET_USB_SMSC95XX=y
+CONFIG_NET_USB_RTL8152=y
+CONFIG_DRIVER_SPI_FSL_QUADSPI=y
+CONFIG_I2C=y
+CONFIG_I2C_EFI=y
+CONFIG_MTD=y
+CONFIG_MTD_CONCAT=y
+CONFIG_MTD_M25P80=y
+CONFIG_DRIVER_CFI=y
+CONFIG_CFI_BUFFER_WRITE=y
+CONFIG_VIRTIO_BLK=y
+CONFIG_USB_HOST=y
+CONFIG_USB_DWC3=y
+CONFIG_USB_DWC3_DUAL_ROLE=y
+CONFIG_USB_EHCI=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_ONBOARD_DEV=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_SERIAL=y
+CONFIG_USB_GADGET_FASTBOOT=y
+CONFIG_USB_GADGET_MASS_STORAGE=y
+CONFIG_VIDEO=y
+CONFIG_FRAMEBUFFER_CONSOLE=y
+CONFIG_DRIVER_VIDEO_EFI_GOP=y
+CONFIG_DRIVER_VIDEO_BOCHS_PCI=y
+CONFIG_SOUND=y
+CONFIG_MCI=y
+CONFIG_MCI_MMC_BOOT_PARTITIONS=y
+CONFIG_MCI_DW=y
+CONFIG_MCI_SUNXI_SMHC=y
+CONFIG_MCI_ROCKCHIP_DWCMSHC=y
+CONFIG_MCI_ARASAN=y
+CONFIG_MCI_AM654=y
+CONFIG_COMMON_CLK=y
+CONFIG_COMMON_CLK_SCMI=y
+CONFIG_CLOCKSOURCE_EFI=y
+CONFIG_RAVE_SP_CORE=y
+CONFIG_MFD_RK808=y
+CONFIG_LED=y
+CONFIG_LED_TRIGGERS=y
+CONFIG_EEPROM_AT25=y
+CONFIG_VIRTIO_INPUT=y
+CONFIG_WATCHDOG=y
+CONFIG_WATCHDOG_POLLER=y
+CONFIG_WATCHDOG_EFI=y
+CONFIG_WATCHDOG_DW=y
+CONFIG_RAVE_SP_WATCHDOG=y
+CONFIG_HWRNG=y
+CONFIG_HW_RANDOM_VIRTIO=y
+CONFIG_HW_RANDOM_EFI=y
+CONFIG_DMADEVICES=y
+CONFIG_PINCTRL_SINGLE=y
+CONFIG_REGULATOR=y
+CONFIG_REGULATOR_ARM_SCMI=y
+CONFIG_REGULATOR_RK808=y
+CONFIG_RESET_IMX7=y
+CONFIG_PCI_ECAM_GENERIC=y
+CONFIG_RTC_CLASS=y
+CONFIG_ARM_SCMI_PROTOCOL=y
+CONFIG_GENERIC_PHY=y
+CONFIG_USB_NOP_XCEIV=y
+CONFIG_VIRTIO_MMIO=y
+CONFIG_VIRTIO_PCI=y
+CONFIG_MAILBOX=y
+CONFIG_FS_CRAMFS=y
+CONFIG_FS_EXT4=y
+CONFIG_FS_TFTP=y
+CONFIG_FS_NFS=y
+CONFIG_9P_FS=y
+CONFIG_9P_FS_WRITE=y
+CONFIG_FS_EFI=y
+CONFIG_FS_EFIVARFS=y
+CONFIG_FS_FAT=y
+CONFIG_FS_FAT_WRITE=y
+CONFIG_FS_BPKFS=y
+CONFIG_FS_UIMAGEFS=y
+CONFIG_FS_PSTORE=y
+CONFIG_FS_PSTORE_CONSOLE=y
+CONFIG_FS_RATP=y
+CONFIG_DIGEST_SHA1_ARM64_CE=y
+CONFIG_DIGEST_SHA256_ARM64_CE=y
+CONFIG_LZO_DECOMPRESS=y
+# CONFIG_MISSING_FIRMWARE_ERROR is not set
--
2.34.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
` (8 preceding siblings ...)
2025-10-07 0:59 ` [PATCH v2 10/10] ARM: efi: add a generic defconfig for v8 efi payload chalianis1
@ 2025-10-07 10:15 ` Sascha Hauer
9 siblings, 0 replies; 13+ messages in thread
From: Sascha Hauer @ 2025-10-07 10:15 UTC (permalink / raw)
To: chalianis1; +Cc: barebox, Ahmad Fatoum
On Mon, 06 Oct 2025 20:59:46 -0400, chalianis1@gmail.com wrote:
> We are already keeping different directories for payload and common EFI
> support. In preparation for adding more payload-specific config options,
> move the existing ones into their own Kconfig file.
>
>
Applied, thanks!
[01/10] efi: payload: split out payload Kconfig symbols
https://git.pengutronix.de/cgit/barebox/commit/?id=4ba4e23652ea (link may not be stable)
[02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool
https://git.pengutronix.de/cgit/barebox/commit/?id=4fd2c32546d6 (link may not be stable)
[03/10] tlsf: support on-demand requesting memory from external store
https://git.pengutronix.de/cgit/barebox/commit/?id=7e43bc6e8f8d (link may not be stable)
[04/10] efi: payload: add support for EFI initrd media protocol
https://git.pengutronix.de/cgit/barebox/commit/?id=9ef8a6e873dc (link may not be stable)
[05/10] efi: payload: earlymem: allocate only the barebox needs in term of memory
https://git.pengutronix.de/cgit/barebox/commit/?id=ca4d3c34699c (link may not be stable)
[06/10] efi: payload: split image handling from legacy handover boot and add linux x86 image filetype
https://git.pengutronix.de/cgit/barebox/commit/?id=24d09817e712 (link may not be stable)
[07/10] efi: payload: bootm: add support for efi stub boot
https://git.pengutronix.de/cgit/barebox/commit/?id=d1485062fc94 (link may not be stable)
[08/10] efi: payload: bootm: add support for fit image
https://git.pengutronix.de/cgit/barebox/commit/?id=cce4c24a1e85 (link may not be stable)
[09/10] efi: payload: make selectable without COMPILE_TEST
https://git.pengutronix.de/cgit/barebox/commit/?id=063da7a655c1 (link may not be stable)
[10/10] ARM: efi: add a generic defconfig for v8 efi payload
https://git.pengutronix.de/cgit/barebox/commit/?id=487cd4e91a99 (link may not be stable)
Best regards,
--
Sascha Hauer <s.hauer@pengutronix.de>
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store
2025-10-07 0:59 ` [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store chalianis1
@ 2025-10-07 13:42 ` Sascha Hauer
2025-10-07 14:34 ` Ahmad Fatoum
0 siblings, 1 reply; 13+ messages in thread
From: Sascha Hauer @ 2025-10-07 13:42 UTC (permalink / raw)
To: chalianis1; +Cc: barebox, Ahmad Fatoum
On Mon, Oct 06, 2025 at 08:59:48PM -0400, chalianis1@gmail.com wrote:
> From: Chali Anis <chalianis1@gmail.com>
>
> barebox running under an operating system (or nearly one like UEFI) does
> not have control over all the memory and should not hog too much memory
> upfront as that can interfere with other applications, e.g. EFI drivers
> or the EFI firmware itself.
>
> To accommodate this use case, allow TLSF to dynamically request more
> memory from an external store via tlsf_register_store().
>
> Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
> Signed-off-by: Chali Anis <chalianis1@gmail.com>
> ---
> common/tlsf.c | 29 ++++++++++++++++++++++++++++-
> include/tlsf.h | 1 +
> 2 files changed, 29 insertions(+), 1 deletion(-)
>
> diff --git a/common/tlsf.c b/common/tlsf.c
> index 4ee53a9b2f20..636b57b1c642 100644
> --- a/common/tlsf.c
> +++ b/common/tlsf.c
> @@ -159,6 +159,9 @@ typedef struct control_t
> /* Empty lists point at this block to indicate they are free. */
> block_header_t block_null;
>
> + void (*request_store)(tlsf_t, size_t);
> +
> +
This breaks compilation on 32bit platforms.
The reason is we have this directly under the definition of control_t:
tlsf_static_assert(sizeof(control_t) % ALIGN_SIZE == 0);
I fixed it up as follows.
It looks odd to me that we have to manually align the struct size each
time we add a field to this struct. Isn't there something better?
Sascha
---------------------------8<------------------------------
>From 11fcc69bbc41954d5e28a3b082dc39171bd6cdc0 Mon Sep 17 00:00:00 2001
From: Sascha Hauer <s.hauer@pengutronix.de>
Date: Tue, 7 Oct 2025 15:39:38 +0200
Subject: [PATCH] fixup! tlsf: support on-demand requesting memory from
external store
---
common/tlsf.c | 2 --
1 file changed, 2 deletions(-)
diff --git a/common/tlsf.c b/common/tlsf.c
index 636b57b1c6..c4ba8259b2 100644
--- a/common/tlsf.c
+++ b/common/tlsf.c
@@ -161,11 +161,9 @@ typedef struct control_t
void (*request_store)(tlsf_t, size_t);
-
/* Bitmaps for free lists. */
unsigned int fl_bitmap;
unsigned int sl_bitmap[FL_INDEX_COUNT];
- u32 : BYTES_TO_BITS(ALIGN_SIZE - sizeof(size_t));
/* Head of free lists. */
block_header_t* blocks[FL_INDEX_COUNT][SL_INDEX_COUNT];
--
2.47.3
--
Pengutronix e.K. | |
Steuerwalder Str. 21 | http://www.pengutronix.de/ |
31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store
2025-10-07 13:42 ` Sascha Hauer
@ 2025-10-07 14:34 ` Ahmad Fatoum
0 siblings, 0 replies; 13+ messages in thread
From: Ahmad Fatoum @ 2025-10-07 14:34 UTC (permalink / raw)
To: Sascha Hauer, chalianis1; +Cc: barebox, Ahmad Fatoum
On 10/7/25 3:42 PM, Sascha Hauer wrote:
> On Mon, Oct 06, 2025 at 08:59:48PM -0400, chalianis1@gmail.com wrote:
>> From: Chali Anis <chalianis1@gmail.com>
>>
>> barebox running under an operating system (or nearly one like UEFI) does
>> not have control over all the memory and should not hog too much memory
>> upfront as that can interfere with other applications, e.g. EFI drivers
>> or the EFI firmware itself.
>>
>> To accommodate this use case, allow TLSF to dynamically request more
>> memory from an external store via tlsf_register_store().
>>
>> Signed-off-by: Ahmad Fatoum <a.fatoum@barebox.org>
>> Signed-off-by: Chali Anis <chalianis1@gmail.com>
>> ---
>> common/tlsf.c | 29 ++++++++++++++++++++++++++++-
>> include/tlsf.h | 1 +
>> 2 files changed, 29 insertions(+), 1 deletion(-)
>>
>> diff --git a/common/tlsf.c b/common/tlsf.c
>> index 4ee53a9b2f20..636b57b1c642 100644
>> --- a/common/tlsf.c
>> +++ b/common/tlsf.c
>> @@ -159,6 +159,9 @@ typedef struct control_t
>> /* Empty lists point at this block to indicate they are free. */
>> block_header_t block_null;
>>
>> + void (*request_store)(tlsf_t, size_t);
>> +
>> +
>
> This breaks compilation on 32bit platforms.
>
> The reason is we have this directly under the definition of control_t:
>
> tlsf_static_assert(sizeof(control_t) % ALIGN_SIZE == 0);
>
> I fixed it up as follows.
Fixup looks good, thanks.
> It looks odd to me that we have to manually align the struct size each
> time we add a field to this struct. Isn't there something better?
Maybe we could hack something together with alignment or a union, but in
the end it would not be applicable to block_header_t, which is
intentionally overlayed in a misaligned manner as prev_phys_block is
part of the previous allocation...
The asserts at least work :-)
Cheers,
Ahmad
>
> Sascha
>
> ---------------------------8<------------------------------
> From 11fcc69bbc41954d5e28a3b082dc39171bd6cdc0 Mon Sep 17 00:00:00 2001
> From: Sascha Hauer <s.hauer@pengutronix.de>
> Date: Tue, 7 Oct 2025 15:39:38 +0200
> Subject: [PATCH] fixup! tlsf: support on-demand requesting memory from
> external store
>
> ---
> common/tlsf.c | 2 --
> 1 file changed, 2 deletions(-)
>
> diff --git a/common/tlsf.c b/common/tlsf.c
> index 636b57b1c6..c4ba8259b2 100644
> --- a/common/tlsf.c
> +++ b/common/tlsf.c
> @@ -161,11 +161,9 @@ typedef struct control_t
>
> void (*request_store)(tlsf_t, size_t);
>
> -
> /* Bitmaps for free lists. */
> unsigned int fl_bitmap;
> unsigned int sl_bitmap[FL_INDEX_COUNT];
> - u32 : BYTES_TO_BITS(ALIGN_SIZE - sizeof(size_t));
>
> /* Head of free lists. */
> block_header_t* blocks[FL_INDEX_COUNT][SL_INDEX_COUNT];
--
Pengutronix e.K. | |
Steuerwalder Str. 21 | http://www.pengutronix.de/ |
31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2025-10-07 14:35 UTC | newest]
Thread overview: 13+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2025-10-07 0:59 [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols chalianis1
2025-10-07 0:59 ` [PATCH v2 02/10] tlsf: move kasan_poison_shadow into tlsf_add_pool chalianis1
2025-10-07 0:59 ` [PATCH v2 03/10] tlsf: support on-demand requesting memory from external store chalianis1
2025-10-07 13:42 ` Sascha Hauer
2025-10-07 14:34 ` Ahmad Fatoum
2025-10-07 0:59 ` [PATCH v2 04/10] efi: payload: add support for EFI initrd media protocol chalianis1
2025-10-07 0:59 ` [PATCH v2 05/10] efi: payload: earlymem: allocate only the barebox needs in term of memory chalianis1
2025-10-07 0:59 ` [PATCH v2 06/10] efi: payload: split image handling from legacy handover boot and add linux x86 image filetype chalianis1
2025-10-07 0:59 ` [PATCH v2 07/10] efi: payload: bootm: add support for efi stub boot chalianis1
2025-10-07 0:59 ` [PATCH v2 08/10] efi: payload: bootm: add support for fit image chalianis1
2025-10-07 0:59 ` [PATCH v2 09/10] efi: payload: make selectable without COMPILE_TEST chalianis1
2025-10-07 0:59 ` [PATCH v2 10/10] ARM: efi: add a generic defconfig for v8 efi payload chalianis1
2025-10-07 10:15 ` [PATCH v2 01/10] efi: payload: split out payload Kconfig symbols Sascha Hauer
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox