]> git.ipfire.org Git - thirdparty/u-boot.git/blob - boot/bootmeth_qfw.c
acpi: document HETP table
[thirdparty/u-boot.git] / boot / bootmeth_qfw.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3 * Bootmethod for QEMU qfw
4 *
5 * Copyright 2023 Google LLC
6 * Written by Simon Glass <sjg@chromium.org>
7 */
8
9 #define LOG_CATEGORY UCLASS_BOOTSTD
10
11 #include <common.h>
12 #include <command.h>
13 #include <bootdev.h>
14 #include <bootflow.h>
15 #include <bootmeth.h>
16 #include <env.h>
17 #include <qfw.h>
18 #include <dm.h>
19
20 static int qfw_check(struct udevice *dev, struct bootflow_iter *iter)
21 {
22 const struct udevice *media = dev_get_parent(iter->dev);
23 enum uclass_id id = device_get_uclass_id(media);
24
25 log_debug("media=%s\n", media->name);
26 if (id == UCLASS_QFW)
27 return 0;
28
29 return -ENOTSUPP;
30 }
31
32 static int qfw_read_bootflow(struct udevice *dev, struct bootflow *bflow)
33 {
34 struct udevice *qfw_dev = dev_get_parent(bflow->dev);
35 ulong load, initrd;
36 int ret;
37
38 load = env_get_hex("kernel_addr_r", 0);
39 initrd = env_get_hex("ramdisk_addr_r", 0);
40 log_debug("setup kernel %s %lx %lx\n", qfw_dev->name, load, initrd);
41 bflow->name = strdup("qfw");
42 if (!bflow->name)
43 return log_msg_ret("name", -ENOMEM);
44
45 ret = qemu_fwcfg_setup_kernel(qfw_dev, load, initrd);
46 log_debug("setup kernel result %d\n", ret);
47 if (ret)
48 return log_msg_ret("cmd", -EIO);
49
50 bflow->state = BOOTFLOWST_READY;
51
52 return 0;
53 }
54
55 static int qfw_read_file(struct udevice *dev, struct bootflow *bflow,
56 const char *file_path, ulong addr, ulong *sizep)
57 {
58 return -ENOSYS;
59 }
60
61 static int qfw_boot(struct udevice *dev, struct bootflow *bflow)
62 {
63 int ret;
64
65 ret = run_command("booti ${kernel_addr_r} ${ramdisk_addr_r}:${filesize} ${fdtcontroladdr}",
66 0);
67 if (ret) {
68 ret = run_command("bootz ${kernel_addr_r} ${ramdisk_addr_r}:${filesize} "
69 "${fdtcontroladdr}", 0);
70 }
71
72 return ret ? -EIO : 0;
73 }
74
75 static int qfw_bootmeth_bind(struct udevice *dev)
76 {
77 struct bootmeth_uc_plat *plat = dev_get_uclass_plat(dev);
78
79 plat->desc = "QEMU boot using firmware interface";
80
81 return 0;
82 }
83
84 static struct bootmeth_ops qfw_bootmeth_ops = {
85 .check = qfw_check,
86 .read_bootflow = qfw_read_bootflow,
87 .read_file = qfw_read_file,
88 .boot = qfw_boot,
89 };
90
91 static const struct udevice_id qfw_bootmeth_ids[] = {
92 { .compatible = "u-boot,qfw-extlinux" },
93 { }
94 };
95
96 U_BOOT_DRIVER(bootmeth_qfw) = {
97 .name = "bootmeth_qfw",
98 .id = UCLASS_BOOTMETH,
99 .of_match = qfw_bootmeth_ids,
100 .ops = &qfw_bootmeth_ops,
101 .bind = qfw_bootmeth_bind,
102 };