[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-ppc] [PATCHv3 05/12] pseries: Consolidate RTAS loading
From: |
David Gibson |
Subject: |
[Qemu-ppc] [PATCHv3 05/12] pseries: Consolidate RTAS loading |
Date: |
Mon, 24 Oct 2016 16:04:36 +1100 |
At each system reset, the pseries machine needs to load RTAS (the runtime
portion of the guest firmware) into the VM. This means copying
the actual RTAS code into guest memory, and also updating the device
tree so that the guest OS and boot firmware can locate it.
For historical reasons the copy and update to the device tree were in
different parts of the code. This cleanup brings them both together in
an spapr_load_rtas() function.
Signed-off-by: David Gibson <address@hidden>
Reviewed-by: Alexey Kardashevskiy <address@hidden>
Reviewed-by: Thomas Huth <address@hidden>
Reviewed-by: Michael Roth <address@hidden>
---
hw/ppc/spapr.c | 3 +--
hw/ppc/spapr_rtas.c | 72 ++++++++++++++++++++++++++++----------------------
include/hw/ppc/spapr.h | 1 +
3 files changed, 43 insertions(+), 33 deletions(-)
diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c
index 1eddd1b..cb6b1a3 100644
--- a/hw/ppc/spapr.c
+++ b/hw/ppc/spapr.c
@@ -1165,8 +1165,7 @@ static void ppc_spapr_reset(void)
fdt = spapr_build_fdt(spapr, rtas_addr, spapr->rtas_size);
- /* Copy RTAS over */
- cpu_physical_memory_write(rtas_addr, spapr->rtas_blob, spapr->rtas_size);
+ spapr_load_rtas(spapr, fdt, rtas_addr);
rc = fdt_pack(fdt);
diff --git a/hw/ppc/spapr_rtas.c b/hw/ppc/spapr_rtas.c
index 0db84c8..54b4ad3 100644
--- a/hw/ppc/spapr_rtas.c
+++ b/hw/ppc/spapr_rtas.c
@@ -721,37 +721,6 @@ int spapr_rtas_device_tree_setup(void *fdt, hwaddr
rtas_addr,
uint64_t max_hotplug_addr = spapr->hotplug_memory.base +
memory_region_size(&spapr->hotplug_memory.mr);
- ret = fdt_add_mem_rsv(fdt, rtas_addr, rtas_size);
- if (ret < 0) {
- error_report("Couldn't add RTAS reserve entry: %s",
- fdt_strerror(ret));
- return ret;
- }
-
- ret = qemu_fdt_setprop_cell(fdt, "/rtas", "linux,rtas-base",
- rtas_addr);
- if (ret < 0) {
- error_report("Couldn't add linux,rtas-base property: %s",
- fdt_strerror(ret));
- return ret;
- }
-
- ret = qemu_fdt_setprop_cell(fdt, "/rtas", "linux,rtas-entry",
- rtas_addr);
- if (ret < 0) {
- error_report("Couldn't add linux,rtas-entry property: %s",
- fdt_strerror(ret));
- return ret;
- }
-
- ret = qemu_fdt_setprop_cell(fdt, "/rtas", "rtas-size",
- rtas_size);
- if (ret < 0) {
- error_report("Couldn't add rtas-size property: %s",
- fdt_strerror(ret));
- return ret;
- }
-
for (i = 0; i < RTAS_TOKEN_MAX - RTAS_TOKEN_BASE; i++) {
struct rtas_call *call = &rtas_table[i];
@@ -784,6 +753,47 @@ int spapr_rtas_device_tree_setup(void *fdt, hwaddr
rtas_addr,
return 0;
}
+void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr)
+{
+ int rtas_node;
+ int ret;
+
+ /* Copy RTAS blob into guest RAM */
+ cpu_physical_memory_write(addr, spapr->rtas_blob, spapr->rtas_size);
+
+ ret = fdt_add_mem_rsv(fdt, addr, spapr->rtas_size);
+ if (ret < 0) {
+ error_report("Couldn't add RTAS reserve entry: %s",
+ fdt_strerror(ret));
+ exit(1);
+ }
+
+ /* Update the device tree with the blob's location */
+ rtas_node = fdt_path_offset(fdt, "/rtas");
+ assert(rtas_node >= 0);
+
+ ret = fdt_setprop_cell(fdt, rtas_node, "linux,rtas-base", addr);
+ if (ret < 0) {
+ error_report("Couldn't add linux,rtas-base property: %s",
+ fdt_strerror(ret));
+ exit(1);
+ }
+
+ ret = fdt_setprop_cell(fdt, rtas_node, "linux,rtas-entry", addr);
+ if (ret < 0) {
+ error_report("Couldn't add linux,rtas-entry property: %s",
+ fdt_strerror(ret));
+ exit(1);
+ }
+
+ ret = fdt_setprop_cell(fdt, rtas_node, "rtas-size", spapr->rtas_size);
+ if (ret < 0) {
+ error_report("Couldn't add rtas-size property: %s",
+ fdt_strerror(ret));
+ exit(1);
+ }
+}
+
static void core_rtas_register_types(void)
{
spapr_rtas_register(RTAS_DISPLAY_CHARACTER, "display-character",
diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h
index a0b4bf8..847ae88 100644
--- a/include/hw/ppc/spapr.h
+++ b/include/hw/ppc/spapr.h
@@ -532,6 +532,7 @@ target_ulong spapr_rtas_call(PowerPCCPU *cpu,
sPAPRMachineState *sm,
uint32_t nret, target_ulong rets);
int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr,
hwaddr rtas_size);
+void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr);
#define SPAPR_TCE_PAGE_SHIFT 12
#define SPAPR_TCE_PAGE_SIZE (1ULL << SPAPR_TCE_PAGE_SHIFT)
--
2.7.4
- [Qemu-ppc] [PATCHv3 00/12] pseries: Consolidate guest device tree construction, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 01/12] pseries: Split device tree construction from device tree load, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 05/12] pseries: Consolidate RTAS loading,
David Gibson <=
- [Qemu-ppc] [PATCHv3 12/12] pseries: Remove spapr_create_fdt_skel(), David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 04/12] pseries: Move adding of fdt reserve map entries, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 03/12] pseries: Make spapr_create_fdt_skel() get information from machine state, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 09/12] pseries: Move /event-sources construction to spapr_build_fdt(), David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 10/12] pseries: Move /hypervisor node construction to fdt_build_fdt(), David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 08/12] pseries: Consolidate construction of /rtas device tree node, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 02/12] pseries: Remove rtas_addr and fdt_addr fields from machinestate, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 11/12] pseries: Consolidate construction of /vdevice device tree node, David Gibson, 2016/10/24
- [Qemu-ppc] [PATCHv3 06/12] pseries: Move construction of /interrupt-controller fdt node, David Gibson, 2016/10/24