]> git.dujemihanovic.xyz Git - u-boot.git/commitdiff
x86: Add a function to boot a zimage
authorSimon Glass <sjg@chromium.org>
Wed, 12 Jul 2023 15:04:43 +0000 (09:04 -0600)
committerBin Meng <bmeng@tinylab.org>
Mon, 17 Jul 2023 05:38:35 +0000 (13:38 +0800)
Add a direct interface to booting a zimage, so that bootstd can call it
without going through the command-line interface.

Signed-off-by: Simon Glass <sjg@chromium.org>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
arch/x86/include/asm/zimage.h
arch/x86/lib/zimage.c

index 000b38ea89937346002db8d3ad58cf3993a96ab6..966d7224eb18fb1729e0bfc9b5a56031d003018b 100644 (file)
@@ -72,4 +72,21 @@ int setup_zimage(struct boot_params *setup_base, char *cmd_line, int auto_boot,
  */
 void zimage_dump(struct boot_params *base_ptr);
 
+/**
+ * zboot_start() - Boot a zimage
+ *
+ * Boot a zimage, given the component parts
+ *
+ * @addr: Address where the bzImage is moved before booting, either
+ *     BZIMAGE_LOAD_ADDR or ZIMAGE_LOAD_ADDR
+ * @base: Pointer to the boot parameters, typically at address
+ *     DEFAULT_SETUP_BASE
+ * @initrd: Address of the initial ramdisk, or 0 if none
+ * @initrd_size: Size of the initial ramdisk, or 0 if none
+ * @cmdline: Command line to use for booting
+ * Return: -EFAULT on error (normally it does not return)
+ */
+int zboot_start(ulong addr, ulong size, ulong initrd, ulong initrd_size,
+               ulong base, char *cmdline);
+
 #endif
index e5ea5129c1e948528ab8842bb952bc11845b4279..540d4d888bc7ed084d10672be447592d5c42b949 100644 (file)
@@ -22,6 +22,7 @@
 #include <irq_func.h>
 #include <log.h>
 #include <malloc.h>
+#include <mapmem.h>
 #include <acpi/acpi_table.h>
 #include <asm/io.h>
 #include <asm/ptrace.h>
@@ -442,8 +443,7 @@ static int do_zboot_start(struct cmd_tbl *cmdtp, int flag, int argc,
        return 0;
 }
 
-static int do_zboot_load(struct cmd_tbl *cmdtp, int flag, int argc,
-                        char *const argv[])
+static int zboot_load(void)
 {
        struct boot_params *base_ptr;
 
@@ -460,31 +460,51 @@ static int do_zboot_load(struct cmd_tbl *cmdtp, int flag, int argc,
                                       &state.load_address);
                if (!base_ptr) {
                        puts("## Kernel loading failed ...\n");
-                       return CMD_RET_FAILURE;
+                       return -EINVAL;
                }
        }
        state.base_ptr = base_ptr;
-       if (env_set_hex("zbootbase", (ulong)base_ptr) ||
+
+       return 0;
+}
+
+static int do_zboot_load(struct cmd_tbl *cmdtp, int flag, int argc,
+                        char *const argv[])
+{
+       if (zboot_load())
+               return CMD_RET_FAILURE;
+
+       if (env_set_hex("zbootbase", map_to_sysmem(state.base_ptr)) ||
            env_set_hex("zbootaddr", state.load_address))
                return CMD_RET_FAILURE;
 
        return 0;
 }
 
+static int zboot_setup(void)
+{
+       struct boot_params *base_ptr = state.base_ptr;
+       int ret;
+
+       ret = setup_zimage(base_ptr, (char *)base_ptr + COMMAND_LINE_OFFSET,
+                          0, state.initrd_addr, state.initrd_size,
+                          (ulong)state.cmdline);
+       if (ret)
+               return -EINVAL;
+
+       return 0;
+}
+
 static int do_zboot_setup(struct cmd_tbl *cmdtp, int flag, int argc,
                          char *const argv[])
 {
        struct boot_params *base_ptr = state.base_ptr;
-       int ret;
 
        if (!base_ptr) {
                printf("base is not set: use 'zboot load' first\n");
                return CMD_RET_FAILURE;
        }
-       ret = setup_zimage(base_ptr, (char *)base_ptr + COMMAND_LINE_OFFSET,
-                          0, state.initrd_addr, state.initrd_size,
-                          (ulong)state.cmdline);
-       if (ret) {
+       if (zboot_setup()) {
                puts("Setting up boot parameters failed ...\n");
                return CMD_RET_FAILURE;
        }
@@ -501,8 +521,7 @@ static int do_zboot_info(struct cmd_tbl *cmdtp, int flag, int argc,
        return 0;
 }
 
-static int do_zboot_go(struct cmd_tbl *cmdtp, int flag, int argc,
-                      char *const argv[])
+static int zboot_go(void)
 {
        struct boot_params *params = state.base_ptr;
        struct setup_header *hdr = &params->hdr;
@@ -522,11 +541,52 @@ static int do_zboot_go(struct cmd_tbl *cmdtp, int flag, int argc,
 
        /* we assume that the kernel is in place */
        ret = boot_linux_kernel((ulong)state.base_ptr, entry, image_64bit);
+
+       return ret;
+}
+
+static int do_zboot_go(struct cmd_tbl *cmdtp, int flag, int argc,
+                      char *const argv[])
+{
+       int ret;
+
+       ret = zboot_go();
        printf("Kernel returned! (err=%d)\n", ret);
 
        return CMD_RET_FAILURE;
 }
 
+int zboot_start(ulong addr, ulong size, ulong initrd, ulong initrd_size,
+               ulong base, char *cmdline)
+{
+       int ret;
+
+       memset(&state, '\0', sizeof(state));
+
+       if (base) {
+               state.base_ptr = map_sysmem(base, 0);
+               state.load_address = addr;
+       } else {
+               state.bzimage_addr = addr;
+       }
+       state.bzimage_size = size;
+       state.initrd_addr = initrd;
+       state.initrd_size = initrd_size;
+       state.cmdline = cmdline;
+
+       ret = zboot_load();
+       if (ret)
+               return log_msg_ret("ld", ret);
+       ret = zboot_setup();
+       if (ret)
+               return log_msg_ret("set", ret);
+       ret = zboot_go();
+       if (ret)
+               return log_msg_ret("set", ret);
+
+       return -EFAULT;
+}
+
 static void print_num(const char *name, ulong value)
 {
        printf("%-20s: %lx\n", name, value);