qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2
@ 2019-10-28 15:48 Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 01/18] riscv: Skip checking CSR privilege level in debugger mode Palmer Dabbelt
                   ` (18 more replies)
  0 siblings, 19 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell; +Cc: qemu-riscv, qemu-devel

merged tag 'for_upstream'
Primary key fingerprint: 0270 606B 6F3C DF3D 0B17  0970 C350 3912 AFBE 8E67
     Subkey fingerprint: 5D09 FD08 71C8 F85B 94CA  8A0D 281F 0DB8 D28D 5469
The following changes since commit 9bb73502321d46f4d320fa17aa38201445783fc4:

  Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging (2019-10-28 13:32:40 +0000)

are available in the Git repository at:

  git://github.com/palmer-dabbelt/qemu.git tags/riscv-for-master-4.2-sf2

for you to fetch changes up to 9667e53573f907d4fcd6accff1c8fe525544b749:

  target/riscv: PMP violation due to wrong size parameter (2019-10-28 08:46:33 -0700)

----------------------------------------------------------------
RISC-V Patches for the 4.2 Soft Freeze, Part 2

This patch set contains a handful of small fixes for RISC-V targets that
I'd like to target for the 4.2 soft freeze.  They include:

* A fix to allow the debugger to access the state of all privilege
  modes, as opposed to just the currently executing one.
* A pair of cleanups to implement cpu_do_transaction_failed.
* Fixes to the device tree.
* The addition of various memory regions to make the sifive_u machine
  more closely match the HiFive Unleashed board.
* Fixes to our GDB interface to allow CSRs to be accessed.
* A fix to a memory leak pointed out by coverity.
* A fix that prevents PMP checks from firing incorrectly.

This passes "make chcek" and boots Open Embedded for me.

----------------------------------------------------------------
Alistair Francis (8):
      riscv/sifive_u: Add L2-LIM cache memory
      riscv/sifive_u: Add QSPI memory region
      riscv/sifive_u: Manually define the machine
      riscv/sifive_u: Add the start-in-flash property
      riscv/virt: Manually define the machine
      riscv/virt: Add the PFlash CFI01 device
      riscv/virt: Jump to pflash if specified
      riscv/boot: Fix possible memory leak

Bin Meng (3):
      riscv: Skip checking CSR privilege level in debugger mode
      riscv: hw: Drop "clock-frequency" property of cpu nodes
      riscv: sifive_u: Add ethernet0 to the aliases node

Dayeol Lee (1):
      target/riscv: PMP violation due to wrong size parameter

Giuseppe Musacchio (1):
      linux-user/riscv: Propagate fault address

Jonathan Behrens (3):
      target/riscv: Tell gdbstub the correct number of CSRs
      target/riscv: Expose "priv" register for GDB for reads
      target/riscv: Make the priv register writable by GDB

Palmer Dabbelt (2):
      RISC-V: Handle bus errors in the page table walker
      RISC-V: Implement cpu_do_transaction_failed

 configure                       |   4 +-
 gdb-xml/riscv-32bit-virtual.xml |  11 ++++
 gdb-xml/riscv-64bit-virtual.xml |  11 ++++
 hw/riscv/Kconfig                |   1 +
 hw/riscv/boot.c                 |  11 ++--
 hw/riscv/sifive_u.c             | 105 ++++++++++++++++++++++++++------
 hw/riscv/spike.c                |   2 -
 hw/riscv/virt.c                 | 129 +++++++++++++++++++++++++++++++++++++---
 include/hw/riscv/sifive_u.h     |  12 +++-
 include/hw/riscv/spike.h        |   4 --
 include/hw/riscv/virt.h         |  14 +++--
 linux-user/riscv/cpu_loop.c     |   3 +-
 target/riscv/cpu.c              |   2 +-
 target/riscv/cpu.h              |   7 ++-
 target/riscv/cpu_helper.c       |  28 ++++++---
 target/riscv/csr.c              |   5 +-
 target/riscv/gdbstub.c          |  36 ++++++++++-
 target/riscv/pmp.c              |  13 +++-
 18 files changed, 334 insertions(+), 64 deletions(-)
 create mode 100644 gdb-xml/riscv-32bit-virtual.xml
 create mode 100644 gdb-xml/riscv-64bit-virtual.xml



^ permalink raw reply	[flat|nested] 20+ messages in thread

* [PULL 01/18] riscv: Skip checking CSR privilege level in debugger mode
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 02/18] RISC-V: Handle bus errors in the page table walker Palmer Dabbelt
                   ` (17 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, qemu-devel, Alistair Francis,
	Zong Li, Bin Meng

From: Bin Meng <bmeng.cn@gmail.com>

If we are in debugger mode, skip the CSR privilege level checking
so that we can read/write all CSRs. Otherwise we get:

(gdb) p/x $mtvec
Could not fetch register "mtvec"; remote failure reply 'E14'

when the hart is currently in S-mode.

Reported-by: Zong Li <zong.li@sifive.com>
Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/csr.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index f767ad24be..974c9c20b5 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -801,7 +801,10 @@ int riscv_csrrw(CPURISCVState *env, int csrno, target_ulong *ret_value,
 #if !defined(CONFIG_USER_ONLY)
     int csr_priv = get_field(csrno, 0x300);
     int read_only = get_field(csrno, 0xC00) == 3;
-    if ((write_mask && read_only) || (env->priv < csr_priv)) {
+    if ((!env->debugger) && (env->priv < csr_priv)) {
+        return -1;
+    }
+    if (write_mask && read_only) {
         return -1;
     }
 #endif
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 02/18] RISC-V: Handle bus errors in the page table walker
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 01/18] riscv: Skip checking CSR privilege level in debugger mode Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 03/18] RISC-V: Implement cpu_do_transaction_failed Palmer Dabbelt
                   ` (16 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, Richard Henderson, qemu-devel,
	Alistair Francis, ilippe=20Mathieu-Daud=C3=A9?=

We directly access physical memory while walking the page tables on
RISC-V, but while doing so we were using cpu_ld*() which does not report
bus errors.  This patch converts the page table walker over to use
address_space_ld*(), which allows bus errors to be detected.

Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/cpu_helper.c | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 87dd6a6ece..c82e7ed52b 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -169,7 +169,8 @@ static int get_physical_address(CPURISCVState *env, hwaddr *physical,
     /* NOTE: the env->pc value visible here will not be
      * correct, but the value visible to the exception handler
      * (riscv_cpu_do_interrupt) is correct */
-
+    MemTxResult res;
+    MemTxAttrs attrs = MEMTXATTRS_UNSPECIFIED;
     int mode = mmu_idx;
 
     if (mode == PRV_M && access_type != MMU_INST_FETCH) {
@@ -256,11 +257,16 @@ restart:
             1 << MMU_DATA_LOAD, PRV_S)) {
             return TRANSLATE_PMP_FAIL;
         }
+
 #if defined(TARGET_RISCV32)
-        target_ulong pte = ldl_phys(cs->as, pte_addr);
+        target_ulong pte = address_space_ldl(cs->as, pte_addr, attrs, &res);
 #elif defined(TARGET_RISCV64)
-        target_ulong pte = ldq_phys(cs->as, pte_addr);
+        target_ulong pte = address_space_ldq(cs->as, pte_addr, attrs, &res);
 #endif
+        if (res != MEMTX_OK) {
+            return TRANSLATE_FAIL;
+        }
+
         hwaddr ppn = pte >> PTE_PPN_SHIFT;
 
         if (!(pte & PTE_V)) {
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 03/18] RISC-V: Implement cpu_do_transaction_failed
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 01/18] riscv: Skip checking CSR privilege level in debugger mode Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 02/18] RISC-V: Handle bus errors in the page table walker Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 04/18] riscv: hw: Drop "clock-frequency" property of cpu nodes Palmer Dabbelt
                   ` (15 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, Richard Henderson, qemu-devel,
	Alistair Francis, ilippe=20Mathieu-Daud=C3=A9?=

This converts our port over from cpu_do_unassigned_access to
cpu_do_transaction_failed, as cpu_do_unassigned_access has been
deprecated.

Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/cpu.c        |  2 +-
 target/riscv/cpu.h        |  7 +++++--
 target/riscv/cpu_helper.c | 11 +++++++----
 3 files changed, 13 insertions(+), 7 deletions(-)

diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index f13e298a36..3939963b71 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -484,7 +484,7 @@ static void riscv_cpu_class_init(ObjectClass *c, void *data)
     cc->gdb_stop_before_watchpoint = true;
     cc->disas_set_info = riscv_cpu_disas_set_info;
 #ifndef CONFIG_USER_ONLY
-    cc->do_unassigned_access = riscv_cpu_unassigned_access;
+    cc->do_transaction_failed = riscv_cpu_do_transaction_failed;
     cc->do_unaligned_access = riscv_cpu_do_unaligned_access;
     cc->get_phys_page_debug = riscv_cpu_get_phys_page_debug;
 #endif
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 124ed33ee4..8c64c68538 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -264,8 +264,11 @@ void  riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
 bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
                         MMUAccessType access_type, int mmu_idx,
                         bool probe, uintptr_t retaddr);
-void riscv_cpu_unassigned_access(CPUState *cpu, hwaddr addr, bool is_write,
-                                 bool is_exec, int unused, unsigned size);
+void riscv_cpu_do_transaction_failed(CPUState *cs, hwaddr physaddr,
+                                     vaddr addr, unsigned size,
+                                     MMUAccessType access_type,
+                                     int mmu_idx, MemTxAttrs attrs,
+                                     MemTxResult response, uintptr_t retaddr);
 char *riscv_isa_string(RISCVCPU *cpu);
 void riscv_cpu_list(void);
 
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index c82e7ed52b..917252f71b 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -408,20 +408,23 @@ hwaddr riscv_cpu_get_phys_page_debug(CPUState *cs, vaddr addr)
     return phys_addr;
 }
 
-void riscv_cpu_unassigned_access(CPUState *cs, hwaddr addr, bool is_write,
-                                 bool is_exec, int unused, unsigned size)
+void riscv_cpu_do_transaction_failed(CPUState *cs, hwaddr physaddr,
+                                     vaddr addr, unsigned size,
+                                     MMUAccessType access_type,
+                                     int mmu_idx, MemTxAttrs attrs,
+                                     MemTxResult response, uintptr_t retaddr)
 {
     RISCVCPU *cpu = RISCV_CPU(cs);
     CPURISCVState *env = &cpu->env;
 
-    if (is_write) {
+    if (access_type == MMU_DATA_STORE) {
         cs->exception_index = RISCV_EXCP_STORE_AMO_ACCESS_FAULT;
     } else {
         cs->exception_index = RISCV_EXCP_LOAD_ACCESS_FAULT;
     }
 
     env->badaddr = addr;
-    riscv_raise_exception(&cpu->env, cs->exception_index, GETPC());
+    riscv_raise_exception(&cpu->env, cs->exception_index, retaddr);
 }
 
 void riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 04/18] riscv: hw: Drop "clock-frequency" property of cpu nodes
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (2 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 03/18] RISC-V: Implement cpu_do_transaction_failed Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 05/18] riscv: sifive_u: Add ethernet0 to the aliases node Palmer Dabbelt
                   ` (14 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Bin Meng <bmeng.cn@gmail.com>

The "clock-frequency" property of cpu nodes isn't required. Drop it.

This is to keep in sync with Linux kernel commit below:
https://patchwork.kernel.org/patch/11133031/

Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c         | 2 --
 hw/riscv/spike.c            | 2 --
 hw/riscv/virt.c             | 2 --
 include/hw/riscv/sifive_u.h | 1 -
 include/hw/riscv/spike.h    | 4 ----
 include/hw/riscv/virt.h     | 4 ----
 6 files changed, 15 deletions(-)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index 9f8e84bf2e..02dd76176e 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -151,8 +151,6 @@ static void create_fdt(SiFiveUState *s, const struct MemmapEntry *memmap,
         char *intc = g_strdup_printf("/cpus/cpu@%d/interrupt-controller", cpu);
         char *isa;
         qemu_fdt_add_subnode(fdt, nodename);
-        qemu_fdt_setprop_cell(fdt, nodename, "clock-frequency",
-                              SIFIVE_U_CLOCK_FREQ);
         /* cpu 0 is the management hart that does not have mmu */
         if (cpu != 0) {
             qemu_fdt_setprop_string(fdt, nodename, "mmu-type", "riscv,sv48");
diff --git a/hw/riscv/spike.c b/hw/riscv/spike.c
index d60415d190..8bbffbcd0f 100644
--- a/hw/riscv/spike.c
+++ b/hw/riscv/spike.c
@@ -102,8 +102,6 @@ static void create_fdt(SpikeState *s, const struct MemmapEntry *memmap,
         char *intc = g_strdup_printf("/cpus/cpu@%d/interrupt-controller", cpu);
         char *isa = riscv_isa_string(&s->soc.harts[cpu]);
         qemu_fdt_add_subnode(fdt, nodename);
-        qemu_fdt_setprop_cell(fdt, nodename, "clock-frequency",
-                              SPIKE_CLOCK_FREQ);
         qemu_fdt_setprop_string(fdt, nodename, "mmu-type", "riscv,sv48");
         qemu_fdt_setprop_string(fdt, nodename, "riscv,isa", isa);
         qemu_fdt_setprop_string(fdt, nodename, "compatible", "riscv");
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
index d36f5625ec..13030619d4 100644
--- a/hw/riscv/virt.c
+++ b/hw/riscv/virt.c
@@ -161,8 +161,6 @@ static void create_fdt(RISCVVirtState *s, const struct MemmapEntry *memmap,
         char *intc = g_strdup_printf("/cpus/cpu@%d/interrupt-controller", cpu);
         char *isa = riscv_isa_string(&s->soc.harts[cpu]);
         qemu_fdt_add_subnode(fdt, nodename);
-        qemu_fdt_setprop_cell(fdt, nodename, "clock-frequency",
-                              VIRT_CLOCK_FREQ);
         qemu_fdt_setprop_string(fdt, nodename, "mmu-type", "riscv,sv48");
         qemu_fdt_setprop_string(fdt, nodename, "riscv,isa", isa);
         qemu_fdt_setprop_string(fdt, nodename, "compatible", "riscv");
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
index e4df298c23..4850805ee7 100644
--- a/include/hw/riscv/sifive_u.h
+++ b/include/hw/riscv/sifive_u.h
@@ -75,7 +75,6 @@ enum {
 };
 
 enum {
-    SIFIVE_U_CLOCK_FREQ = 1000000000,
     SIFIVE_U_HFCLK_FREQ = 33333333,
     SIFIVE_U_RTCCLK_FREQ = 1000000
 };
diff --git a/include/hw/riscv/spike.h b/include/hw/riscv/spike.h
index 03d870363c..dc770421bc 100644
--- a/include/hw/riscv/spike.h
+++ b/include/hw/riscv/spike.h
@@ -38,10 +38,6 @@ enum {
     SPIKE_DRAM
 };
 
-enum {
-    SPIKE_CLOCK_FREQ = 1000000000
-};
-
 #if defined(TARGET_RISCV32)
 #define SPIKE_V1_09_1_CPU TYPE_RISCV_CPU_RV32GCSU_V1_09_1
 #define SPIKE_V1_10_0_CPU TYPE_RISCV_CPU_RV32GCSU_V1_10_0
diff --git a/include/hw/riscv/virt.h b/include/hw/riscv/virt.h
index 6e5fbe5d3b..68978a13e8 100644
--- a/include/hw/riscv/virt.h
+++ b/include/hw/riscv/virt.h
@@ -55,10 +55,6 @@ enum {
     VIRTIO_NDEV = 0x35 /* Arbitrary maximum number of interrupts */
 };
 
-enum {
-    VIRT_CLOCK_FREQ = 1000000000
-};
-
 #define VIRT_PLIC_HART_CONFIG "MS"
 #define VIRT_PLIC_NUM_SOURCES 127
 #define VIRT_PLIC_NUM_PRIORITIES 7
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 05/18] riscv: sifive_u: Add ethernet0 to the aliases node
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (3 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 04/18] riscv: hw: Drop "clock-frequency" property of cpu nodes Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 06/18] linux-user/riscv: Propagate fault address Palmer Dabbelt
                   ` (13 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, qemu-devel, Alistair Francis,
	Bin Meng, ilippe=20Mathieu-Daud=C3=A9?=

From: Bin Meng <bmeng.cn@gmail.com>

U-Boot expects this alias to be in place in order to fix up the mac
address of the ethernet node.

This is to keep in sync with Linux kernel commit below:
https://patchwork.kernel.org/patch/11133033/

Signed-off-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index 02dd76176e..1ac51e3632 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -270,6 +270,10 @@ static void create_fdt(SiFiveUState *s, const struct MemmapEntry *memmap,
         s->soc.gem.conf.macaddr.a, ETH_ALEN);
     qemu_fdt_setprop_cell(fdt, nodename, "#address-cells", 1);
     qemu_fdt_setprop_cell(fdt, nodename, "#size-cells", 0);
+
+    qemu_fdt_add_subnode(fdt, "/aliases");
+    qemu_fdt_setprop_string(fdt, "/aliases", "ethernet0", nodename);
+
     g_free(nodename);
 
     nodename = g_strdup_printf("/soc/ethernet@%lx/ethernet-phy@0",
@@ -297,7 +301,6 @@ static void create_fdt(SiFiveUState *s, const struct MemmapEntry *memmap,
         qemu_fdt_setprop_string(fdt, "/chosen", "bootargs", cmdline);
     }
 
-    qemu_fdt_add_subnode(fdt, "/aliases");
     qemu_fdt_setprop_string(fdt, "/aliases", "serial0", nodename);
 
     g_free(nodename);
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 06/18] linux-user/riscv: Propagate fault address
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (4 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 05/18] riscv: sifive_u: Add ethernet0 to the aliases node Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 07/18] riscv/sifive_u: Add L2-LIM cache memory Palmer Dabbelt
                   ` (12 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell; +Cc: Giuseppe Musacchio, Palmer Dabbelt, qemu-riscv, qemu-devel

From: Giuseppe Musacchio <thatlemon@gmail.com>

The CPU loop tagged all the queued signals as QEMU_SI_KILL while it was
filling the `_sigfault` part of `siginfo`: this caused QEMU to copy the
wrong fields over to the userspace program.

Make sure the fault address recorded by the MMU is is stored in the CPU
environment structure.

In case of memory faults store the exception address into `siginfo`.

Signed-off-by: Giuseppe Musacchio <thatlemon@gmail.com>
Reviewed-by: Palmer Dabbelt <palmer@sifive.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 linux-user/riscv/cpu_loop.c | 3 ++-
 target/riscv/cpu_helper.c   | 5 ++++-
 2 files changed, 6 insertions(+), 2 deletions(-)

diff --git a/linux-user/riscv/cpu_loop.c b/linux-user/riscv/cpu_loop.c
index 12aa3c0f16..aa9e437875 100644
--- a/linux-user/riscv/cpu_loop.c
+++ b/linux-user/riscv/cpu_loop.c
@@ -89,6 +89,7 @@ void cpu_loop(CPURISCVState *env)
         case RISCV_EXCP_STORE_PAGE_FAULT:
             signum = TARGET_SIGSEGV;
             sigcode = TARGET_SEGV_MAPERR;
+            sigaddr = env->badaddr;
             break;
         case EXCP_DEBUG:
         gdbstep:
@@ -108,7 +109,7 @@ void cpu_loop(CPURISCVState *env)
                 .si_code = sigcode,
                 ._sifields._sigfault._addr = sigaddr
             };
-            queue_signal(env, info.si_signo, QEMU_SI_KILL, &info);
+            queue_signal(env, info.si_signo, QEMU_SI_FAULT, &info);
         }
 
         process_pending_signals(env);
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 917252f71b..f13131a51b 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -455,9 +455,9 @@ bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
                         MMUAccessType access_type, int mmu_idx,
                         bool probe, uintptr_t retaddr)
 {
-#ifndef CONFIG_USER_ONLY
     RISCVCPU *cpu = RISCV_CPU(cs);
     CPURISCVState *env = &cpu->env;
+#ifndef CONFIG_USER_ONLY
     hwaddr pa = 0;
     int prot;
     bool pmp_violation = false;
@@ -508,7 +508,10 @@ bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
     case MMU_DATA_STORE:
         cs->exception_index = RISCV_EXCP_STORE_PAGE_FAULT;
         break;
+    default:
+        g_assert_not_reached();
     }
+    env->badaddr = address;
     cpu_loop_exit_restore(cs, retaddr);
 #endif
 }
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 07/18] riscv/sifive_u: Add L2-LIM cache memory
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (5 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 06/18] linux-user/riscv: Propagate fault address Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 08/18] riscv/sifive_u: Add QSPI memory region Palmer Dabbelt
                   ` (11 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

On reset only a single L2 cache way is enabled, the others are exposed
as memory that can be used by early boot firmware. This L2 region is
generally disabled using the WayEnable register at a later stage in the
boot process. To allow firmware to target QEMU and the HiFive Unleashed
let's add the L2 LIM (LooselyIntegrated Memory).

Ideally we would want to adjust the size of this chunk of memory as the
L2 Cache Controller WayEnable register is incremented. Unfortunately I
don't see a nice way to handle reducing or blocking out the L2 LIM while
still allowing it be re returned to all enabled from a reset.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c         | 16 ++++++++++++++++
 include/hw/riscv/sifive_u.h |  1 +
 2 files changed, 17 insertions(+)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index 1ac51e3632..fbaa3a234e 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -65,6 +65,7 @@ static const struct MemmapEntry {
     [SIFIVE_U_DEBUG] =    {        0x0,      0x100 },
     [SIFIVE_U_MROM] =     {     0x1000,    0x11000 },
     [SIFIVE_U_CLINT] =    {  0x2000000,    0x10000 },
+    [SIFIVE_U_L2LIM] =    {  0x8000000,  0x2000000 },
     [SIFIVE_U_PLIC] =     {  0xc000000,  0x4000000 },
     [SIFIVE_U_PRCI] =     { 0x10000000,     0x1000 },
     [SIFIVE_U_UART0] =    { 0x10010000,     0x1000 },
@@ -432,6 +433,7 @@ static void riscv_sifive_u_soc_realize(DeviceState *dev, Error **errp)
     const struct MemmapEntry *memmap = sifive_u_memmap;
     MemoryRegion *system_memory = get_system_memory();
     MemoryRegion *mask_rom = g_new(MemoryRegion, 1);
+    MemoryRegion *l2lim_mem = g_new(MemoryRegion, 1);
     qemu_irq plic_gpios[SIFIVE_U_PLIC_NUM_SOURCES];
     char *plic_hart_config;
     size_t plic_hart_config_len;
@@ -460,6 +462,20 @@ static void riscv_sifive_u_soc_realize(DeviceState *dev, Error **errp)
     memory_region_add_subregion(system_memory, memmap[SIFIVE_U_MROM].base,
                                 mask_rom);
 
+    /*
+     * Add L2-LIM at reset size.
+     * This should be reduced in size as the L2 Cache Controller WayEnable
+     * register is incremented. Unfortunately I don't see a nice (or any) way
+     * to handle reducing or blocking out the L2 LIM while still allowing it
+     * be re returned to all enabled after a reset. For the time being, just
+     * leave it enabled all the time. This won't break anything, but will be
+     * too generous to misbehaving guests.
+     */
+    memory_region_init_ram(l2lim_mem, NULL, "riscv.sifive.u.l2lim",
+                           memmap[SIFIVE_U_L2LIM].size, &error_fatal);
+    memory_region_add_subregion(system_memory, memmap[SIFIVE_U_L2LIM].base,
+                                l2lim_mem);
+
     /* create PLIC hart topology configuration string */
     plic_hart_config_len = (strlen(SIFIVE_U_PLIC_HART_CONFIG) + 1) *
                            ms->smp.cpus;
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
index 4850805ee7..66ee76a780 100644
--- a/include/hw/riscv/sifive_u.h
+++ b/include/hw/riscv/sifive_u.h
@@ -58,6 +58,7 @@ enum {
     SIFIVE_U_DEBUG,
     SIFIVE_U_MROM,
     SIFIVE_U_CLINT,
+    SIFIVE_U_L2LIM,
     SIFIVE_U_PLIC,
     SIFIVE_U_PRCI,
     SIFIVE_U_UART0,
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 08/18] riscv/sifive_u: Add QSPI memory region
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (6 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 07/18] riscv/sifive_u: Add L2-LIM cache memory Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 09/18] riscv/sifive_u: Manually define the machine Palmer Dabbelt
                   ` (10 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

The HiFive Unleashed uses is25wp256 SPI NOR flash. There is currently no
model of this in QEMU, so to allow boot firmware developers to use QEMU
to target the Unleashed let's add a chunk of memory to represent the QSPI0
memory mapped flash. This can be targeted using QEMU's -device loader
command line option.

In the future we can look at adding a model for the is25wp256 flash.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c         | 8 ++++++++
 include/hw/riscv/sifive_u.h | 1 +
 2 files changed, 9 insertions(+)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index fbaa3a234e..a32d6773a8 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -71,6 +71,7 @@ static const struct MemmapEntry {
     [SIFIVE_U_UART0] =    { 0x10010000,     0x1000 },
     [SIFIVE_U_UART1] =    { 0x10011000,     0x1000 },
     [SIFIVE_U_OTP] =      { 0x10070000,     0x1000 },
+    [SIFIVE_U_FLASH0] =   { 0x20000000, 0x10000000 },
     [SIFIVE_U_DRAM] =     { 0x80000000,        0x0 },
     [SIFIVE_U_GEM] =      { 0x10090000,     0x2000 },
     [SIFIVE_U_GEM_MGMT] = { 0x100a0000,     0x1000 },
@@ -314,6 +315,7 @@ static void riscv_sifive_u_init(MachineState *machine)
     SiFiveUState *s = g_new0(SiFiveUState, 1);
     MemoryRegion *system_memory = get_system_memory();
     MemoryRegion *main_mem = g_new(MemoryRegion, 1);
+    MemoryRegion *flash0 = g_new(MemoryRegion, 1);
     int i;
 
     /* Initialize SoC */
@@ -329,6 +331,12 @@ static void riscv_sifive_u_init(MachineState *machine)
     memory_region_add_subregion(system_memory, memmap[SIFIVE_U_DRAM].base,
                                 main_mem);
 
+    /* register QSPI0 Flash */
+    memory_region_init_ram(flash0, NULL, "riscv.sifive.u.flash0",
+                           memmap[SIFIVE_U_FLASH0].size, &error_fatal);
+    memory_region_add_subregion(system_memory, memmap[SIFIVE_U_FLASH0].base,
+                                flash0);
+
     /* create device tree */
     create_fdt(s, memmap, machine->ram_size, machine->kernel_cmdline);
 
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
index 66ee76a780..0062276190 100644
--- a/include/hw/riscv/sifive_u.h
+++ b/include/hw/riscv/sifive_u.h
@@ -64,6 +64,7 @@ enum {
     SIFIVE_U_UART0,
     SIFIVE_U_UART1,
     SIFIVE_U_OTP,
+    SIFIVE_U_FLASH0,
     SIFIVE_U_DRAM,
     SIFIVE_U_GEM,
     SIFIVE_U_GEM_MGMT
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 09/18] riscv/sifive_u: Manually define the machine
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (7 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 08/18] riscv/sifive_u: Add QSPI memory region Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 10/18] riscv/sifive_u: Add the start-in-flash property Palmer Dabbelt
                   ` (9 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

Instead of using the DEFINE_MACHINE() macro to define the machine let's
do it manually. This allows us to specify machine properties.

This patch is no functional change.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c         | 44 ++++++++++++++++++++++++++-----------
 include/hw/riscv/sifive_u.h |  7 +++++-
 2 files changed, 37 insertions(+), 14 deletions(-)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index a32d6773a8..eb4124f5b4 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -311,8 +311,7 @@ static void create_fdt(SiFiveUState *s, const struct MemmapEntry *memmap,
 static void riscv_sifive_u_init(MachineState *machine)
 {
     const struct MemmapEntry *memmap = sifive_u_memmap;
-
-    SiFiveUState *s = g_new0(SiFiveUState, 1);
+    SiFiveUState *s = RISCV_U_MACHINE(machine);
     MemoryRegion *system_memory = get_system_memory();
     MemoryRegion *main_mem = g_new(MemoryRegion, 1);
     MemoryRegion *flash0 = g_new(MemoryRegion, 1);
@@ -434,6 +433,10 @@ static void riscv_sifive_u_soc_init(Object *obj)
                           TYPE_CADENCE_GEM);
 }
 
+static void riscv_sifive_u_machine_instance_init(Object *obj)
+{
+}
+
 static void riscv_sifive_u_soc_realize(DeviceState *dev, Error **errp)
 {
     MachineState *ms = MACHINE(qdev_get_machine());
@@ -547,17 +550,6 @@ static void riscv_sifive_u_soc_realize(DeviceState *dev, Error **errp)
         memmap[SIFIVE_U_GEM_MGMT].base, memmap[SIFIVE_U_GEM_MGMT].size);
 }
 
-static void riscv_sifive_u_machine_init(MachineClass *mc)
-{
-    mc->desc = "RISC-V Board compatible with SiFive U SDK";
-    mc->init = riscv_sifive_u_init;
-    mc->max_cpus = SIFIVE_U_MANAGEMENT_CPU_COUNT + SIFIVE_U_COMPUTE_CPU_COUNT;
-    mc->min_cpus = SIFIVE_U_MANAGEMENT_CPU_COUNT + 1;
-    mc->default_cpus = mc->min_cpus;
-}
-
-DEFINE_MACHINE("sifive_u", riscv_sifive_u_machine_init)
-
 static void riscv_sifive_u_soc_class_init(ObjectClass *oc, void *data)
 {
     DeviceClass *dc = DEVICE_CLASS(oc);
@@ -581,3 +573,29 @@ static void riscv_sifive_u_soc_register_types(void)
 }
 
 type_init(riscv_sifive_u_soc_register_types)
+
+static void riscv_sifive_u_machine_class_init(ObjectClass *oc, void *data)
+{
+    MachineClass *mc = MACHINE_CLASS(oc);
+
+    mc->desc = "RISC-V Board compatible with SiFive U SDK";
+    mc->init = riscv_sifive_u_init;
+    mc->max_cpus = SIFIVE_U_MANAGEMENT_CPU_COUNT + SIFIVE_U_COMPUTE_CPU_COUNT;
+    mc->min_cpus = SIFIVE_U_MANAGEMENT_CPU_COUNT + 1;
+    mc->default_cpus = mc->min_cpus;
+}
+
+static const TypeInfo riscv_sifive_u_machine_typeinfo = {
+    .name       = MACHINE_TYPE_NAME("sifive_u"),
+    .parent     = TYPE_MACHINE,
+    .class_init = riscv_sifive_u_machine_class_init,
+    .instance_init = riscv_sifive_u_machine_instance_init,
+    .instance_size = sizeof(SiFiveUState),
+};
+
+static void riscv_sifive_u_machine_init_register_types(void)
+{
+    type_register_static(&riscv_sifive_u_machine_typeinfo);
+}
+
+type_init(riscv_sifive_u_machine_init_register_types)
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
index 0062276190..794b958dcc 100644
--- a/include/hw/riscv/sifive_u.h
+++ b/include/hw/riscv/sifive_u.h
@@ -44,12 +44,17 @@ typedef struct SiFiveUSoCState {
     CadenceGEMState gem;
 } SiFiveUSoCState;
 
+#define TYPE_RISCV_U_MACHINE MACHINE_TYPE_NAME("sifive_u")
+#define RISCV_U_MACHINE(obj) \
+    OBJECT_CHECK(SiFiveUState, (obj), TYPE_RISCV_U_MACHINE)
+
 typedef struct SiFiveUState {
     /*< private >*/
-    SysBusDevice parent_obj;
+    MachineState parent_obj;
 
     /*< public >*/
     SiFiveUSoCState soc;
+
     void *fdt;
     int fdt_size;
 } SiFiveUState;
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 10/18] riscv/sifive_u: Add the start-in-flash property
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (8 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 09/18] riscv/sifive_u: Manually define the machine Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 11/18] riscv/virt: Manually define the machine Palmer Dabbelt
                   ` (8 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

Add a property that when set to true QEMU will jump from the ROM code to
the start of flash memory instead of DRAM which is the default
behaviour.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/sifive_u.c         | 30 +++++++++++++++++++++++++++++-
 include/hw/riscv/sifive_u.h |  2 ++
 2 files changed, 31 insertions(+), 1 deletion(-)

diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
index eb4124f5b4..9552abf4dd 100644
--- a/hw/riscv/sifive_u.c
+++ b/hw/riscv/sifive_u.c
@@ -315,6 +315,7 @@ static void riscv_sifive_u_init(MachineState *machine)
     MemoryRegion *system_memory = get_system_memory();
     MemoryRegion *main_mem = g_new(MemoryRegion, 1);
     MemoryRegion *flash0 = g_new(MemoryRegion, 1);
+    target_ulong start_addr = memmap[SIFIVE_U_DRAM].base;
     int i;
 
     /* Initialize SoC */
@@ -357,6 +358,10 @@ static void riscv_sifive_u_init(MachineState *machine)
         }
     }
 
+    if (s->start_in_flash) {
+        start_addr = memmap[SIFIVE_U_FLASH0].base;
+    }
+
     /* reset vector */
     uint32_t reset_vec[8] = {
         0x00000297,                    /* 1:  auipc  t0, %pcrel_hi(dtb) */
@@ -369,7 +374,7 @@ static void riscv_sifive_u_init(MachineState *machine)
 #endif
         0x00028067,                    /*     jr     t0 */
         0x00000000,
-        memmap[SIFIVE_U_DRAM].base, /* start: .dword DRAM_BASE */
+        start_addr,                    /* start: .dword */
         0x00000000,
                                        /* dtb: */
     };
@@ -433,8 +438,31 @@ static void riscv_sifive_u_soc_init(Object *obj)
                           TYPE_CADENCE_GEM);
 }
 
+static bool sifive_u_get_start_in_flash(Object *obj, Error **errp)
+{
+    SiFiveUState *s = RISCV_U_MACHINE(obj);
+
+    return s->start_in_flash;
+}
+
+static void sifive_u_set_start_in_flash(Object *obj, bool value, Error **errp)
+{
+    SiFiveUState *s = RISCV_U_MACHINE(obj);
+
+    s->start_in_flash = value;
+}
+
 static void riscv_sifive_u_machine_instance_init(Object *obj)
 {
+    SiFiveUState *s = RISCV_U_MACHINE(obj);
+
+    s->start_in_flash = false;
+    object_property_add_bool(obj, "start-in-flash", sifive_u_get_start_in_flash,
+                             sifive_u_set_start_in_flash, NULL);
+    object_property_set_description(obj, "start-in-flash",
+                                    "Set on to tell QEMU's ROM to jump to " \
+                                    "flash. Otherwise QEMU will jump to DRAM",
+                                    NULL);
 }
 
 static void riscv_sifive_u_soc_realize(DeviceState *dev, Error **errp)
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
index 794b958dcc..82667b5746 100644
--- a/include/hw/riscv/sifive_u.h
+++ b/include/hw/riscv/sifive_u.h
@@ -57,6 +57,8 @@ typedef struct SiFiveUState {
 
     void *fdt;
     int fdt_size;
+
+    bool start_in_flash;
 } SiFiveUState;
 
 enum {
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 11/18] riscv/virt: Manually define the machine
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (9 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 10/18] riscv/sifive_u: Add the start-in-flash property Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 12/18] riscv/virt: Add the PFlash CFI01 device Palmer Dabbelt
                   ` (7 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

Instead of using the DEFINE_MACHINE() macro to define the machine let's
do it manually. This allows us to use the machine object to create
RISCVVirtState. This is required to add children and aliases to the
machine.

This patch is no functional change.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/virt.c         | 30 ++++++++++++++++++++++++------
 include/hw/riscv/virt.h |  7 ++++++-
 2 files changed, 30 insertions(+), 7 deletions(-)

diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
index 13030619d4..bdbdfadd29 100644
--- a/hw/riscv/virt.c
+++ b/hw/riscv/virt.c
@@ -360,8 +360,7 @@ static inline DeviceState *gpex_pcie_init(MemoryRegion *sys_mem,
 static void riscv_virt_board_init(MachineState *machine)
 {
     const struct MemmapEntry *memmap = virt_memmap;
-
-    RISCVVirtState *s = g_new0(RISCVVirtState, 1);
+    RISCVVirtState *s = RISCV_VIRT_MACHINE(machine);
     MemoryRegion *system_memory = get_system_memory();
     MemoryRegion *main_mem = g_new(MemoryRegion, 1);
     MemoryRegion *mask_rom = g_new(MemoryRegion, 1);
@@ -497,12 +496,31 @@ static void riscv_virt_board_init(MachineState *machine)
     g_free(plic_hart_config);
 }
 
-static void riscv_virt_board_machine_init(MachineClass *mc)
+static void riscv_virt_machine_instance_init(Object *obj)
 {
-    mc->desc = "RISC-V VirtIO Board (Privileged ISA v1.10)";
+}
+
+static void riscv_virt_machine_class_init(ObjectClass *oc, void *data)
+{
+    MachineClass *mc = MACHINE_CLASS(oc);
+
+    mc->desc = "RISC-V VirtIO board";
     mc->init = riscv_virt_board_init;
-    mc->max_cpus = 8; /* hardcoded limit in BBL */
+    mc->max_cpus = 8;
     mc->default_cpu_type = VIRT_CPU;
 }
 
-DEFINE_MACHINE("virt", riscv_virt_board_machine_init)
+static const TypeInfo riscv_virt_machine_typeinfo = {
+    .name       = MACHINE_TYPE_NAME("virt"),
+    .parent     = TYPE_MACHINE,
+    .class_init = riscv_virt_machine_class_init,
+    .instance_init = riscv_virt_machine_instance_init,
+    .instance_size = sizeof(RISCVVirtState),
+};
+
+static void riscv_virt_machine_init_register_types(void)
+{
+    type_register_static(&riscv_virt_machine_typeinfo);
+}
+
+type_init(riscv_virt_machine_init_register_types)
diff --git a/include/hw/riscv/virt.h b/include/hw/riscv/virt.h
index 68978a13e8..3d875305d3 100644
--- a/include/hw/riscv/virt.h
+++ b/include/hw/riscv/virt.h
@@ -22,13 +22,18 @@
 #include "hw/riscv/riscv_hart.h"
 #include "hw/sysbus.h"
 
+#define TYPE_RISCV_VIRT_MACHINE MACHINE_TYPE_NAME("virt")
+#define RISCV_VIRT_MACHINE(obj) \
+    OBJECT_CHECK(RISCVVirtState, (obj), TYPE_RISCV_VIRT_MACHINE)
+
 typedef struct {
     /*< private >*/
-    SysBusDevice parent_obj;
+    MachineState parent;
 
     /*< public >*/
     RISCVHartArrayState soc;
     DeviceState *plic;
+
     void *fdt;
     int fdt_size;
 } RISCVVirtState;
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 12/18] riscv/virt: Add the PFlash CFI01 device
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (10 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 11/18] riscv/virt: Manually define the machine Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 13/18] riscv/virt: Jump to pflash if specified Palmer Dabbelt
                   ` (6 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Alistair Francis, Bin Meng, qemu-riscv, qemu-devel, Palmer Dabbelt

From: Alistair Francis <alistair.francis@wdc.com>

Add the CFI01 PFlash to the RISC-V virt board. This is the same PFlash
from the ARM Virt board and the implementation is based on the ARM Virt
board. This allows users to specify flash files from the command line.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/Kconfig        |  1 +
 hw/riscv/virt.c         | 86 +++++++++++++++++++++++++++++++++++++++++
 include/hw/riscv/virt.h |  3 ++
 3 files changed, 90 insertions(+)

diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
index fb19b2df3a..b12660b9f8 100644
--- a/hw/riscv/Kconfig
+++ b/hw/riscv/Kconfig
@@ -36,4 +36,5 @@ config RISCV_VIRT
     select SERIAL
     select VIRTIO_MMIO
     select PCI_EXPRESS_GENERIC_BRIDGE
+    select PFLASH_CFI01
     select SIFIVE
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
index bdbdfadd29..b2156abd6c 100644
--- a/hw/riscv/virt.c
+++ b/hw/riscv/virt.c
@@ -26,6 +26,7 @@
 #include "hw/boards.h"
 #include "hw/loader.h"
 #include "hw/sysbus.h"
+#include "hw/qdev-properties.h"
 #include "hw/char/serial.h"
 #include "target/riscv/cpu.h"
 #include "hw/riscv/riscv_hart.h"
@@ -61,12 +62,77 @@ static const struct MemmapEntry {
     [VIRT_PLIC] =        {  0xc000000,     0x4000000 },
     [VIRT_UART0] =       { 0x10000000,         0x100 },
     [VIRT_VIRTIO] =      { 0x10001000,        0x1000 },
+    [VIRT_FLASH] =       { 0x20000000,     0x2000000 },
     [VIRT_DRAM] =        { 0x80000000,           0x0 },
     [VIRT_PCIE_MMIO] =   { 0x40000000,    0x40000000 },
     [VIRT_PCIE_PIO] =    { 0x03000000,    0x00010000 },
     [VIRT_PCIE_ECAM] =   { 0x30000000,    0x10000000 },
 };
 
+#define VIRT_FLASH_SECTOR_SIZE (256 * KiB)
+
+static PFlashCFI01 *virt_flash_create1(RISCVVirtState *s,
+                                       const char *name,
+                                       const char *alias_prop_name)
+{
+    /*
+     * Create a single flash device.  We use the same parameters as
+     * the flash devices on the ARM virt board.
+     */
+    DeviceState *dev = qdev_create(NULL, TYPE_PFLASH_CFI01);
+
+    qdev_prop_set_uint64(dev, "sector-length", VIRT_FLASH_SECTOR_SIZE);
+    qdev_prop_set_uint8(dev, "width", 4);
+    qdev_prop_set_uint8(dev, "device-width", 2);
+    qdev_prop_set_bit(dev, "big-endian", false);
+    qdev_prop_set_uint16(dev, "id0", 0x89);
+    qdev_prop_set_uint16(dev, "id1", 0x18);
+    qdev_prop_set_uint16(dev, "id2", 0x00);
+    qdev_prop_set_uint16(dev, "id3", 0x00);
+    qdev_prop_set_string(dev, "name", name);
+
+    object_property_add_child(OBJECT(s), name, OBJECT(dev),
+                              &error_abort);
+    object_property_add_alias(OBJECT(s), alias_prop_name,
+                              OBJECT(dev), "drive", &error_abort);
+
+    return PFLASH_CFI01(dev);
+}
+
+static void virt_flash_create(RISCVVirtState *s)
+{
+    s->flash[0] = virt_flash_create1(s, "virt.flash0", "pflash0");
+    s->flash[1] = virt_flash_create1(s, "virt.flash1", "pflash1");
+}
+
+static void virt_flash_map1(PFlashCFI01 *flash,
+                            hwaddr base, hwaddr size,
+                            MemoryRegion *sysmem)
+{
+    DeviceState *dev = DEVICE(flash);
+
+    assert(size % VIRT_FLASH_SECTOR_SIZE == 0);
+    assert(size / VIRT_FLASH_SECTOR_SIZE <= UINT32_MAX);
+    qdev_prop_set_uint32(dev, "num-blocks", size / VIRT_FLASH_SECTOR_SIZE);
+    qdev_init_nofail(dev);
+
+    memory_region_add_subregion(sysmem, base,
+                                sysbus_mmio_get_region(SYS_BUS_DEVICE(dev),
+                                                       0));
+}
+
+static void virt_flash_map(RISCVVirtState *s,
+                           MemoryRegion *sysmem)
+{
+    hwaddr flashsize = virt_memmap[VIRT_FLASH].size / 2;
+    hwaddr flashbase = virt_memmap[VIRT_FLASH].base;
+
+    virt_flash_map1(s->flash[0], flashbase, flashsize,
+                    sysmem);
+    virt_flash_map1(s->flash[1], flashbase + flashsize, flashsize,
+                    sysmem);
+}
+
 static void create_pcie_irq_map(void *fdt, char *nodename,
                                 uint32_t plic_phandle)
 {
@@ -121,6 +187,8 @@ static void create_fdt(RISCVVirtState *s, const struct MemmapEntry *memmap,
     char *nodename;
     uint32_t plic_phandle, phandle = 1;
     int i;
+    hwaddr flashsize = virt_memmap[VIRT_FLASH].size / 2;
+    hwaddr flashbase = virt_memmap[VIRT_FLASH].base;
 
     fdt = s->fdt = create_device_tree(&s->fdt_size);
     if (!fdt) {
@@ -314,6 +382,15 @@ static void create_fdt(RISCVVirtState *s, const struct MemmapEntry *memmap,
         qemu_fdt_setprop_string(fdt, "/chosen", "bootargs", cmdline);
     }
     g_free(nodename);
+
+    nodename = g_strdup_printf("/flash@%" PRIx64, flashbase);
+    qemu_fdt_add_subnode(s->fdt, nodename);
+    qemu_fdt_setprop_string(s->fdt, nodename, "compatible", "cfi-flash");
+    qemu_fdt_setprop_sized_cells(s->fdt, nodename, "reg",
+                                 2, flashbase, 2, flashsize,
+                                 2, flashbase + flashsize, 2, flashsize);
+    qemu_fdt_setprop_cell(s->fdt, nodename, "bank-width", 4);
+    g_free(nodename);
 }
 
 
@@ -493,6 +570,15 @@ static void riscv_virt_board_init(MachineState *machine)
         0, qdev_get_gpio_in(DEVICE(s->plic), UART0_IRQ), 399193,
         serial_hd(0), DEVICE_LITTLE_ENDIAN);
 
+    virt_flash_create(s);
+
+    for (i = 0; i < ARRAY_SIZE(s->flash); i++) {
+        /* Map legacy -drive if=pflash to machine properties */
+        pflash_cfi01_legacy_drive(s->flash[i],
+                                  drive_get(IF_PFLASH, 0, i));
+    }
+    virt_flash_map(s, system_memory);
+
     g_free(plic_hart_config);
 }
 
diff --git a/include/hw/riscv/virt.h b/include/hw/riscv/virt.h
index 3d875305d3..b17048a93a 100644
--- a/include/hw/riscv/virt.h
+++ b/include/hw/riscv/virt.h
@@ -21,6 +21,7 @@
 
 #include "hw/riscv/riscv_hart.h"
 #include "hw/sysbus.h"
+#include "hw/block/flash.h"
 
 #define TYPE_RISCV_VIRT_MACHINE MACHINE_TYPE_NAME("virt")
 #define RISCV_VIRT_MACHINE(obj) \
@@ -33,6 +34,7 @@ typedef struct {
     /*< public >*/
     RISCVHartArrayState soc;
     DeviceState *plic;
+    PFlashCFI01 *flash[2];
 
     void *fdt;
     int fdt_size;
@@ -46,6 +48,7 @@ enum {
     VIRT_PLIC,
     VIRT_UART0,
     VIRT_VIRTIO,
+    VIRT_FLASH,
     VIRT_DRAM,
     VIRT_PCIE_MMIO,
     VIRT_PCIE_PIO,
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 13/18] riscv/virt: Jump to pflash if specified
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (11 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 12/18] riscv/virt: Add the PFlash CFI01 device Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 14/18] target/riscv: Tell gdbstub the correct number of CSRs Palmer Dabbelt
                   ` (5 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, qemu-devel, Alistair Francis,
	Bin Meng, ilippe=20Mathieu-Daud=C3=A9?=

From: Alistair Francis <alistair.francis@wdc.com>

If the user supplied pflash to QEMU then change the reset code to jump
to the pflash base address instead of the DRAM base address.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/virt.c | 11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)

diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
index b2156abd6c..cc8f311e6b 100644
--- a/hw/riscv/virt.c
+++ b/hw/riscv/virt.c
@@ -443,6 +443,7 @@ static void riscv_virt_board_init(MachineState *machine)
     MemoryRegion *mask_rom = g_new(MemoryRegion, 1);
     char *plic_hart_config;
     size_t plic_hart_config_len;
+    target_ulong start_addr = memmap[VIRT_DRAM].base;
     int i;
     unsigned int smp_cpus = machine->smp.cpus;
 
@@ -489,6 +490,14 @@ static void riscv_virt_board_init(MachineState *machine)
         }
     }
 
+    if (drive_get(IF_PFLASH, 0, 0)) {
+        /*
+         * Pflash was supplied, let's overwrite the address we jump to after
+         * reset to the base of the flash.
+         */
+        start_addr = virt_memmap[VIRT_FLASH].base;
+    }
+
     /* reset vector */
     uint32_t reset_vec[8] = {
         0x00000297,                  /* 1:  auipc  t0, %pcrel_hi(dtb) */
@@ -501,7 +510,7 @@ static void riscv_virt_board_init(MachineState *machine)
 #endif
         0x00028067,                  /*     jr     t0 */
         0x00000000,
-        memmap[VIRT_DRAM].base,      /* start: .dword memmap[VIRT_DRAM].base */
+        start_addr,                  /* start: .dword */
         0x00000000,
                                      /* dtb: */
     };
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 14/18] target/riscv: Tell gdbstub the correct number of CSRs
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (12 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 13/18] riscv/virt: Jump to pflash if specified Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:48 ` [PULL 15/18] target/riscv: Expose "priv" register for GDB for reads Palmer Dabbelt
                   ` (4 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Jonathan Behrens, Palmer Dabbelt, qemu-devel,
	Alistair Francis, Bin Meng

From: Jonathan Behrens <jonathan@fintelia.io>

If the number of registers reported to the gdbstub code does not match the
number in the associated XML file, then the register numbers used by the stub
may get out of sync with a remote GDB instance.

Signed-off-by: Jonathan Behrens <jonathan@fintelia.io>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/gdbstub.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/target/riscv/gdbstub.c b/target/riscv/gdbstub.c
index ded140e8d8..cb5bfd3d50 100644
--- a/target/riscv/gdbstub.c
+++ b/target/riscv/gdbstub.c
@@ -384,7 +384,7 @@ void riscv_cpu_register_gdb_regs_for_features(CPUState *cs)
     }
 
     gdb_register_coprocessor(cs, riscv_gdb_get_csr, riscv_gdb_set_csr,
-                             4096, "riscv-32bit-csr.xml", 0);
+                             240, "riscv-32bit-csr.xml", 0);
 #elif defined(TARGET_RISCV64)
     if (env->misa & RVF) {
         gdb_register_coprocessor(cs, riscv_gdb_get_fpu, riscv_gdb_set_fpu,
@@ -392,6 +392,6 @@ void riscv_cpu_register_gdb_regs_for_features(CPUState *cs)
     }
 
     gdb_register_coprocessor(cs, riscv_gdb_get_csr, riscv_gdb_set_csr,
-                             4096, "riscv-64bit-csr.xml", 0);
+                             240, "riscv-64bit-csr.xml", 0);
 #endif
 }
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 15/18] target/riscv: Expose "priv" register for GDB for reads
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (13 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 14/18] target/riscv: Tell gdbstub the correct number of CSRs Palmer Dabbelt
@ 2019-10-28 15:48 ` Palmer Dabbelt
  2019-10-28 15:49 ` [PULL 16/18] target/riscv: Make the priv register writable by GDB Palmer Dabbelt
                   ` (3 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:48 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Jonathan Behrens, Palmer Dabbelt, qemu-devel,
	Alistair Francis, Bin Meng

From: Jonathan Behrens <jonathan@fintelia.io>

This patch enables a debugger to read the current privilege level via a virtual
"priv" register. When compiled with CONFIG_USER_ONLY the register is still
visible but always reports the value zero.

Signed-off-by: Jonathan Behrens <jonathan@fintelia.io>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 configure                       |  4 ++--
 gdb-xml/riscv-32bit-virtual.xml | 11 +++++++++++
 gdb-xml/riscv-64bit-virtual.xml | 11 +++++++++++
 target/riscv/gdbstub.c          | 23 +++++++++++++++++++++++
 4 files changed, 47 insertions(+), 2 deletions(-)
 create mode 100644 gdb-xml/riscv-32bit-virtual.xml
 create mode 100644 gdb-xml/riscv-64bit-virtual.xml

diff --git a/configure b/configure
index 145fcabbb3..dc94026a3c 100755
--- a/configure
+++ b/configure
@@ -7526,13 +7526,13 @@ case "$target_name" in
     TARGET_BASE_ARCH=riscv
     TARGET_ABI_DIR=riscv
     mttcg=yes
-    gdb_xml_files="riscv-32bit-cpu.xml riscv-32bit-fpu.xml riscv-32bit-csr.xml"
+    gdb_xml_files="riscv-32bit-cpu.xml riscv-32bit-fpu.xml riscv-32bit-csr.xml riscv-32bit-virtual.xml"
   ;;
   riscv64)
     TARGET_BASE_ARCH=riscv
     TARGET_ABI_DIR=riscv
     mttcg=yes
-    gdb_xml_files="riscv-64bit-cpu.xml riscv-64bit-fpu.xml riscv-64bit-csr.xml"
+    gdb_xml_files="riscv-64bit-cpu.xml riscv-64bit-fpu.xml riscv-64bit-csr.xml riscv-64bit-virtual.xml"
   ;;
   sh4|sh4eb)
     TARGET_ARCH=sh4
diff --git a/gdb-xml/riscv-32bit-virtual.xml b/gdb-xml/riscv-32bit-virtual.xml
new file mode 100644
index 0000000000..905f1c555d
--- /dev/null
+++ b/gdb-xml/riscv-32bit-virtual.xml
@@ -0,0 +1,11 @@
+<?xml version="1.0"?>
+<!-- Copyright (C) 2018-2019 Free Software Foundation, Inc.
+
+     Copying and distribution of this file, with or without modification,
+     are permitted in any medium without royalty provided the copyright
+     notice and this notice are preserved.  -->
+
+<!DOCTYPE feature SYSTEM "gdb-target.dtd">
+<feature name="org.gnu.gdb.riscv.virtual">
+  <reg name="priv" bitsize="32"/>
+</feature>
diff --git a/gdb-xml/riscv-64bit-virtual.xml b/gdb-xml/riscv-64bit-virtual.xml
new file mode 100644
index 0000000000..62d86c237b
--- /dev/null
+++ b/gdb-xml/riscv-64bit-virtual.xml
@@ -0,0 +1,11 @@
+<?xml version="1.0"?>
+<!-- Copyright (C) 2018-2019 Free Software Foundation, Inc.
+
+     Copying and distribution of this file, with or without modification,
+     are permitted in any medium without royalty provided the copyright
+     notice and this notice are preserved.  -->
+
+<!DOCTYPE feature SYSTEM "gdb-target.dtd">
+<feature name="org.gnu.gdb.riscv.virtual">
+  <reg name="priv" bitsize="64"/>
+</feature>
diff --git a/target/riscv/gdbstub.c b/target/riscv/gdbstub.c
index cb5bfd3d50..1f71604b78 100644
--- a/target/riscv/gdbstub.c
+++ b/target/riscv/gdbstub.c
@@ -373,6 +373,23 @@ static int riscv_gdb_set_csr(CPURISCVState *env, uint8_t *mem_buf, int n)
     return 0;
 }
 
+static int riscv_gdb_get_virtual(CPURISCVState *cs, uint8_t *mem_buf, int n)
+{
+    if (n == 0) {
+#ifdef CONFIG_USER_ONLY
+        return gdb_get_regl(mem_buf, 0);
+#else
+        return gdb_get_regl(mem_buf, cs->priv);
+#endif
+    }
+    return 0;
+}
+
+static int riscv_gdb_set_virtual(CPURISCVState *cs, uint8_t *mem_buf, int n)
+{
+    return 0;
+}
+
 void riscv_cpu_register_gdb_regs_for_features(CPUState *cs)
 {
     RISCVCPU *cpu = RISCV_CPU(cs);
@@ -385,6 +402,9 @@ void riscv_cpu_register_gdb_regs_for_features(CPUState *cs)
 
     gdb_register_coprocessor(cs, riscv_gdb_get_csr, riscv_gdb_set_csr,
                              240, "riscv-32bit-csr.xml", 0);
+
+    gdb_register_coprocessor(cs, riscv_gdb_get_virtual, riscv_gdb_set_virtual,
+                             1, "riscv-32bit-virtual.xml", 0);
 #elif defined(TARGET_RISCV64)
     if (env->misa & RVF) {
         gdb_register_coprocessor(cs, riscv_gdb_get_fpu, riscv_gdb_set_fpu,
@@ -393,5 +413,8 @@ void riscv_cpu_register_gdb_regs_for_features(CPUState *cs)
 
     gdb_register_coprocessor(cs, riscv_gdb_get_csr, riscv_gdb_set_csr,
                              240, "riscv-64bit-csr.xml", 0);
+
+    gdb_register_coprocessor(cs, riscv_gdb_get_virtual, riscv_gdb_set_virtual,
+                             1, "riscv-64bit-virtual.xml", 0);
 #endif
 }
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 16/18] target/riscv: Make the priv register writable by GDB
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (14 preceding siblings ...)
  2019-10-28 15:48 ` [PULL 15/18] target/riscv: Expose "priv" register for GDB for reads Palmer Dabbelt
@ 2019-10-28 15:49 ` Palmer Dabbelt
  2019-10-28 15:49 ` [PULL 17/18] riscv/boot: Fix possible memory leak Palmer Dabbelt
                   ` (2 subsequent siblings)
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:49 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Jonathan Behrens, Palmer Dabbelt, qemu-devel,
	Alistair Francis, Bin Meng

From: Jonathan Behrens <jonathan@fintelia.io>

Currently only PRV_U, PRV_S and PRV_M are supported, so this patch ensures that
the privilege mode is set to one of them. Once support for the H-extension is
added, this code will also need to properly update the virtualization status
when switching between VU/VS-modes and M-mode.

Signed-off-by: Jonathan Behrens <jonathan@fintelia.io>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Tested-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/gdbstub.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/target/riscv/gdbstub.c b/target/riscv/gdbstub.c
index 1f71604b78..1a7947e019 100644
--- a/target/riscv/gdbstub.c
+++ b/target/riscv/gdbstub.c
@@ -387,6 +387,15 @@ static int riscv_gdb_get_virtual(CPURISCVState *cs, uint8_t *mem_buf, int n)
 
 static int riscv_gdb_set_virtual(CPURISCVState *cs, uint8_t *mem_buf, int n)
 {
+    if (n == 0) {
+#ifndef CONFIG_USER_ONLY
+        cs->priv = ldtul_p(mem_buf) & 0x3;
+        if (cs->priv == PRV_H) {
+            cs->priv = PRV_S;
+        }
+#endif
+        return sizeof(target_ulong);
+    }
     return 0;
 }
 
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 17/18] riscv/boot: Fix possible memory leak
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (15 preceding siblings ...)
  2019-10-28 15:49 ` [PULL 16/18] target/riscv: Make the priv register writable by GDB Palmer Dabbelt
@ 2019-10-28 15:49 ` Palmer Dabbelt
  2019-10-28 15:49 ` [PULL 18/18] target/riscv: PMP violation due to wrong size parameter Palmer Dabbelt
  2019-10-29  8:37 ` [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Peter Maydell
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:49 UTC (permalink / raw)
  To: Peter Maydell
  Cc: qemu-riscv, Palmer Dabbelt, Richard Henderson, qemu-devel,
	Alistair Francis, Bin Meng, ilippe=20Mathieu-Daud=C3=A9?=

From: Alistair Francis <alistair.francis@wdc.com>

Coverity (CID 1405786) thinks that there is a possible memory leak as
we don't guarantee that the memory allocated from riscv_find_firmware()
is freed. This is a false positive, but let's tidy up the code to fix
the warning.

Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Bin Meng <bmeng.cn@gmail.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 hw/riscv/boot.c | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)

diff --git a/hw/riscv/boot.c b/hw/riscv/boot.c
index 2e92fb0680..7fee98d2f8 100644
--- a/hw/riscv/boot.c
+++ b/hw/riscv/boot.c
@@ -38,7 +38,7 @@ void riscv_find_and_load_firmware(MachineState *machine,
                                   const char *default_machine_firmware,
                                   hwaddr firmware_load_addr)
 {
-    char *firmware_filename;
+    char *firmware_filename = NULL;
 
     if (!machine->firmware) {
         /*
@@ -70,14 +70,11 @@ void riscv_find_and_load_firmware(MachineState *machine,
          * if no -bios option is set without breaking anything.
          */
         firmware_filename = riscv_find_firmware(default_machine_firmware);
-    } else {
-        firmware_filename = machine->firmware;
-        if (strcmp(firmware_filename, "none")) {
-            firmware_filename = riscv_find_firmware(firmware_filename);
-        }
+    } else if (strcmp(machine->firmware, "none")) {
+        firmware_filename = riscv_find_firmware(machine->firmware);
     }
 
-    if (strcmp(firmware_filename, "none")) {
+    if (firmware_filename) {
         /* If not "none" load the firmware */
         riscv_load_firmware(firmware_filename, firmware_load_addr);
         g_free(firmware_filename);
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PULL 18/18] target/riscv: PMP violation due to wrong size parameter
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (16 preceding siblings ...)
  2019-10-28 15:49 ` [PULL 17/18] riscv/boot: Fix possible memory leak Palmer Dabbelt
@ 2019-10-28 15:49 ` Palmer Dabbelt
  2019-10-29  8:37 ` [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Peter Maydell
  18 siblings, 0 replies; 20+ messages in thread
From: Palmer Dabbelt @ 2019-10-28 15:49 UTC (permalink / raw)
  To: Peter Maydell
  Cc: Dayeol Lee, Richard Henderson, Palmer Dabbelt, qemu-riscv, qemu-devel

From: Dayeol Lee <dayeol@berkeley.edu>

riscv_cpu_tlb_fill() uses the `size` parameter to check PMP violation
using pmp_hart_has_privs().
However, if the size is unknown (=0), the ending address will be
`addr - 1` as it is `addr + size - 1` in `pmp_hart_has_privs()`.
This always causes a false PMP violation on the starting address of the
range, as `addr - 1` is not in the range.

In order to fix, we just assume that all bytes from addr to the end of
the page will be accessed if the size is unknown.

Signed-off-by: Dayeol Lee <dayeol@berkeley.edu>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Signed-off-by: Palmer Dabbelt <palmer@sifive.com>
---
 target/riscv/pmp.c | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/target/riscv/pmp.c b/target/riscv/pmp.c
index d4f1007109..0e6b640fbd 100644
--- a/target/riscv/pmp.c
+++ b/target/riscv/pmp.c
@@ -223,6 +223,7 @@ bool pmp_hart_has_privs(CPURISCVState *env, target_ulong addr,
 {
     int i = 0;
     int ret = -1;
+    int pmp_size = 0;
     target_ulong s = 0;
     target_ulong e = 0;
     pmp_priv_t allowed_privs = 0;
@@ -232,11 +233,21 @@ bool pmp_hart_has_privs(CPURISCVState *env, target_ulong addr,
         return true;
     }
 
+    /*
+     * if size is unknown (0), assume that all bytes
+     * from addr to the end of the page will be accessed.
+     */
+    if (size == 0) {
+        pmp_size = -(addr | TARGET_PAGE_MASK);
+    } else {
+        pmp_size = size;
+    }
+
     /* 1.10 draft priv spec states there is an implicit order
          from low to high */
     for (i = 0; i < MAX_RISCV_PMPS; i++) {
         s = pmp_is_in_range(env, i, addr);
-        e = pmp_is_in_range(env, i, addr + size - 1);
+        e = pmp_is_in_range(env, i, addr + pmp_size - 1);
 
         /* partially inside */
         if ((s + e) == 1) {
-- 
2.21.0



^ permalink raw reply related	[flat|nested] 20+ messages in thread

* Re: [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2
  2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
                   ` (17 preceding siblings ...)
  2019-10-28 15:49 ` [PULL 18/18] target/riscv: PMP violation due to wrong size parameter Palmer Dabbelt
@ 2019-10-29  8:37 ` Peter Maydell
  18 siblings, 0 replies; 20+ messages in thread
From: Peter Maydell @ 2019-10-29  8:37 UTC (permalink / raw)
  To: Palmer Dabbelt; +Cc: open list:RISC-V, QEMU Developers

On Mon, 28 Oct 2019 at 15:58, Palmer Dabbelt <palmer@sifive.com> wrote:
>
> merged tag 'for_upstream'
> Primary key fingerprint: 0270 606B 6F3C DF3D 0B17  0970 C350 3912 AFBE 8E67
>      Subkey fingerprint: 5D09 FD08 71C8 F85B 94CA  8A0D 281F 0DB8 D28D 5469
> The following changes since commit 9bb73502321d46f4d320fa17aa38201445783fc4:
>
>   Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging (2019-10-28 13:32:40 +0000)
>
> are available in the Git repository at:
>
>   git://github.com/palmer-dabbelt/qemu.git tags/riscv-for-master-4.2-sf2
>
> for you to fetch changes up to 9667e53573f907d4fcd6accff1c8fe525544b749:
>
>   target/riscv: PMP violation due to wrong size parameter (2019-10-28 08:46:33 -0700)
>
> ----------------------------------------------------------------
> RISC-V Patches for the 4.2 Soft Freeze, Part 2
>
> This patch set contains a handful of small fixes for RISC-V targets that
> I'd like to target for the 4.2 soft freeze.  They include:
>
> * A fix to allow the debugger to access the state of all privilege
>   modes, as opposed to just the currently executing one.
> * A pair of cleanups to implement cpu_do_transaction_failed.
> * Fixes to the device tree.
> * The addition of various memory regions to make the sifive_u machine
>   more closely match the HiFive Unleashed board.
> * Fixes to our GDB interface to allow CSRs to be accessed.
> * A fix to a memory leak pointed out by coverity.
> * A fix that prevents PMP checks from firing incorrectly.
>
> This passes "make chcek" and boots Open Embedded for me.


Applied, thanks.

Please update the changelog at https://wiki.qemu.org/ChangeLog/4.2
for any user-visible changes.

-- PMM


^ permalink raw reply	[flat|nested] 20+ messages in thread

end of thread, other threads:[~2019-10-29  8:38 UTC | newest]

Thread overview: 20+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-10-28 15:48 [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Palmer Dabbelt
2019-10-28 15:48 ` [PULL 01/18] riscv: Skip checking CSR privilege level in debugger mode Palmer Dabbelt
2019-10-28 15:48 ` [PULL 02/18] RISC-V: Handle bus errors in the page table walker Palmer Dabbelt
2019-10-28 15:48 ` [PULL 03/18] RISC-V: Implement cpu_do_transaction_failed Palmer Dabbelt
2019-10-28 15:48 ` [PULL 04/18] riscv: hw: Drop "clock-frequency" property of cpu nodes Palmer Dabbelt
2019-10-28 15:48 ` [PULL 05/18] riscv: sifive_u: Add ethernet0 to the aliases node Palmer Dabbelt
2019-10-28 15:48 ` [PULL 06/18] linux-user/riscv: Propagate fault address Palmer Dabbelt
2019-10-28 15:48 ` [PULL 07/18] riscv/sifive_u: Add L2-LIM cache memory Palmer Dabbelt
2019-10-28 15:48 ` [PULL 08/18] riscv/sifive_u: Add QSPI memory region Palmer Dabbelt
2019-10-28 15:48 ` [PULL 09/18] riscv/sifive_u: Manually define the machine Palmer Dabbelt
2019-10-28 15:48 ` [PULL 10/18] riscv/sifive_u: Add the start-in-flash property Palmer Dabbelt
2019-10-28 15:48 ` [PULL 11/18] riscv/virt: Manually define the machine Palmer Dabbelt
2019-10-28 15:48 ` [PULL 12/18] riscv/virt: Add the PFlash CFI01 device Palmer Dabbelt
2019-10-28 15:48 ` [PULL 13/18] riscv/virt: Jump to pflash if specified Palmer Dabbelt
2019-10-28 15:48 ` [PULL 14/18] target/riscv: Tell gdbstub the correct number of CSRs Palmer Dabbelt
2019-10-28 15:48 ` [PULL 15/18] target/riscv: Expose "priv" register for GDB for reads Palmer Dabbelt
2019-10-28 15:49 ` [PULL 16/18] target/riscv: Make the priv register writable by GDB Palmer Dabbelt
2019-10-28 15:49 ` [PULL 17/18] riscv/boot: Fix possible memory leak Palmer Dabbelt
2019-10-28 15:49 ` [PULL 18/18] target/riscv: PMP violation due to wrong size parameter Palmer Dabbelt
2019-10-29  8:37 ` [PULL] RISC-V Patches for the 4.2 Soft Freeze, Part 2 Peter Maydell

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).