summaryrefslogtreecommitdiff
path: root/arch
diff options
context:
space:
mode:
authorTom Rini <[email protected]>2026-03-18 18:36:50 -0600
committerTom Rini <[email protected]>2026-03-18 18:36:50 -0600
commiteb00c710508d09b2a3b9aca75dd18280f1304703 (patch)
treef91864725bde06d16a7243e0a539b28b03c0f125 /arch
parent28608c808774a39ec47d31353b141db547136e58 (diff)
parentdc88ac7681084b2aff8c3c4e1bb3e861451489a3 (diff)
Merge patch series "bootm: Clean up arch-specific, pre-OS clean-up"
Simon Glass <[email protected]> says: Each arch does something slightly different before booting the OS. Some archs even do different things depending on the CPU type. It is quite hard to know what actually happens in the final milliseconds before the OS boot. This series attempts to start cleaning up U-Boot in this area. The basic intent is to create a new bootm_final() function which can be called by all archs. It provides some flags for a couple of necessary variations but otherwise it is generic. All architectures are converted over to use this new function. board_quiesce_devices() is moved into bootm_final() so that all archs benefit from it. This series fixes a bug in device_remove() is fixed where removing a parent with specialised flags (e.g. DM_REMOVE_ACTIVE_ALL) could leave children activated, since they do not match the flags. This fixes is needed to avoid bootm_final() causing test failures on sandbox. Future work could take this a little further: - Convert EFI loader to use the same function - Improve comments for cleanup_before_linux() across architectures - Support fake-run tracing on all archs Link: https://lore.kernel.org/r/[email protected]
Diffstat (limited to 'arch')
-rw-r--r--arch/arc/lib/bootm.c8
-rw-r--r--arch/arm/lib/bootm.c50
-rw-r--r--arch/m68k/lib/bootm.c2
-rw-r--r--arch/microblaze/lib/bootm.c8
-rw-r--r--arch/mips/lib/bootm.c7
-rw-r--r--arch/nios2/lib/bootm.c2
-rw-r--r--arch/powerpc/lib/bootm.c7
-rw-r--r--arch/riscv/include/asm/u-boot-riscv.h1
-rw-r--r--arch/riscv/lib/bootm.c39
-rw-r--r--arch/sandbox/lib/bootm.c1
-rw-r--r--arch/sh/lib/bootm.c2
-rw-r--r--arch/x86/lib/bootm.c14
-rw-r--r--arch/xtensa/lib/bootm.c2
13 files changed, 25 insertions, 118 deletions
diff --git a/arch/arc/lib/bootm.c b/arch/arc/lib/bootm.c
index 91bce5235a5..91165a06a46 100644
--- a/arch/arc/lib/bootm.c
+++ b/arch/arc/lib/bootm.c
@@ -50,17 +50,13 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
{
ulong kernel_entry;
unsigned int r0, r2;
- int fake = (flag & BOOTM_STATE_OS_FAKE_GO);
-
kernel_entry = images->ep;
debug("## Transferring control to Linux (at address %08lx)...\n",
kernel_entry);
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
- printf("\nStarting kernel ...%s\n\n", fake ?
- "(fake run for tracing)" : "");
- bootstage_mark_name(BOOTSTAGE_ID_BOOTM_HANDOFF, "start_kernel");
+ bootm_final(flag);
if (CONFIG_IS_ENABLED(OF_LIBFDT) && images->ft_len) {
r0 = 2;
@@ -72,7 +68,7 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
cleanup_before_linux();
- if (!fake)
+ if (!(flag & BOOTM_STATE_OS_FAKE_GO))
board_jump_and_run(kernel_entry, r0, 0, r2);
}
diff --git a/arch/arm/lib/bootm.c b/arch/arm/lib/bootm.c
index 019eca95780..727b9c5ca5b 100644
--- a/arch/arm/lib/bootm.c
+++ b/arch/arm/lib/bootm.c
@@ -42,42 +42,6 @@ DECLARE_GLOBAL_DATA_PTR;
static struct tag *params;
-__weak void board_quiesce_devices(void)
-{
-}
-
-/**
- * announce_and_cleanup() - Print message and prepare for kernel boot
- *
- * @fake: non-zero to do everything except actually boot
- */
-static void announce_and_cleanup(int fake)
-{
- bootstage_mark_name(BOOTSTAGE_ID_BOOTM_HANDOFF, "start_kernel");
-#ifdef CONFIG_BOOTSTAGE_FDT
- bootstage_fdt_add_report();
-#endif
- bootstage_stash_default();
-#ifdef CONFIG_BOOTSTAGE_REPORT
- bootstage_report();
-#endif
-
- board_quiesce_devices();
-
- printf("\nStarting kernel ...%s\n\n", fake ?
- "(fake run for tracing)" : "");
- /*
- * Call remove function of all devices with a removal flag set.
- * This may be useful for last-stage operations, like cancelling
- * of DMA operation or releasing device internal buffers.
- * dm_remove_devices_active() ensures that vital devices are removed in
- * a second round.
- */
- dm_remove_devices_active();
-
- cleanup_before_linux();
-}
-
static void setup_start_tag (struct bd_info *bd)
{
params = (struct tag *)bd->bi_boot_params;
@@ -294,8 +258,6 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
{
void (*kernel_entry)(void *fdt_addr, void *res0, void *res1,
void *res2);
- int fake = (flag & BOOTM_STATE_OS_FAKE_GO);
-
kernel_entry = (void (*)(void *fdt_addr, void *res0, void *res1,
void *res2))images->ep;
@@ -303,9 +265,10 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
(ulong) kernel_entry);
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
- announce_and_cleanup(fake);
+ bootm_final(flag);
+ cleanup_before_linux();
- if (!fake) {
+ if (!(flag & BOOTM_STATE_OS_FAKE_GO)) {
#ifdef CONFIG_ARMV8_PSCI
armv8_setup_psci();
#endif
@@ -340,8 +303,6 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
char *s;
void (*kernel_entry)(int zero, int arch, uint params);
unsigned long r2;
- int fake = (flag & BOOTM_STATE_OS_FAKE_GO);
-
kernel_entry = (void (*)(int, int, uint))images->ep;
#ifdef CONFIG_CPU_V7M
ulong addr = (ulong)kernel_entry | 1;
@@ -366,14 +327,15 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
debug("## Transferring control to Linux (at address %08lx)" \
"...\n", (ulong) kernel_entry);
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
- announce_and_cleanup(fake);
+ bootm_final(flag);
+ cleanup_before_linux();
if (CONFIG_IS_ENABLED(OF_LIBFDT) && images->ft_len)
r2 = (unsigned long)images->ft_addr;
else
r2 = gd->bd->bi_boot_params;
- if (fake)
+ if (flag & BOOTM_STATE_OS_FAKE_GO)
return;
#ifdef CONFIG_ARMV7_NONSEC
diff --git a/arch/m68k/lib/bootm.c b/arch/m68k/lib/bootm.c
index 1fa112f8dbf..7d65f3ea1a8 100644
--- a/arch/m68k/lib/bootm.c
+++ b/arch/m68k/lib/bootm.c
@@ -62,6 +62,8 @@ int do_bootm_linux(int flag, struct bootm_info *bmi)
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
+ bootm_final(0);
+
/*
* Linux Kernel Parameters (passing board info data):
* sp+00: Ignore, side effect of using jsr to jump to kernel
diff --git a/arch/microblaze/lib/bootm.c b/arch/microblaze/lib/bootm.c
index 2410515f4ac..b54c902602f 100644
--- a/arch/microblaze/lib/bootm.c
+++ b/arch/microblaze/lib/bootm.c
@@ -26,8 +26,6 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
ulong dt = (ulong)images->ft_addr;
ulong rd_start = images->initrd_start;
ulong cmdline = images->cmdline_start;
- int fake = (flag & BOOTM_STATE_OS_FAKE_GO);
-
thekernel = (void (*)(char *, ulong, ulong))images->ep;
debug("## Transferring control to Linux (at address 0x%08lx) ",
@@ -36,13 +34,11 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
cmdline, rd_start, dt);
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
- printf("\nStarting kernel ...%s\n\n", fake ?
- "(fake run for tracing)" : "");
- bootstage_mark_name(BOOTSTAGE_ID_BOOTM_HANDOFF, "start_kernel");
+ bootm_final(flag);
flush_cache_all();
- if (!fake) {
+ if (!(flag & BOOTM_STATE_OS_FAKE_GO)) {
/*
* Linux Kernel Parameters (passing device tree):
* r5: pointer to command line
diff --git a/arch/mips/lib/bootm.c b/arch/mips/lib/bootm.c
index 87195100023..066c830f3fa 100644
--- a/arch/mips/lib/bootm.c
+++ b/arch/mips/lib/bootm.c
@@ -268,12 +268,7 @@ static void boot_jump_linux(struct bootm_headers *images)
if (CONFIG_IS_ENABLED(MALTA))
linux_extra = gd->ram_size;
-#if IS_ENABLED(CONFIG_BOOTSTAGE_FDT)
- bootstage_fdt_add_report();
-#endif
-#if IS_ENABLED(CONFIG_BOOTSTAGE_REPORT)
- bootstage_report();
-#endif
+ bootm_final(0);
if (CONFIG_IS_ENABLED(RESTORE_EXCEPTION_VECTOR_BASE))
trap_restore();
diff --git a/arch/nios2/lib/bootm.c b/arch/nios2/lib/bootm.c
index 294ebfb508b..6004e83bf0c 100644
--- a/arch/nios2/lib/bootm.c
+++ b/arch/nios2/lib/bootm.c
@@ -41,6 +41,8 @@ int do_bootm_linux(int flag, struct bootm_info *bmi)
if ((flag != 0) && (flag != BOOTM_STATE_OS_GO))
return 1;
+ bootm_final(0);
+
/* flushes data and instruction caches before calling the kernel */
disable_interrupts();
flush_dcache_all();
diff --git a/arch/powerpc/lib/bootm.c b/arch/powerpc/lib/bootm.c
index dc44bf3ab3a..f9351a17a48 100644
--- a/arch/powerpc/lib/bootm.c
+++ b/arch/powerpc/lib/bootm.c
@@ -54,12 +54,7 @@ static void boot_jump_linux(struct bootm_headers *images)
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
-#ifdef CONFIG_BOOTSTAGE_FDT
- bootstage_fdt_add_report();
-#endif
-#ifdef CONFIG_BOOTSTAGE_REPORT
- bootstage_report();
-#endif
+ bootm_final(0);
#if defined(CONFIG_SYS_INIT_RAM_LOCK) && !defined(CONFIG_E500)
unlock_ram_in_cache();
diff --git a/arch/riscv/include/asm/u-boot-riscv.h b/arch/riscv/include/asm/u-boot-riscv.h
index 543a1688db8..3a8fdb57136 100644
--- a/arch/riscv/include/asm/u-boot-riscv.h
+++ b/arch/riscv/include/asm/u-boot-riscv.h
@@ -16,7 +16,6 @@ int cleanup_before_linux(void);
/* board/.../... */
int board_init(void);
-void board_quiesce_devices(void);
int riscv_board_reserved_mem_fixup(void *fdt);
int riscv_fdt_copy_resv_mem_node(const void *src_fdt, void *dest_fdt);
diff --git a/arch/riscv/lib/bootm.c b/arch/riscv/lib/bootm.c
index 9544907ab1e..69c9ca5c487 100644
--- a/arch/riscv/lib/bootm.c
+++ b/arch/riscv/lib/bootm.c
@@ -25,39 +25,6 @@
DECLARE_GLOBAL_DATA_PTR;
-__weak void board_quiesce_devices(void)
-{
-}
-
-/**
- * announce_and_cleanup() - Print message and prepare for kernel boot
- *
- * @fake: non-zero to do everything except actually boot
- */
-static void announce_and_cleanup(int fake)
-{
- printf("\nStarting kernel ...%s\n\n", fake ?
- "(fake run for tracing)" : "");
- bootstage_mark_name(BOOTSTAGE_ID_BOOTM_HANDOFF, "start_kernel");
-#ifdef CONFIG_BOOTSTAGE_FDT
- bootstage_fdt_add_report();
-#endif
-#if CONFIG_IS_ENABLED(BOOTSTAGE_REPORT)
- bootstage_report();
-#endif
-
- board_quiesce_devices();
-
- /*
- * Call remove function of all devices with a removal flag set.
- * This may be useful for last-stage operations, like cancelling
- * of DMA operation or releasing device internal buffers.
- */
- dm_remove_devices_active();
-
- cleanup_before_linux();
-}
-
static void boot_prep_linux(struct bootm_headers *images)
{
if (CONFIG_IS_ENABLED(OF_LIBFDT) && IS_ENABLED(CONFIG_LMB) && images->ft_len) {
@@ -75,7 +42,6 @@ static void boot_prep_linux(struct bootm_headers *images)
static void boot_jump_linux(struct bootm_headers *images, int flag)
{
void (*kernel)(ulong hart, void *dtb);
- int fake = (flag & BOOTM_STATE_OS_FAKE_GO);
#ifdef CONFIG_SMP
int ret;
#endif
@@ -87,9 +53,10 @@ static void boot_jump_linux(struct bootm_headers *images, int flag)
debug("## Transferring control to kernel (at address %08lx) ...\n",
(ulong)kernel);
- announce_and_cleanup(fake);
+ bootm_final(flag);
+ cleanup_before_linux();
- if (!fake) {
+ if (!(flag & BOOTM_STATE_OS_FAKE_GO)) {
if (CONFIG_IS_ENABLED(OF_LIBFDT) && images->ft_len) {
#ifdef CONFIG_SMP
ret = smp_call_function(images->ep,
diff --git a/arch/sandbox/lib/bootm.c b/arch/sandbox/lib/bootm.c
index 44ba8b52e13..7a5f6f7d36e 100644
--- a/arch/sandbox/lib/bootm.c
+++ b/arch/sandbox/lib/bootm.c
@@ -73,6 +73,7 @@ int do_bootm_linux(int flag, struct bootm_info *bmi)
if (flag & (BOOTM_STATE_OS_GO | BOOTM_STATE_OS_FAKE_GO)) {
bootstage_mark(BOOTSTAGE_ID_RUN_OS);
+ bootm_final(flag);
printf("## Transferring control to Linux (at address %08lx)...\n",
images->ep);
printf("sandbox: continuing, as we cannot run Linux\n");
diff --git a/arch/sh/lib/bootm.c b/arch/sh/lib/bootm.c
index 1c118870dad..81d5957edaa 100644
--- a/arch/sh/lib/bootm.c
+++ b/arch/sh/lib/bootm.c
@@ -92,6 +92,8 @@ int do_bootm_linux(int flag, struct bootm_info *bmi)
images->rd_end - images->rd_start);
}
+ bootm_final(0);
+
/* Boot kernel */
kernel();
diff --git a/arch/x86/lib/bootm.c b/arch/x86/lib/bootm.c
index 7a94dc877e3..cde4fbf3557 100644
--- a/arch/x86/lib/bootm.c
+++ b/arch/x86/lib/bootm.c
@@ -34,22 +34,10 @@ DECLARE_GLOBAL_DATA_PTR;
void bootm_announce_and_cleanup(void)
{
- printf("\nStarting kernel ...\n\n");
-
#ifdef CONFIG_SYS_COREBOOT
timestamp_add_now(TS_START_KERNEL);
#endif
- bootstage_mark_name(BOOTSTAGE_ID_BOOTM_HANDOFF, "start_kernel");
-#if IS_ENABLED(CONFIG_BOOTSTAGE_REPORT)
- bootstage_report();
-#endif
-
- /*
- * Call remove function of all devices with a removal flag set.
- * This may be useful for last-stage operations, like cancelling
- * of DMA operation or releasing device internal buffers.
- */
- dm_remove_devices_active();
+ bootm_final(0);
}
#if defined(CONFIG_OF_LIBFDT) && !defined(CONFIG_OF_NO_KERNEL)
diff --git a/arch/xtensa/lib/bootm.c b/arch/xtensa/lib/bootm.c
index 2958f207397..c19ac9d1f9a 100644
--- a/arch/xtensa/lib/bootm.c
+++ b/arch/xtensa/lib/bootm.c
@@ -178,6 +178,8 @@ int do_bootm_linux(int flag, struct bootm_info *bmi)
printf("Transferring Control to Linux @0x%08lx ...\n\n",
(ulong)images->ep);
+ bootm_final(flag);
+
flush_dcache_range((unsigned long)params_start, (unsigned long)params);
if (flag & BOOTM_STATE_OS_FAKE_GO)