From patchwork Wed Apr 25 23:45:14 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Clark X-Patchwork-Id: 10364407 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id ABA036038F for ; Thu, 26 Apr 2018 00:04:27 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 977BE28F98 for ; Thu, 26 Apr 2018 00:04:27 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 87FD829022; Thu, 26 Apr 2018 00:04:27 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.8 required=2.0 tests=BAYES_00,DKIM_SIGNED, MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI, T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 56EB728F98 for ; Thu, 26 Apr 2018 00:04:26 +0000 (UTC) Received: from localhost ([::1]:39637 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fBUOf-0002F6-EE for patchwork-qemu-devel@patchwork.kernel.org; Wed, 25 Apr 2018 20:04:25 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:46481) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fBU8c-0004rZ-61 for qemu-devel@nongnu.org; Wed, 25 Apr 2018 19:47:53 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1fBU8Y-000502-TY for qemu-devel@nongnu.org; Wed, 25 Apr 2018 19:47:50 -0400 Received: from mail-pf0-x244.google.com ([2607:f8b0:400e:c00::244]:39002) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1fBU8Y-0004zb-KS for qemu-devel@nongnu.org; Wed, 25 Apr 2018 19:47:46 -0400 Received: by mail-pf0-x244.google.com with SMTP id z9so16592043pfe.6 for ; Wed, 25 Apr 2018 16:47:46 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=NTLeMAW+JJv1/2NDChCvkpafxJEHB0lN3eaXT4Ai7ds=; b=dtXOkgdNL4AYnYh2TENxoHidBx0XBNhu54w8SLwo+FOUqk8jHByKABqeNKxy0Y0pIV UB+KHp6KfScKLs0rkLtbmzYpckgVYm2UL3aOLcueuub8fvteuJ/BueODkHcPdFOo+e61 hh/B0nkVpn3SixXxxWV5MRD4yPdBMzmCEbFJ/z9JgXIl1Fuhwe3q8CJB8CitI1uBROQi qmgwQwjwvvN07/2ZCBTjl7ymBde5rscA0lr/d3zy2jXtX/jG08PIGF8nct0O1rZXuQoA FIRJ4i3iLxeB6bMT8hlMK6B5mCJXCkaLnFnybR3vE/7Z1zxdvwvsjQYelypDcJXKaSn1 H3Kw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=NTLeMAW+JJv1/2NDChCvkpafxJEHB0lN3eaXT4Ai7ds=; b=OMD5qNDpT6XYuIkjAAzAZ7cTinfzSyhID5YC58LmLdgjz8O9MHDKgxNVwDCMn2Os3j QcBu7jynWj7Fp3MTWEI7i+WlxU9di37BcDc939GhhdCQjiVp8sBzKrNq7++hnDvIoPN+ fM6Ya9Inaki3IN2pj6i/uR/io1x8Wyrxngn9kz3fS3lMmKX4hAOdNeymNkjhbU+wzXM+ N/l49oHiVozHSWi+yedqldGf1k37FmOkiwx+fBptQExr0zkVT9gO85k/O5DHqmI3rEo9 CzR4ENVxjZiHaqdSEx2uzJEzLvzp+EjNsKxOWZGAjPyIRHc3ePCh9BuLRH75bvx2EAH5 bhqw== X-Gm-Message-State: ALQs6tAVHCtV059sXv5wnPBS1b+iW+WgqVuHCG1VqaGeZqZvnhpoFq7w RVs8iLIocblr0rPzX9EdlixyNdRD5a0= X-Google-Smtp-Source: AIpwx4/yzvRTL1jZPph8Xc8ty6kkvG6aXJf++d00iMVj+0n/LZLmvzz7mKsRNJFP2+az6etNob02aA== X-Received: by 10.99.109.132 with SMTP id i126mr25294642pgc.414.1524700065457; Wed, 25 Apr 2018 16:47:45 -0700 (PDT) Received: from localhost.localdomain (122-58-167-38-fibre.bb.spark.co.nz. [122.58.167.38]) by smtp.gmail.com with ESMTPSA id e10sm29577549pfn.67.2018.04.25.16.47.42 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 25 Apr 2018 16:47:44 -0700 (PDT) From: Michael Clark To: qemu-devel@nongnu.org Date: Thu, 26 Apr 2018 11:45:14 +1200 Message-Id: <1524699938-6764-12-git-send-email-mjc@sifive.com> X-Mailer: git-send-email 2.7.0 In-Reply-To: <1524699938-6764-1-git-send-email-mjc@sifive.com> References: <1524699938-6764-1-git-send-email-mjc@sifive.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2607:f8b0:400e:c00::244 Subject: [Qemu-devel] [PATCH v8 11/35] RISC-V: Mark ROM read-only after copying in code X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Sagar Karandikar , Bastian Koppelmann , Palmer Dabbelt , Michael Clark , Alistair Francis , patches@groups.riscv.org Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP The sifive_u machine already marks its ROM readonly. This fixes the remaining boards. This commit also makes all boards use mask_rom as the variable name for the ROM. This change also makes space for the maximum device tree size size and adds an explicit bounds check and error message. Cc: Sagar Karandikar Cc: Bastian Koppelmann Cc: Palmer Dabbelt Cc: Alistair Francis Signed-off-by: Michael Clark --- hw/riscv/sifive_e.c | 20 +++++++--------- hw/riscv/sifive_u.c | 46 ++++++++++++++++++----------------- hw/riscv/spike.c | 64 ++++++++++++++++++++++++++++--------------------- hw/riscv/virt.c | 38 +++++++++++++++-------------- include/hw/riscv/virt.h | 4 ++++ 5 files changed, 93 insertions(+), 79 deletions(-) diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c index 39e4cb4..0c8b8e9 100644 --- a/hw/riscv/sifive_e.c +++ b/hw/riscv/sifive_e.c @@ -74,14 +74,6 @@ static const struct MemmapEntry { [SIFIVE_E_DTIM] = { 0x80000000, 0x4000 } }; -static void copy_le32_to_phys(hwaddr pa, uint32_t *rom, size_t len) -{ - int i; - for (i = 0; i < (len >> 2); i++) { - stl_phys(&address_space_memory, pa + (i << 2), rom[i]); - } -} - static uint64_t load_kernel(const char *kernel_filename) { uint64_t kernel_entry, kernel_high; @@ -112,6 +104,7 @@ static void riscv_sifive_e_init(MachineState *machine) MemoryRegion *main_mem = g_new(MemoryRegion, 1); MemoryRegion *mask_rom = g_new(MemoryRegion, 1); MemoryRegion *xip_mem = g_new(MemoryRegion, 1); + int i; /* Initialize SOC */ object_initialize(&s->soc, sizeof(s->soc), TYPE_RISCV_HART_ARRAY); @@ -131,7 +124,7 @@ static void riscv_sifive_e_init(MachineState *machine) memmap[SIFIVE_E_DTIM].base, main_mem); /* Mask ROM */ - memory_region_init_ram(mask_rom, NULL, "riscv.sifive.e.mrom", + memory_region_init_rom(mask_rom, NULL, "riscv.sifive.e.mrom", memmap[SIFIVE_E_MROM].size, &error_fatal); memory_region_add_subregion(sys_mem, memmap[SIFIVE_E_MROM].base, mask_rom); @@ -185,9 +178,12 @@ static void riscv_sifive_e_init(MachineState *machine) 0x00028067, /* 0x1004: jr t0 */ }; - /* copy in the reset vector */ - copy_le32_to_phys(memmap[SIFIVE_E_MROM].base, reset_vec, sizeof(reset_vec)); - memory_region_set_readonly(mask_rom, true); + /* copy in the reset vector in little_endian byte order */ + for (i = 0; i < sizeof(reset_vec) >> 2; i++) { + reset_vec[i] = cpu_to_le32(reset_vec[i]); + } + rom_add_blob_fixed_as("mrom.reset", reset_vec, sizeof(reset_vec), + memmap[SIFIVE_E_MROM].base, &address_space_memory); if (machine->kernel_filename) { load_kernel(machine->kernel_filename); diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c index 115618b..11ba4c3 100644 --- a/hw/riscv/sifive_u.c +++ b/hw/riscv/sifive_u.c @@ -52,7 +52,7 @@ static const struct MemmapEntry { hwaddr size; } sifive_u_memmap[] = { [SIFIVE_U_DEBUG] = { 0x0, 0x100 }, - [SIFIVE_U_MROM] = { 0x1000, 0x2000 }, + [SIFIVE_U_MROM] = { 0x1000, 0x11000 }, [SIFIVE_U_CLINT] = { 0x2000000, 0x10000 }, [SIFIVE_U_PLIC] = { 0xc000000, 0x4000000 }, [SIFIVE_U_UART0] = { 0x10013000, 0x1000 }, @@ -60,14 +60,6 @@ static const struct MemmapEntry { [SIFIVE_U_DRAM] = { 0x80000000, 0x0 }, }; -static void copy_le32_to_phys(hwaddr pa, uint32_t *rom, size_t len) -{ - int i; - for (i = 0; i < (len >> 2); i++) { - stl_phys(&address_space_memory, pa + (i << 2), rom[i]); - } -} - static uint64_t load_kernel(const char *kernel_filename) { uint64_t kernel_entry, kernel_high; @@ -221,9 +213,10 @@ static void riscv_sifive_u_init(MachineState *machine) const struct MemmapEntry *memmap = sifive_u_memmap; SiFiveUState *s = g_new0(SiFiveUState, 1); - MemoryRegion *sys_memory = get_system_memory(); + MemoryRegion *system_memory = get_system_memory(); MemoryRegion *main_mem = g_new(MemoryRegion, 1); - MemoryRegion *boot_rom = g_new(MemoryRegion, 1); + MemoryRegion *mask_rom = g_new(MemoryRegion, 1); + int i; /* Initialize SOC */ object_initialize(&s->soc, sizeof(s->soc), TYPE_RISCV_HART_ARRAY); @@ -239,17 +232,17 @@ static void riscv_sifive_u_init(MachineState *machine) /* register RAM */ memory_region_init_ram(main_mem, NULL, "riscv.sifive.u.ram", machine->ram_size, &error_fatal); - memory_region_add_subregion(sys_memory, memmap[SIFIVE_U_DRAM].base, + memory_region_add_subregion(system_memory, memmap[SIFIVE_U_DRAM].base, main_mem); /* create device tree */ create_fdt(s, memmap, machine->ram_size, machine->kernel_cmdline); /* boot rom */ - memory_region_init_ram(boot_rom, NULL, "riscv.sifive.u.mrom", - memmap[SIFIVE_U_MROM].base, &error_fatal); - memory_region_set_readonly(boot_rom, true); - memory_region_add_subregion(sys_memory, 0x0, boot_rom); + memory_region_init_rom(mask_rom, NULL, "riscv.sifive.u.mrom", + memmap[SIFIVE_U_MROM].size, &error_fatal); + memory_region_add_subregion(system_memory, memmap[SIFIVE_U_MROM].base, + mask_rom); if (machine->kernel_filename) { load_kernel(machine->kernel_filename); @@ -272,13 +265,22 @@ static void riscv_sifive_u_init(MachineState *machine) /* dtb: */ }; - /* copy in the reset vector */ - copy_le32_to_phys(memmap[SIFIVE_U_MROM].base, reset_vec, sizeof(reset_vec)); + /* copy in the reset vector in little_endian byte order */ + for (i = 0; i < sizeof(reset_vec) >> 2; i++) { + reset_vec[i] = cpu_to_le32(reset_vec[i]); + } + rom_add_blob_fixed_as("mrom.reset", reset_vec, sizeof(reset_vec), + memmap[SIFIVE_U_MROM].base, &address_space_memory); /* copy in the device tree */ + if (s->fdt_size >= memmap[SIFIVE_U_MROM].size - sizeof(reset_vec)) { + error_report("qemu: not enough space to store device-tree"); + exit(1); + } qemu_fdt_dumpdtb(s->fdt, s->fdt_size); - cpu_physical_memory_write(memmap[SIFIVE_U_MROM].base + - sizeof(reset_vec), s->fdt, s->fdt_size); + rom_add_blob_fixed_as("mrom.fdt", s->fdt, s->fdt_size, + memmap[SIFIVE_U_MROM].base + sizeof(reset_vec), + &address_space_memory); /* MMIO */ s->plic = sifive_plic_create(memmap[SIFIVE_U_PLIC].base, @@ -292,9 +294,9 @@ static void riscv_sifive_u_init(MachineState *machine) SIFIVE_U_PLIC_CONTEXT_BASE, SIFIVE_U_PLIC_CONTEXT_STRIDE, memmap[SIFIVE_U_PLIC].size); - sifive_uart_create(sys_memory, memmap[SIFIVE_U_UART0].base, + sifive_uart_create(system_memory, memmap[SIFIVE_U_UART0].base, serial_hds[0], SIFIVE_PLIC(s->plic)->irqs[SIFIVE_U_UART0_IRQ]); - /* sifive_uart_create(sys_memory, memmap[SIFIVE_U_UART1].base, + /* sifive_uart_create(system_memory, memmap[SIFIVE_U_UART1].base, serial_hds[1], SIFIVE_PLIC(s->plic)->irqs[SIFIVE_U_UART1_IRQ]); */ sifive_clint_create(memmap[SIFIVE_U_CLINT].base, memmap[SIFIVE_U_CLINT].size, smp_cpus, diff --git a/hw/riscv/spike.c b/hw/riscv/spike.c index 3f6bd0a..d1dbe6b 100644 --- a/hw/riscv/spike.c +++ b/hw/riscv/spike.c @@ -46,19 +46,11 @@ static const struct MemmapEntry { hwaddr base; hwaddr size; } spike_memmap[] = { - [SPIKE_MROM] = { 0x1000, 0x2000 }, + [SPIKE_MROM] = { 0x1000, 0x11000 }, [SPIKE_CLINT] = { 0x2000000, 0x10000 }, [SPIKE_DRAM] = { 0x80000000, 0x0 }, }; -static void copy_le32_to_phys(hwaddr pa, uint32_t *rom, size_t len) -{ - int i; - for (i = 0; i < (len >> 2); i++) { - stl_phys(&address_space_memory, pa + (i << 2), rom[i]); - } -} - static uint64_t load_kernel(const char *kernel_filename) { uint64_t kernel_entry, kernel_high; @@ -173,7 +165,8 @@ static void spike_v1_10_0_board_init(MachineState *machine) SpikeState *s = g_new0(SpikeState, 1); MemoryRegion *system_memory = get_system_memory(); MemoryRegion *main_mem = g_new(MemoryRegion, 1); - MemoryRegion *boot_rom = g_new(MemoryRegion, 1); + MemoryRegion *mask_rom = g_new(MemoryRegion, 1); + int i; /* Initialize SOC */ object_initialize(&s->soc, sizeof(s->soc), TYPE_RISCV_HART_ARRAY); @@ -196,9 +189,10 @@ static void spike_v1_10_0_board_init(MachineState *machine) create_fdt(s, memmap, machine->ram_size, machine->kernel_cmdline); /* boot rom */ - memory_region_init_ram(boot_rom, NULL, "riscv.spike.bootrom", - s->fdt_size + 0x2000, &error_fatal); - memory_region_add_subregion(system_memory, 0x0, boot_rom); + memory_region_init_rom(mask_rom, NULL, "riscv.spike.mrom", + memmap[SPIKE_MROM].size, &error_fatal); + memory_region_add_subregion(system_memory, memmap[SPIKE_MROM].base, + mask_rom); if (machine->kernel_filename) { load_kernel(machine->kernel_filename); @@ -221,16 +215,25 @@ static void spike_v1_10_0_board_init(MachineState *machine) /* dtb: */ }; - /* copy in the reset vector */ - copy_le32_to_phys(memmap[SPIKE_MROM].base, reset_vec, sizeof(reset_vec)); + /* copy in the reset vector in little_endian byte order */ + for (i = 0; i < sizeof(reset_vec) >> 2; i++) { + reset_vec[i] = cpu_to_le32(reset_vec[i]); + } + rom_add_blob_fixed_as("mrom.reset", reset_vec, sizeof(reset_vec), + memmap[SPIKE_MROM].base, &address_space_memory); /* copy in the device tree */ + if (s->fdt_size >= memmap[SPIKE_MROM].size - sizeof(reset_vec)) { + error_report("qemu: not enough space to store device-tree"); + exit(1); + } qemu_fdt_dumpdtb(s->fdt, s->fdt_size); - cpu_physical_memory_write(memmap[SPIKE_MROM].base + sizeof(reset_vec), - s->fdt, s->fdt_size); + rom_add_blob_fixed_as("mrom.fdt", s->fdt, s->fdt_size, + memmap[SPIKE_MROM].base + sizeof(reset_vec), + &address_space_memory); /* initialize HTIF using symbols found in load_kernel */ - htif_mm_init(system_memory, boot_rom, &s->soc.harts[0].env, serial_hds[0]); + htif_mm_init(system_memory, mask_rom, &s->soc.harts[0].env, serial_hds[0]); /* Core Local Interruptor (timer and IPI) */ sifive_clint_create(memmap[SPIKE_CLINT].base, memmap[SPIKE_CLINT].size, @@ -244,7 +247,8 @@ static void spike_v1_09_1_board_init(MachineState *machine) SpikeState *s = g_new0(SpikeState, 1); MemoryRegion *system_memory = get_system_memory(); MemoryRegion *main_mem = g_new(MemoryRegion, 1); - MemoryRegion *boot_rom = g_new(MemoryRegion, 1); + MemoryRegion *mask_rom = g_new(MemoryRegion, 1); + int i; /* Initialize SOC */ object_initialize(&s->soc, sizeof(s->soc), TYPE_RISCV_HART_ARRAY); @@ -264,9 +268,10 @@ static void spike_v1_09_1_board_init(MachineState *machine) main_mem); /* boot rom */ - memory_region_init_ram(boot_rom, NULL, "riscv.spike.bootrom", - 0x40000, &error_fatal); - memory_region_add_subregion(system_memory, 0x0, boot_rom); + memory_region_init_rom(mask_rom, NULL, "riscv.spike.mrom", + memmap[SPIKE_MROM].size, &error_fatal); + memory_region_add_subregion(system_memory, memmap[SPIKE_MROM].base, + mask_rom); if (machine->kernel_filename) { load_kernel(machine->kernel_filename); @@ -319,15 +324,20 @@ static void spike_v1_09_1_board_init(MachineState *machine) g_free(isa); size_t config_string_len = strlen(config_string); - /* copy in the reset vector */ - copy_le32_to_phys(memmap[SPIKE_MROM].base, reset_vec, sizeof(reset_vec)); + /* copy in the reset vector in little_endian byte order */ + for (i = 0; i < sizeof(reset_vec) >> 2; i++) { + reset_vec[i] = cpu_to_le32(reset_vec[i]); + } + rom_add_blob_fixed_as("mrom.reset", reset_vec, sizeof(reset_vec), + memmap[SPIKE_MROM].base, &address_space_memory); /* copy in the config string */ - cpu_physical_memory_write(memmap[SPIKE_MROM].base + sizeof(reset_vec), - config_string, config_string_len); + rom_add_blob_fixed_as("mrom.reset", config_string, config_string_len, + memmap[SPIKE_MROM].base + sizeof(reset_vec), + &address_space_memory); /* initialize HTIF using symbols found in load_kernel */ - htif_mm_init(system_memory, boot_rom, &s->soc.harts[0].env, serial_hds[0]); + htif_mm_init(system_memory, mask_rom, &s->soc.harts[0].env, serial_hds[0]); /* Core Local Interruptor (timer and IPI) */ sifive_clint_create(memmap[SPIKE_CLINT].base, memmap[SPIKE_CLINT].size, diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c index 090befe..20c509d 100644 --- a/hw/riscv/virt.c +++ b/hw/riscv/virt.c @@ -45,8 +45,8 @@ static const struct MemmapEntry { hwaddr size; } virt_memmap[] = { [VIRT_DEBUG] = { 0x0, 0x100 }, - [VIRT_MROM] = { 0x1000, 0x2000 }, - [VIRT_TEST] = { 0x4000, 0x1000 }, + [VIRT_MROM] = { 0x1000, 0x11000 }, + [VIRT_TEST] = { 0x100000, 0x1000 }, [VIRT_CLINT] = { 0x2000000, 0x10000 }, [VIRT_PLIC] = { 0xc000000, 0x4000000 }, [VIRT_UART0] = { 0x10000000, 0x100 }, @@ -54,14 +54,6 @@ static const struct MemmapEntry { [VIRT_DRAM] = { 0x80000000, 0x0 }, }; -static void copy_le32_to_phys(hwaddr pa, uint32_t *rom, size_t len) -{ - int i; - for (i = 0; i < (len >> 2); i++) { - stl_phys(&address_space_memory, pa + (i << 2), rom[i]); - } -} - static uint64_t load_kernel(const char *kernel_filename) { uint64_t kernel_entry, kernel_high; @@ -272,7 +264,7 @@ static void riscv_virt_board_init(MachineState *machine) RISCVVirtState *s = g_new0(RISCVVirtState, 1); MemoryRegion *system_memory = get_system_memory(); MemoryRegion *main_mem = g_new(MemoryRegion, 1); - MemoryRegion *boot_rom = g_new(MemoryRegion, 1); + MemoryRegion *mask_rom = g_new(MemoryRegion, 1); char *plic_hart_config; size_t plic_hart_config_len; int i; @@ -299,9 +291,10 @@ static void riscv_virt_board_init(MachineState *machine) fdt = create_fdt(s, memmap, machine->ram_size, machine->kernel_cmdline); /* boot rom */ - memory_region_init_ram(boot_rom, NULL, "riscv_virt_board.bootrom", - s->fdt_size + 0x2000, &error_fatal); - memory_region_add_subregion(system_memory, 0x0, boot_rom); + memory_region_init_rom(mask_rom, NULL, "riscv_virt_board.mrom", + memmap[VIRT_MROM].size, &error_fatal); + memory_region_add_subregion(system_memory, memmap[VIRT_MROM].base, + mask_rom); if (machine->kernel_filename) { uint64_t kernel_entry = load_kernel(machine->kernel_filename); @@ -335,13 +328,22 @@ static void riscv_virt_board_init(MachineState *machine) /* dtb: */ }; - /* copy in the reset vector */ - copy_le32_to_phys(memmap[VIRT_MROM].base, reset_vec, sizeof(reset_vec)); + /* copy in the reset vector in little_endian byte order */ + for (i = 0; i < sizeof(reset_vec) >> 2; i++) { + reset_vec[i] = cpu_to_le32(reset_vec[i]); + } + rom_add_blob_fixed_as("mrom.reset", reset_vec, sizeof(reset_vec), + memmap[VIRT_MROM].base, &address_space_memory); /* copy in the device tree */ + if (s->fdt_size >= memmap[VIRT_MROM].size - sizeof(reset_vec)) { + error_report("qemu: not enough space to store device-tree"); + exit(1); + } qemu_fdt_dumpdtb(s->fdt, s->fdt_size); - cpu_physical_memory_write(memmap[VIRT_MROM].base + sizeof(reset_vec), - s->fdt, s->fdt_size); + rom_add_blob_fixed_as("mrom.fdt", s->fdt, s->fdt_size, + memmap[VIRT_MROM].base + sizeof(reset_vec), + &address_space_memory); /* create PLIC hart topology configuration string */ plic_hart_config_len = (strlen(VIRT_PLIC_HART_CONFIG) + 1) * smp_cpus; diff --git a/include/hw/riscv/virt.h b/include/hw/riscv/virt.h index 91163d6..6f2668e 100644 --- a/include/hw/riscv/virt.h +++ b/include/hw/riscv/virt.h @@ -19,6 +19,10 @@ #ifndef HW_RISCV_VIRT_H #define HW_RISCV_VIRT_H +#define TYPE_RISCV_VIRT_BOARD "riscv.virt" +#define VIRT(obj) \ + OBJECT_CHECK(RISCVVirtState, (obj), TYPE_RISCV_VIRT_BOARD) + typedef struct { /*< private >*/ SysBusDevice parent_obj;