1
The following changes since commit 9435a8b3dd35f1f926f1b9127e8a906217a5518a:
1
The following changes since commit fcb237e64f9d026c03d635579c7b288d0008a6e5:
2
2
3
Merge remote-tracking branch 'remotes/kraxel/tags/sirius/ipxe-20200908-pull-request' into staging (2020-09-08 21:21:13 +0100)
3
Merge tag 'pull-vfio-20230710' of https://github.com/legoater/qemu into staging (2023-07-10 09:17:06 +0100)
4
4
5
are available in the Git repository at:
5
are available in the Git repository at:
6
6
7
git@github.com:alistair23/qemu.git tags/pull-riscv-to-apply-20200910
7
https://github.com/alistair23/qemu.git tags/pull-riscv-to-apply-20230710-1
8
8
9
for you to fetch changes up to 7595a65818ea9b49c36650a8c217a1ef9bd6e62a:
9
for you to fetch changes up to a47842d16653b4f73b5d56ff0c252dd8a329481b:
10
10
11
hw/riscv: Sort the Kconfig options in alphabetical order (2020-09-09 15:54:19 -0700)
11
riscv: Add support for the Zfa extension (2023-07-10 22:29:20 +1000)
12
12
13
----------------------------------------------------------------
13
----------------------------------------------------------------
14
This PR includes multiple fixes and features for RISC-V:
14
Third RISC-V PR for 8.1
15
- Fixes a bug in printing trap causes
15
16
- Allows 16-bit writes to the SiFive test device. This fixes the
16
* Use xl instead of mxl for disassemble
17
failure to reboot the RISC-V virt machine
17
* Factor out extension tests to cpu_cfg.h
18
- Support for the Microchip PolarFire SoC and Icicle Kit
18
* disas/riscv: Add vendor extension support
19
- A reafactor of RISC-V code out of hw/riscv
19
* disas/riscv: Add support for XVentanaCondOps
20
* disas/riscv: Add support for XThead* instructions
21
* Fix mstatus related problems
22
* Fix veyron-v1 CPU properties
23
* Fix the xlen for data address when MPRV=1
24
* opensbi: Upgrade from v1.2 to v1.3
25
* Enable 32-bit Spike OpenSBI boot testing
26
* Support the watchdog timer of HiFive 1 rev b
27
* Only build qemu-system-riscv$$ on rv$$ host
28
* Add RVV registers to log
29
* Restrict ACLINT to TCG
30
* Add syscall riscv_hwprobe
31
* Add support for BF16 extensions
32
* KVM_RISCV_SET_TIMER macro is not configured correctly
33
* Generate devicetree only after machine initialization is complete
34
* virt: Convert fdt_load_addr to uint64_t
35
* KVM: fixes and enhancements
36
* Add support for the Zfa extension
20
37
21
----------------------------------------------------------------
38
----------------------------------------------------------------
22
Bin Meng (28):
39
Bin Meng (2):
23
target/riscv: cpu: Add a new 'resetvec' property
40
roms/opensbi: Upgrade from v1.2 to v1.3
24
hw/riscv: hart: Add a new 'resetvec' property
41
tests/avocado: riscv: Enable 32-bit Spike OpenSBI boot testing
25
target/riscv: cpu: Set reset vector based on the configured property value
26
hw/riscv: Initial support for Microchip PolarFire SoC Icicle Kit board
27
hw/char: Add Microchip PolarFire SoC MMUART emulation
28
hw/riscv: microchip_pfsoc: Connect 5 MMUARTs
29
hw/sd: Add Cadence SDHCI emulation
30
hw/riscv: microchip_pfsoc: Connect a Cadence SDHCI controller and an SD card
31
hw/dma: Add SiFive platform DMA controller emulation
32
hw/riscv: microchip_pfsoc: Connect a DMA controller
33
hw/net: cadence_gem: Add a new 'phy-addr' property
34
hw/arm: xlnx: Set all boards' GEM 'phy-addr' property value to 23
35
hw/riscv: microchip_pfsoc: Connect 2 Cadence GEMs
36
hw/riscv: microchip_pfsoc: Hook GPIO controllers
37
hw/riscv: clint: Avoid using hard-coded timebase frequency
38
hw/riscv: sifive_u: Connect a DMA controller
39
hw/riscv: Move sifive_e_prci model to hw/misc
40
hw/riscv: Move sifive_u_prci model to hw/misc
41
hw/riscv: Move sifive_u_otp model to hw/misc
42
hw/riscv: Move sifive_gpio model to hw/gpio
43
hw/riscv: Move sifive_clint model to hw/intc
44
hw/riscv: Move sifive_plic model to hw/intc
45
hw/riscv: Move riscv_htif model to hw/char
46
hw/riscv: Move sifive_uart model to hw/char
47
hw/riscv: Move sifive_test model to hw/misc
48
hw/riscv: Always build riscv_hart.c
49
hw/riscv: Drop CONFIG_SIFIVE
50
hw/riscv: Sort the Kconfig options in alphabetical order
51
42
52
Nathan Chancellor (1):
43
Christoph Müllner (8):
53
riscv: sifive_test: Allow 16-bit writes to memory region
44
target/riscv: Factor out extension tests to cpu_cfg.h
45
disas/riscv: Move types/constants to new header file
46
disas/riscv: Make rv_op_illegal a shared enum value
47
disas/riscv: Encapsulate opcode_data into decode
48
disas/riscv: Provide infrastructure for vendor extensions
49
disas/riscv: Add support for XVentanaCondOps
50
disas/riscv: Add support for XThead* instructions
51
riscv: Add support for the Zfa extension
54
52
55
Yifei Jiang (1):
53
Daniel Henrique Barboza (20):
56
target/riscv: Fix bug in getting trap cause name for trace_riscv_trap
54
target/riscv/cpu.c: fix veyron-v1 CPU properties
55
target/riscv: skip features setup for KVM CPUs
56
hw/riscv/virt.c: skip 'mmu-type' FDT if satp mode not set
57
target/riscv/cpu.c: restrict 'mvendorid' value
58
target/riscv/cpu.c: restrict 'mimpid' value
59
target/riscv/cpu.c: restrict 'marchid' value
60
target/riscv: use KVM scratch CPUs to init KVM properties
61
target/riscv: read marchid/mimpid in kvm_riscv_init_machine_ids()
62
target/riscv: handle mvendorid/marchid/mimpid for KVM CPUs
63
target/riscv/kvm.c: init 'misa_ext_mask' with scratch CPU
64
target/riscv/cpu: add misa_ext_info_arr[]
65
target/riscv: add KVM specific MISA properties
66
target/riscv/kvm.c: update KVM MISA bits
67
target/riscv/kvm.c: add multi-letter extension KVM properties
68
target/riscv/cpu.c: add satp_mode properties earlier
69
target/riscv/cpu.c: remove priv_ver check from riscv_isa_string_ext()
70
target/riscv/cpu.c: create KVM mock properties
71
target/riscv: update multi-letter extension KVM properties
72
target/riscv/kvm.c: add kvmconfig_get_cfg_addr() helper
73
target/riscv/kvm.c: read/write (cbom|cboz)_blocksize in KVM
57
74
58
default-configs/riscv64-softmmu.mak | 1 +
75
Guenter Roeck (1):
59
{include/hw/riscv => hw/intc}/sifive_plic.h | 0
76
riscv: Generate devicetree only after machine initialization is complete
60
hw/riscv/trace.h | 1 -
61
include/hw/char/mchp_pfsoc_mmuart.h | 61 ++++
62
include/hw/{riscv => char}/riscv_htif.h | 0
63
include/hw/{riscv => char}/sifive_uart.h | 0
64
include/hw/dma/sifive_pdma.h | 57 ++++
65
include/hw/{riscv => gpio}/sifive_gpio.h | 0
66
include/hw/{riscv => intc}/sifive_clint.h | 4 +-
67
include/hw/{riscv => misc}/sifive_e_prci.h | 0
68
include/hw/{riscv => misc}/sifive_test.h | 0
69
include/hw/{riscv => misc}/sifive_u_otp.h | 0
70
include/hw/{riscv => misc}/sifive_u_prci.h | 0
71
include/hw/net/cadence_gem.h | 2 +
72
include/hw/riscv/microchip_pfsoc.h | 133 +++++++++
73
include/hw/riscv/riscv_hart.h | 1 +
74
include/hw/riscv/sifive_e.h | 2 +-
75
include/hw/riscv/sifive_u.h | 17 +-
76
include/hw/sd/cadence_sdhci.h | 47 +++
77
target/riscv/cpu.h | 8 +-
78
hw/arm/xilinx_zynq.c | 1 +
79
hw/arm/xlnx-versal.c | 1 +
80
hw/arm/xlnx-zynqmp.c | 2 +
81
hw/char/mchp_pfsoc_mmuart.c | 86 ++++++
82
hw/{riscv => char}/riscv_htif.c | 2 +-
83
hw/{riscv => char}/sifive_uart.c | 2 +-
84
hw/dma/sifive_pdma.c | 313 ++++++++++++++++++++
85
hw/{riscv => gpio}/sifive_gpio.c | 2 +-
86
hw/{riscv => intc}/sifive_clint.c | 28 +-
87
hw/{riscv => intc}/sifive_plic.c | 2 +-
88
hw/{riscv => misc}/sifive_e_prci.c | 2 +-
89
hw/{riscv => misc}/sifive_test.c | 4 +-
90
hw/{riscv => misc}/sifive_u_otp.c | 2 +-
91
hw/{riscv => misc}/sifive_u_prci.c | 2 +-
92
hw/net/cadence_gem.c | 7 +-
93
hw/riscv/microchip_pfsoc.c | 437 ++++++++++++++++++++++++++++
94
hw/riscv/opentitan.c | 1 +
95
hw/riscv/riscv_hart.c | 3 +
96
hw/riscv/sifive_e.c | 12 +-
97
hw/riscv/sifive_u.c | 41 ++-
98
hw/riscv/spike.c | 7 +-
99
hw/riscv/virt.c | 9 +-
100
hw/sd/cadence_sdhci.c | 193 ++++++++++++
101
target/riscv/cpu.c | 19 +-
102
target/riscv/cpu_helper.c | 8 +-
103
target/riscv/csr.c | 4 +-
104
MAINTAINERS | 9 +
105
hw/char/Kconfig | 9 +
106
hw/char/meson.build | 3 +
107
hw/dma/Kconfig | 3 +
108
hw/dma/meson.build | 1 +
109
hw/gpio/Kconfig | 3 +
110
hw/gpio/meson.build | 1 +
111
hw/gpio/trace-events | 6 +
112
hw/intc/Kconfig | 6 +
113
hw/intc/meson.build | 2 +
114
hw/misc/Kconfig | 12 +
115
hw/misc/meson.build | 6 +
116
hw/riscv/Kconfig | 70 +++--
117
hw/riscv/meson.build | 12 +-
118
hw/riscv/trace-events | 7 -
119
hw/sd/Kconfig | 4 +
120
hw/sd/meson.build | 1 +
121
meson.build | 1 -
122
64 files changed, 1575 insertions(+), 105 deletions(-)
123
rename {include/hw/riscv => hw/intc}/sifive_plic.h (100%)
124
delete mode 100644 hw/riscv/trace.h
125
create mode 100644 include/hw/char/mchp_pfsoc_mmuart.h
126
rename include/hw/{riscv => char}/riscv_htif.h (100%)
127
rename include/hw/{riscv => char}/sifive_uart.h (100%)
128
create mode 100644 include/hw/dma/sifive_pdma.h
129
rename include/hw/{riscv => gpio}/sifive_gpio.h (100%)
130
rename include/hw/{riscv => intc}/sifive_clint.h (92%)
131
rename include/hw/{riscv => misc}/sifive_e_prci.h (100%)
132
rename include/hw/{riscv => misc}/sifive_test.h (100%)
133
rename include/hw/{riscv => misc}/sifive_u_otp.h (100%)
134
rename include/hw/{riscv => misc}/sifive_u_prci.h (100%)
135
create mode 100644 include/hw/riscv/microchip_pfsoc.h
136
create mode 100644 include/hw/sd/cadence_sdhci.h
137
create mode 100644 hw/char/mchp_pfsoc_mmuart.c
138
rename hw/{riscv => char}/riscv_htif.c (99%)
139
rename hw/{riscv => char}/sifive_uart.c (99%)
140
create mode 100644 hw/dma/sifive_pdma.c
141
rename hw/{riscv => gpio}/sifive_gpio.c (99%)
142
rename hw/{riscv => intc}/sifive_clint.c (90%)
143
rename hw/{riscv => intc}/sifive_plic.c (99%)
144
rename hw/{riscv => misc}/sifive_e_prci.c (99%)
145
rename hw/{riscv => misc}/sifive_test.c (97%)
146
rename hw/{riscv => misc}/sifive_u_otp.c (99%)
147
rename hw/{riscv => misc}/sifive_u_prci.c (99%)
148
create mode 100644 hw/riscv/microchip_pfsoc.c
149
create mode 100644 hw/sd/cadence_sdhci.c
150
delete mode 100644 hw/riscv/trace-events
151
77
78
Ivan Klokov (1):
79
target/riscv: Add RVV registers to log
80
81
Jason Chien (1):
82
target/riscv: Set the correct exception for implict G-stage translation fail
83
84
LIU Zhiwei (1):
85
target/riscv: Use xl instead of mxl for disassemble
86
87
Lakshmi Bai Raja Subramanian (1):
88
hw/riscv: virt: Convert fdt_load_addr to uint64_t
89
90
Philippe Mathieu-Daudé (3):
91
target/riscv: Only unify 'riscv32/64' -> 'riscv' for host cpu in meson
92
target/riscv: Only build KVM guest with same wordsize as host
93
hw/riscv/virt: Restrict ACLINT to TCG
94
95
Robbin Ehn (1):
96
linux-user/riscv: Add syscall riscv_hwprobe
97
98
Tommy Wu (3):
99
hw/misc: sifive_e_aon: Support the watchdog timer of HiFive 1 rev b.
100
hw/riscv: sifive_e: Support the watchdog timer of HiFive 1 rev b.
101
tests/qtest: sifive-e-aon-watchdog-test.c: Add QTest of watchdog of sifive_e
102
103
Weiwei Li (11):
104
target/riscv: Make MPV only work when MPP != PRV_M
105
target/riscv: Support MSTATUS.MPV/GVA only when RVH is enabled
106
target/riscv: Remove redundant assignment to SXL
107
target/riscv: Add additional xlen for address when MPRV=1
108
target/riscv: update cur_pmbase/pmmask based on mode affected by MPRV
109
target/riscv: Add properties for BF16 extensions
110
target/riscv: Add support for Zfbfmin extension
111
target/riscv: Add support for Zvfbfmin extension
112
target/riscv: Add support for Zvfbfwma extension
113
target/riscv: Expose properties for BF16 extensions
114
target/riscv: Add disas support for BF16 extensions
115
116
yang.zhang (1):
117
target/riscv KVM_RISCV_SET_TIMER macro is not configured correctly
118
119
docs/system/riscv/virt.rst | 1 +
120
meson.build | 15 +-
121
disas/riscv-xthead.h | 28 +
122
disas/riscv-xventana.h | 18 +
123
disas/riscv.h | 302 +++++++++++
124
include/hw/misc/sifive_e_aon.h | 60 +++
125
include/hw/riscv/sifive_e.h | 9 +-
126
linux-user/riscv/syscall32_nr.h | 1 +
127
linux-user/riscv/syscall64_nr.h | 1 +
128
target/riscv/cpu.h | 56 +-
129
target/riscv/cpu_cfg.h | 41 ++
130
target/riscv/helper.h | 29 +
131
target/riscv/kvm_riscv.h | 1 +
132
target/riscv/insn32.decode | 38 ++
133
disas/riscv-xthead.c | 707 +++++++++++++++++++++++++
134
disas/riscv-xventana.c | 41 ++
135
disas/riscv.c | 559 +++++++++----------
136
hw/misc/sifive_e_aon.c | 319 +++++++++++
137
hw/riscv/sifive_e.c | 17 +-
138
hw/riscv/virt.c | 56 +-
139
linux-user/syscall.c | 146 +++++
140
target/riscv/cpu.c | 439 +++++++++++++--
141
target/riscv/cpu_helper.c | 12 +-
142
target/riscv/csr.c | 41 +-
143
target/riscv/fpu_helper.c | 166 ++++++
144
target/riscv/kvm.c | 501 +++++++++++++++++-
145
target/riscv/op_helper.c | 3 +-
146
target/riscv/translate.c | 42 +-
147
target/riscv/vector_helper.c | 17 +
148
tests/qtest/sifive-e-aon-watchdog-test.c | 450 ++++++++++++++++
149
tests/tcg/riscv64/test-fcvtmod.c | 345 ++++++++++++
150
target/riscv/insn_trans/trans_rvbf16.c.inc | 175 ++++++
151
target/riscv/insn_trans/trans_rvzfa.c.inc | 521 ++++++++++++++++++
152
target/riscv/insn_trans/trans_rvzfh.c.inc | 12 +-
153
disas/meson.build | 6 +-
154
hw/misc/Kconfig | 3 +
155
hw/misc/meson.build | 1 +
156
hw/riscv/Kconfig | 1 +
157
pc-bios/opensbi-riscv32-generic-fw_dynamic.bin | Bin 123072 -> 135344 bytes
158
pc-bios/opensbi-riscv64-generic-fw_dynamic.bin | Bin 121800 -> 138304 bytes
159
roms/opensbi | 2 +-
160
tests/avocado/riscv_opensbi.py | 2 -
161
tests/qtest/meson.build | 3 +
162
tests/tcg/riscv64/Makefile.target | 6 +
163
44 files changed, 4751 insertions(+), 442 deletions(-)
164
create mode 100644 disas/riscv-xthead.h
165
create mode 100644 disas/riscv-xventana.h
166
create mode 100644 disas/riscv.h
167
create mode 100644 include/hw/misc/sifive_e_aon.h
168
create mode 100644 disas/riscv-xthead.c
169
create mode 100644 disas/riscv-xventana.c
170
create mode 100644 hw/misc/sifive_e_aon.c
171
create mode 100644 tests/qtest/sifive-e-aon-watchdog-test.c
172
create mode 100644 tests/tcg/riscv64/test-fcvtmod.c
173
create mode 100644 target/riscv/insn_trans/trans_rvbf16.c.inc
174
create mode 100644 target/riscv/insn_trans/trans_rvzfa.c.inc
175
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
2
2
3
At present the Kconfig file is in disorder. Let's sort the options.
3
Disassemble function(plugin_disas, target_disas, monitor_disas) will
4
always call set_disas_info before disassembling instructions.
4
5
5
Signed-off-by: Bin Meng <bin.meng@windriver.com>
6
plugin_disas and target_disas will always be called under a TB, which
7
has the same XLEN.
8
9
We can't ensure that monitor_disas will always be called under a TB,
10
but current XLEN will still be a better choice, thus we can ensure at
11
least the disassemble of the nearest one TB is right.
12
13
Signed-off-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
14
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
6
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
15
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
Message-Id: <1599129623-68957-13-git-send-email-bmeng.cn@gmail.com>
16
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
17
Message-Id: <20230612111034.3955227-2-christoph.muellner@vrull.eu>
8
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
18
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
9
---
19
---
10
hw/riscv/Kconfig | 58 ++++++++++++++++++++++++------------------------
20
target/riscv/cpu.c | 3 ++-
11
1 file changed, 29 insertions(+), 29 deletions(-)
21
1 file changed, 2 insertions(+), 1 deletion(-)
12
22
13
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
23
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
14
index XXXXXXX..XXXXXXX 100644
24
index XXXXXXX..XXXXXXX 100644
15
--- a/hw/riscv/Kconfig
25
--- a/target/riscv/cpu.c
16
+++ b/hw/riscv/Kconfig
26
+++ b/target/riscv/cpu.c
17
@@ -XXX,XX +XXX,XX @@
27
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_reset_hold(Object *obj)
18
config IBEX
28
static void riscv_cpu_disas_set_info(CPUState *s, disassemble_info *info)
19
bool
29
{
20
30
RISCVCPU *cpu = RISCV_CPU(s);
21
-config SIFIVE_E
31
+ CPURISCVState *env = &cpu->env;
22
- bool
32
info->target_info = &cpu->cfg;
23
- select MSI_NONBROKEN
33
24
- select SIFIVE_CLINT
34
- switch (riscv_cpu_mxl(&cpu->env)) {
25
- select SIFIVE_GPIO
35
+ switch (env->xl) {
26
- select SIFIVE_PLIC
36
case MXL_RV32:
27
- select SIFIVE_UART
37
info->print_insn = print_insn_riscv32;
28
- select SIFIVE_E_PRCI
38
break;
29
- select UNIMP
30
-
31
-config SIFIVE_U
32
+config MICROCHIP_PFSOC
33
bool
34
- select CADENCE
35
+ select CADENCE_SDHCI
36
+ select MCHP_PFSOC_MMUART
37
select MSI_NONBROKEN
38
select SIFIVE_CLINT
39
- select SIFIVE_GPIO
40
select SIFIVE_PDMA
41
select SIFIVE_PLIC
42
- select SIFIVE_UART
43
- select SIFIVE_U_OTP
44
- select SIFIVE_U_PRCI
45
select UNIMP
46
47
-config SPIKE
48
- bool
49
- select HTIF
50
- select MSI_NONBROKEN
51
- select SIFIVE_CLINT
52
- select SIFIVE_PLIC
53
-
54
config OPENTITAN
55
bool
56
select IBEX
57
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
58
bool
59
imply PCI_DEVICES
60
imply TEST_DEVICES
61
+ select GOLDFISH_RTC
62
select MSI_NONBROKEN
63
select PCI
64
- select SERIAL
65
- select GOLDFISH_RTC
66
- select VIRTIO_MMIO
67
select PCI_EXPRESS_GENERIC_BRIDGE
68
select PFLASH_CFI01
69
+ select SERIAL
70
select SIFIVE_CLINT
71
select SIFIVE_PLIC
72
select SIFIVE_TEST
73
+ select VIRTIO_MMIO
74
75
-config MICROCHIP_PFSOC
76
+config SIFIVE_E
77
bool
78
select MSI_NONBROKEN
79
select SIFIVE_CLINT
80
+ select SIFIVE_GPIO
81
+ select SIFIVE_PLIC
82
+ select SIFIVE_UART
83
+ select SIFIVE_E_PRCI
84
select UNIMP
85
- select MCHP_PFSOC_MMUART
86
+
87
+config SIFIVE_U
88
+ bool
89
+ select CADENCE
90
+ select MSI_NONBROKEN
91
+ select SIFIVE_CLINT
92
+ select SIFIVE_GPIO
93
select SIFIVE_PDMA
94
select SIFIVE_PLIC
95
- select CADENCE_SDHCI
96
+ select SIFIVE_UART
97
+ select SIFIVE_U_OTP
98
+ select SIFIVE_U_PRCI
99
+ select UNIMP
100
+
101
+config SPIKE
102
+ bool
103
+ select HTIF
104
+ select MSI_NONBROKEN
105
+ select SIFIVE_CLINT
106
+ select SIFIVE_PLIC
107
--
39
--
108
2.28.0
40
2.40.1
109
41
110
42
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
When cadence_gem model was created for Xilinx boards, the PHY address
3
This patch moves the extension test functions that are used
4
was hard-coded to 23 in the GEM model. Now that we have introduced a
4
to gate vendor extension decoders, into cpu_cfg.h.
5
property we can use that to tell GEM model what our PHY address is.
5
This allows to reuse them in the disassembler.
6
Change all boards' GEM 'phy-addr' property value to 23, and set the
7
PHY address default value to 0 in the GEM model.
8
6
9
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
This patch does not introduce new functionality.
10
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
8
However, the patch includes a small change:
11
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
The parameter for the extension test functions has been changed
12
Message-Id: <1598924352-89526-13-git-send-email-bmeng.cn@gmail.com>
10
from 'DisasContext*' to 'const RISCVCPUConfig*' to keep
11
the code in cpu_cfg.h self-contained.
12
13
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
14
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
15
Reviewed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
16
Reviewed-by: Weiwei Li <liweiwei@iscas.ac.cn>
17
Message-Id: <20230612111034.3955227-3-christoph.muellner@vrull.eu>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
18
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
14
---
19
---
15
hw/arm/xilinx_zynq.c | 1 +
20
target/riscv/cpu_cfg.h | 26 ++++++++++++++++++++++++++
16
hw/arm/xlnx-versal.c | 1 +
21
target/riscv/translate.c | 27 ++-------------------------
17
hw/arm/xlnx-zynqmp.c | 2 ++
22
2 files changed, 28 insertions(+), 25 deletions(-)
18
hw/net/cadence_gem.c | 6 +++---
19
4 files changed, 7 insertions(+), 3 deletions(-)
20
23
21
diff --git a/hw/arm/xilinx_zynq.c b/hw/arm/xilinx_zynq.c
24
diff --git a/target/riscv/cpu_cfg.h b/target/riscv/cpu_cfg.h
22
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX 100644
23
--- a/hw/arm/xilinx_zynq.c
26
--- a/target/riscv/cpu_cfg.h
24
+++ b/hw/arm/xilinx_zynq.c
27
+++ b/target/riscv/cpu_cfg.h
25
@@ -XXX,XX +XXX,XX @@ static void gem_init(NICInfo *nd, uint32_t base, qemu_irq irq)
28
@@ -XXX,XX +XXX,XX @@ struct RISCVCPUConfig {
26
qemu_check_nic_model(nd, TYPE_CADENCE_GEM);
29
};
27
qdev_set_nic_properties(dev, nd);
30
28
}
31
typedef struct RISCVCPUConfig RISCVCPUConfig;
29
+ object_property_set_int(OBJECT(dev), "phy-addr", 23, &error_abort);
32
+
30
s = SYS_BUS_DEVICE(dev);
33
+/* Helper functions to test for extensions. */
31
sysbus_realize_and_unref(s, &error_fatal);
34
+
32
sysbus_mmio_map(s, 0, base);
35
+static inline bool always_true_p(const RISCVCPUConfig *cfg __attribute__((__unused__)))
33
diff --git a/hw/arm/xlnx-versal.c b/hw/arm/xlnx-versal.c
36
+{
37
+ return true;
38
+}
39
+
40
+static inline bool has_xthead_p(const RISCVCPUConfig *cfg)
41
+{
42
+ return cfg->ext_xtheadba || cfg->ext_xtheadbb ||
43
+ cfg->ext_xtheadbs || cfg->ext_xtheadcmo ||
44
+ cfg->ext_xtheadcondmov ||
45
+ cfg->ext_xtheadfmemidx || cfg->ext_xtheadfmv ||
46
+ cfg->ext_xtheadmac || cfg->ext_xtheadmemidx ||
47
+ cfg->ext_xtheadmempair || cfg->ext_xtheadsync;
48
+}
49
+
50
+#define MATERIALISE_EXT_PREDICATE(ext) \
51
+ static inline bool has_ ## ext ## _p(const RISCVCPUConfig *cfg) \
52
+ { \
53
+ return cfg->ext_ ## ext ; \
54
+ }
55
+
56
+MATERIALISE_EXT_PREDICATE(XVentanaCondOps)
57
+
58
#endif
59
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
34
index XXXXXXX..XXXXXXX 100644
60
index XXXXXXX..XXXXXXX 100644
35
--- a/hw/arm/xlnx-versal.c
61
--- a/target/riscv/translate.c
36
+++ b/hw/arm/xlnx-versal.c
62
+++ b/target/riscv/translate.c
37
@@ -XXX,XX +XXX,XX @@ static void versal_create_gems(Versal *s, qemu_irq *pic)
63
@@ -XXX,XX +XXX,XX @@ static inline bool has_ext(DisasContext *ctx, uint32_t ext)
38
qemu_check_nic_model(nd, "cadence_gem");
64
return ctx->misa_ext & ext;
39
qdev_set_nic_properties(dev, nd);
65
}
40
}
66
41
+ object_property_set_int(OBJECT(dev), "phy-addr", 23, &error_abort);
67
-static bool always_true_p(DisasContext *ctx __attribute__((__unused__)))
42
object_property_set_int(OBJECT(dev), "num-priority-queues", 2,
68
-{
43
&error_abort);
69
- return true;
44
object_property_set_link(OBJECT(dev), "dma", OBJECT(&s->mr_ps),
70
-}
45
diff --git a/hw/arm/xlnx-zynqmp.c b/hw/arm/xlnx-zynqmp.c
71
-
46
index XXXXXXX..XXXXXXX 100644
72
-static bool has_xthead_p(DisasContext *ctx __attribute__((__unused__)))
47
--- a/hw/arm/xlnx-zynqmp.c
73
-{
48
+++ b/hw/arm/xlnx-zynqmp.c
74
- return ctx->cfg_ptr->ext_xtheadba || ctx->cfg_ptr->ext_xtheadbb ||
49
@@ -XXX,XX +XXX,XX @@ static void xlnx_zynqmp_realize(DeviceState *dev, Error **errp)
75
- ctx->cfg_ptr->ext_xtheadbs || ctx->cfg_ptr->ext_xtheadcmo ||
50
}
76
- ctx->cfg_ptr->ext_xtheadcondmov ||
51
object_property_set_int(OBJECT(&s->gem[i]), "revision", GEM_REVISION,
77
- ctx->cfg_ptr->ext_xtheadfmemidx || ctx->cfg_ptr->ext_xtheadfmv ||
52
&error_abort);
78
- ctx->cfg_ptr->ext_xtheadmac || ctx->cfg_ptr->ext_xtheadmemidx ||
53
+ object_property_set_int(OBJECT(&s->gem[i]), "phy-addr", 23,
79
- ctx->cfg_ptr->ext_xtheadmempair || ctx->cfg_ptr->ext_xtheadsync;
54
+ &error_abort);
80
-}
55
object_property_set_int(OBJECT(&s->gem[i]), "num-priority-queues", 2,
81
-
56
&error_abort);
82
-#define MATERIALISE_EXT_PREDICATE(ext) \
57
if (!sysbus_realize(SYS_BUS_DEVICE(&s->gem[i]), errp)) {
83
- static bool has_ ## ext ## _p(DisasContext *ctx) \
58
diff --git a/hw/net/cadence_gem.c b/hw/net/cadence_gem.c
84
- { \
59
index XXXXXXX..XXXXXXX 100644
85
- return ctx->cfg_ptr->ext_ ## ext ; \
60
--- a/hw/net/cadence_gem.c
86
- }
61
+++ b/hw/net/cadence_gem.c
87
-
62
@@ -XXX,XX +XXX,XX @@
88
-MATERIALISE_EXT_PREDICATE(XVentanaCondOps);
63
#define GEM_PHYMNTNC_REG_SHIFT 18
89
-
64
90
#ifdef TARGET_RISCV32
65
/* Marvell PHY definitions */
91
#define get_xl(ctx) MXL_RV32
66
-#define BOARD_PHY_ADDRESS 23 /* PHY address we will emulate a device at */
92
#elif defined(CONFIG_USER_ONLY)
67
+#define BOARD_PHY_ADDRESS 0 /* PHY address we will emulate a device at */
93
@@ -XXX,XX +XXX,XX @@ static void decode_opc(CPURISCVState *env, DisasContext *ctx, uint16_t opcode)
68
94
* that are tested in-order until a decoder matches onto the opcode.
69
#define PHY_REG_CONTROL 0
95
*/
70
#define PHY_REG_STATUS 1
96
static const struct {
71
@@ -XXX,XX +XXX,XX @@ static uint64_t gem_read(void *opaque, hwaddr offset, unsigned size)
97
- bool (*guard_func)(DisasContext *);
72
uint32_t phy_addr, reg_num;
98
+ bool (*guard_func)(const RISCVCPUConfig *);
73
99
bool (*decode_func)(DisasContext *, uint32_t);
74
phy_addr = (retval & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
100
} decoders[] = {
75
- if (phy_addr == s->phy_addr || phy_addr == 0) {
101
{ always_true_p, decode_insn32 },
76
+ if (phy_addr == s->phy_addr) {
102
@@ -XXX,XX +XXX,XX @@ static void decode_opc(CPURISCVState *env, DisasContext *ctx, uint16_t opcode)
77
reg_num = (retval & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
103
ctx->opcode = opcode32;
78
retval &= 0xFFFF0000;
104
79
retval |= gem_phy_read(s, reg_num);
105
for (size_t i = 0; i < ARRAY_SIZE(decoders); ++i) {
80
@@ -XXX,XX +XXX,XX @@ static void gem_write(void *opaque, hwaddr offset, uint64_t val,
106
- if (decoders[i].guard_func(ctx) &&
81
uint32_t phy_addr, reg_num;
107
+ if (decoders[i].guard_func(ctx->cfg_ptr) &&
82
108
decoders[i].decode_func(ctx, opcode32)) {
83
phy_addr = (val & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
109
return;
84
- if (phy_addr == s->phy_addr || phy_addr == 0) {
85
+ if (phy_addr == s->phy_addr) {
86
reg_num = (val & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
87
gem_phy_write(s, reg_num, val);
88
}
110
}
89
--
111
--
90
2.28.0
112
2.40.1
91
113
92
114
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
In order to enable vendor disassembler support, we need to
4
should only contain the RISC-V SoC / machine codes plus generic
4
move types and constants into a header file so that other
5
codes. Let's move sifive_u_prci model to hw/misc directory.
5
compilation units can use them as well.
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
This patch does not introduce any functional changes.
8
9
Reviewed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-3-git-send-email-bmeng.cn@gmail.com>
11
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
12
Message-Id: <20230612111034.3955227-4-christoph.muellner@vrull.eu>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
14
---
12
include/hw/{riscv => misc}/sifive_u_prci.h | 0
15
disas/riscv.h | 282 ++++++++++++++++++++++++++++++++++++++++++++++++++
13
include/hw/riscv/sifive_u.h | 2 +-
16
disas/riscv.c | 270 +----------------------------------------------
14
hw/{riscv => misc}/sifive_u_prci.c | 2 +-
17
2 files changed, 283 insertions(+), 269 deletions(-)
15
hw/misc/Kconfig | 3 +++
18
create mode 100644 disas/riscv.h
16
hw/misc/meson.build | 1 +
17
hw/riscv/Kconfig | 1 +
18
hw/riscv/meson.build | 1 -
19
7 files changed, 7 insertions(+), 3 deletions(-)
20
rename include/hw/{riscv => misc}/sifive_u_prci.h (100%)
21
rename hw/{riscv => misc}/sifive_u_prci.c (99%)
22
19
23
diff --git a/include/hw/riscv/sifive_u_prci.h b/include/hw/misc/sifive_u_prci.h
20
diff --git a/disas/riscv.h b/disas/riscv.h
24
similarity index 100%
21
new file mode 100644
25
rename from include/hw/riscv/sifive_u_prci.h
22
index XXXXXXX..XXXXXXX
26
rename to include/hw/misc/sifive_u_prci.h
23
--- /dev/null
27
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
24
+++ b/disas/riscv.h
25
@@ -XXX,XX +XXX,XX @@
26
+/*
27
+ * QEMU disassembler -- RISC-V specific header.
28
+ *
29
+ * SPDX-License-Identifier: GPL-2.0-or-later
30
+ */
31
+
32
+#ifndef DISAS_RISCV_H
33
+#define DISAS_RISCV_H
34
+
35
+#include "qemu/osdep.h"
36
+#include "target/riscv/cpu_cfg.h"
37
+
38
+/* types */
39
+
40
+typedef uint64_t rv_inst;
41
+typedef uint16_t rv_opcode;
42
+
43
+/* enums */
44
+
45
+typedef enum {
46
+ rv32,
47
+ rv64,
48
+ rv128
49
+} rv_isa;
50
+
51
+typedef enum {
52
+ rv_rm_rne = 0,
53
+ rv_rm_rtz = 1,
54
+ rv_rm_rdn = 2,
55
+ rv_rm_rup = 3,
56
+ rv_rm_rmm = 4,
57
+ rv_rm_dyn = 7,
58
+} rv_rm;
59
+
60
+typedef enum {
61
+ rv_fence_i = 8,
62
+ rv_fence_o = 4,
63
+ rv_fence_r = 2,
64
+ rv_fence_w = 1,
65
+} rv_fence;
66
+
67
+typedef enum {
68
+ rv_ireg_zero,
69
+ rv_ireg_ra,
70
+ rv_ireg_sp,
71
+ rv_ireg_gp,
72
+ rv_ireg_tp,
73
+ rv_ireg_t0,
74
+ rv_ireg_t1,
75
+ rv_ireg_t2,
76
+ rv_ireg_s0,
77
+ rv_ireg_s1,
78
+ rv_ireg_a0,
79
+ rv_ireg_a1,
80
+ rv_ireg_a2,
81
+ rv_ireg_a3,
82
+ rv_ireg_a4,
83
+ rv_ireg_a5,
84
+ rv_ireg_a6,
85
+ rv_ireg_a7,
86
+ rv_ireg_s2,
87
+ rv_ireg_s3,
88
+ rv_ireg_s4,
89
+ rv_ireg_s5,
90
+ rv_ireg_s6,
91
+ rv_ireg_s7,
92
+ rv_ireg_s8,
93
+ rv_ireg_s9,
94
+ rv_ireg_s10,
95
+ rv_ireg_s11,
96
+ rv_ireg_t3,
97
+ rv_ireg_t4,
98
+ rv_ireg_t5,
99
+ rv_ireg_t6,
100
+} rv_ireg;
101
+
102
+typedef enum {
103
+ rvc_end,
104
+ rvc_rd_eq_ra,
105
+ rvc_rd_eq_x0,
106
+ rvc_rs1_eq_x0,
107
+ rvc_rs2_eq_x0,
108
+ rvc_rs2_eq_rs1,
109
+ rvc_rs1_eq_ra,
110
+ rvc_imm_eq_zero,
111
+ rvc_imm_eq_n1,
112
+ rvc_imm_eq_p1,
113
+ rvc_csr_eq_0x001,
114
+ rvc_csr_eq_0x002,
115
+ rvc_csr_eq_0x003,
116
+ rvc_csr_eq_0xc00,
117
+ rvc_csr_eq_0xc01,
118
+ rvc_csr_eq_0xc02,
119
+ rvc_csr_eq_0xc80,
120
+ rvc_csr_eq_0xc81,
121
+ rvc_csr_eq_0xc82,
122
+} rvc_constraint;
123
+
124
+typedef enum {
125
+ rv_codec_illegal,
126
+ rv_codec_none,
127
+ rv_codec_u,
128
+ rv_codec_uj,
129
+ rv_codec_i,
130
+ rv_codec_i_sh5,
131
+ rv_codec_i_sh6,
132
+ rv_codec_i_sh7,
133
+ rv_codec_i_csr,
134
+ rv_codec_s,
135
+ rv_codec_sb,
136
+ rv_codec_r,
137
+ rv_codec_r_m,
138
+ rv_codec_r4_m,
139
+ rv_codec_r_a,
140
+ rv_codec_r_l,
141
+ rv_codec_r_f,
142
+ rv_codec_cb,
143
+ rv_codec_cb_imm,
144
+ rv_codec_cb_sh5,
145
+ rv_codec_cb_sh6,
146
+ rv_codec_ci,
147
+ rv_codec_ci_sh5,
148
+ rv_codec_ci_sh6,
149
+ rv_codec_ci_16sp,
150
+ rv_codec_ci_lwsp,
151
+ rv_codec_ci_ldsp,
152
+ rv_codec_ci_lqsp,
153
+ rv_codec_ci_li,
154
+ rv_codec_ci_lui,
155
+ rv_codec_ci_none,
156
+ rv_codec_ciw_4spn,
157
+ rv_codec_cj,
158
+ rv_codec_cj_jal,
159
+ rv_codec_cl_lw,
160
+ rv_codec_cl_ld,
161
+ rv_codec_cl_lq,
162
+ rv_codec_cr,
163
+ rv_codec_cr_mv,
164
+ rv_codec_cr_jalr,
165
+ rv_codec_cr_jr,
166
+ rv_codec_cs,
167
+ rv_codec_cs_sw,
168
+ rv_codec_cs_sd,
169
+ rv_codec_cs_sq,
170
+ rv_codec_css_swsp,
171
+ rv_codec_css_sdsp,
172
+ rv_codec_css_sqsp,
173
+ rv_codec_k_bs,
174
+ rv_codec_k_rnum,
175
+ rv_codec_v_r,
176
+ rv_codec_v_ldst,
177
+ rv_codec_v_i,
178
+ rv_codec_vsetvli,
179
+ rv_codec_vsetivli,
180
+ rv_codec_zcb_ext,
181
+ rv_codec_zcb_mul,
182
+ rv_codec_zcb_lb,
183
+ rv_codec_zcb_lh,
184
+ rv_codec_zcmp_cm_pushpop,
185
+ rv_codec_zcmp_cm_mv,
186
+ rv_codec_zcmt_jt,
187
+} rv_codec;
188
+
189
+/* structures */
190
+
191
+typedef struct {
192
+ RISCVCPUConfig *cfg;
193
+ uint64_t pc;
194
+ uint64_t inst;
195
+ int32_t imm;
196
+ uint16_t op;
197
+ uint8_t codec;
198
+ uint8_t rd;
199
+ uint8_t rs1;
200
+ uint8_t rs2;
201
+ uint8_t rs3;
202
+ uint8_t rm;
203
+ uint8_t pred;
204
+ uint8_t succ;
205
+ uint8_t aq;
206
+ uint8_t rl;
207
+ uint8_t bs;
208
+ uint8_t rnum;
209
+ uint8_t vm;
210
+ uint32_t vzimm;
211
+ uint8_t rlist;
212
+} rv_decode;
213
+
214
+typedef struct {
215
+ const int op;
216
+ const rvc_constraint *constraints;
217
+} rv_comp_data;
218
+
219
+enum {
220
+ rvcd_imm_nz = 0x1
221
+};
222
+
223
+typedef struct {
224
+ const char * const name;
225
+ const rv_codec codec;
226
+ const char * const format;
227
+ const rv_comp_data *pseudo;
228
+ const short decomp_rv32;
229
+ const short decomp_rv64;
230
+ const short decomp_rv128;
231
+ const short decomp_data;
232
+} rv_opcode_data;
233
+
234
+/* instruction formats */
235
+
236
+#define rv_fmt_none "O\t"
237
+#define rv_fmt_rs1 "O\t1"
238
+#define rv_fmt_offset "O\to"
239
+#define rv_fmt_pred_succ "O\tp,s"
240
+#define rv_fmt_rs1_rs2 "O\t1,2"
241
+#define rv_fmt_rd_imm "O\t0,i"
242
+#define rv_fmt_rd_offset "O\t0,o"
243
+#define rv_fmt_rd_rs1_rs2 "O\t0,1,2"
244
+#define rv_fmt_frd_rs1 "O\t3,1"
245
+#define rv_fmt_frd_frs1 "O\t3,4"
246
+#define rv_fmt_rd_frs1 "O\t0,4"
247
+#define rv_fmt_rd_frs1_frs2 "O\t0,4,5"
248
+#define rv_fmt_frd_frs1_frs2 "O\t3,4,5"
249
+#define rv_fmt_rm_frd_frs1 "O\tr,3,4"
250
+#define rv_fmt_rm_frd_rs1 "O\tr,3,1"
251
+#define rv_fmt_rm_rd_frs1 "O\tr,0,4"
252
+#define rv_fmt_rm_frd_frs1_frs2 "O\tr,3,4,5"
253
+#define rv_fmt_rm_frd_frs1_frs2_frs3 "O\tr,3,4,5,6"
254
+#define rv_fmt_rd_rs1_imm "O\t0,1,i"
255
+#define rv_fmt_rd_rs1_offset "O\t0,1,i"
256
+#define rv_fmt_rd_offset_rs1 "O\t0,i(1)"
257
+#define rv_fmt_frd_offset_rs1 "O\t3,i(1)"
258
+#define rv_fmt_rd_csr_rs1 "O\t0,c,1"
259
+#define rv_fmt_rd_csr_zimm "O\t0,c,7"
260
+#define rv_fmt_rs2_offset_rs1 "O\t2,i(1)"
261
+#define rv_fmt_frs2_offset_rs1 "O\t5,i(1)"
262
+#define rv_fmt_rs1_rs2_offset "O\t1,2,o"
263
+#define rv_fmt_rs2_rs1_offset "O\t2,1,o"
264
+#define rv_fmt_aqrl_rd_rs2_rs1 "OAR\t0,2,(1)"
265
+#define rv_fmt_aqrl_rd_rs1 "OAR\t0,(1)"
266
+#define rv_fmt_rd "O\t0"
267
+#define rv_fmt_rd_zimm "O\t0,7"
268
+#define rv_fmt_rd_rs1 "O\t0,1"
269
+#define rv_fmt_rd_rs2 "O\t0,2"
270
+#define rv_fmt_rs1_offset "O\t1,o"
271
+#define rv_fmt_rs2_offset "O\t2,o"
272
+#define rv_fmt_rs1_rs2_bs "O\t1,2,b"
273
+#define rv_fmt_rd_rs1_rnum "O\t0,1,n"
274
+#define rv_fmt_ldst_vd_rs1_vm "O\tD,(1)m"
275
+#define rv_fmt_ldst_vd_rs1_rs2_vm "O\tD,(1),2m"
276
+#define rv_fmt_ldst_vd_rs1_vs2_vm "O\tD,(1),Fm"
277
+#define rv_fmt_vd_vs2_vs1 "O\tD,F,E"
278
+#define rv_fmt_vd_vs2_vs1_vl "O\tD,F,El"
279
+#define rv_fmt_vd_vs2_vs1_vm "O\tD,F,Em"
280
+#define rv_fmt_vd_vs2_rs1_vl "O\tD,F,1l"
281
+#define rv_fmt_vd_vs2_fs1_vl "O\tD,F,4l"
282
+#define rv_fmt_vd_vs2_rs1_vm "O\tD,F,1m"
283
+#define rv_fmt_vd_vs2_fs1_vm "O\tD,F,4m"
284
+#define rv_fmt_vd_vs2_imm_vl "O\tD,F,il"
285
+#define rv_fmt_vd_vs2_imm_vm "O\tD,F,im"
286
+#define rv_fmt_vd_vs2_uimm_vm "O\tD,F,um"
287
+#define rv_fmt_vd_vs1_vs2_vm "O\tD,E,Fm"
288
+#define rv_fmt_vd_rs1_vs2_vm "O\tD,1,Fm"
289
+#define rv_fmt_vd_fs1_vs2_vm "O\tD,4,Fm"
290
+#define rv_fmt_vd_vs1 "O\tD,E"
291
+#define rv_fmt_vd_rs1 "O\tD,1"
292
+#define rv_fmt_vd_fs1 "O\tD,4"
293
+#define rv_fmt_vd_imm "O\tD,i"
294
+#define rv_fmt_vd_vs2 "O\tD,F"
295
+#define rv_fmt_vd_vs2_vm "O\tD,Fm"
296
+#define rv_fmt_rd_vs2_vm "O\t0,Fm"
297
+#define rv_fmt_rd_vs2 "O\t0,F"
298
+#define rv_fmt_fd_vs2 "O\t3,F"
299
+#define rv_fmt_vd_vm "O\tDm"
300
+#define rv_fmt_vsetvli "O\t0,1,v"
301
+#define rv_fmt_vsetivli "O\t0,u,v"
302
+#define rv_fmt_rs1_rs2_zce_ldst "O\t2,i(1)"
303
+#define rv_fmt_push_rlist "O\tx,-i"
304
+#define rv_fmt_pop_rlist "O\tx,i"
305
+#define rv_fmt_zcmt_index "O\ti"
306
+
307
+#endif /* DISAS_RISCV_H */
308
diff --git a/disas/riscv.c b/disas/riscv.c
28
index XXXXXXX..XXXXXXX 100644
309
index XXXXXXX..XXXXXXX 100644
29
--- a/include/hw/riscv/sifive_u.h
310
--- a/disas/riscv.c
30
+++ b/include/hw/riscv/sifive_u.h
311
+++ b/disas/riscv.c
31
@@ -XXX,XX +XXX,XX @@
312
@@ -XXX,XX +XXX,XX @@
32
#include "hw/riscv/riscv_hart.h"
313
#include "qemu/osdep.h"
33
#include "hw/riscv/sifive_cpu.h"
314
#include "disas/dis-asm.h"
34
#include "hw/riscv/sifive_gpio.h"
315
#include "target/riscv/cpu_cfg.h"
35
-#include "hw/riscv/sifive_u_prci.h"
316
-
36
#include "hw/riscv/sifive_u_otp.h"
317
-/* types */
37
+#include "hw/misc/sifive_u_prci.h"
318
-
38
319
-typedef uint64_t rv_inst;
39
#define TYPE_RISCV_U_SOC "riscv.sifive.u.soc"
320
-typedef uint16_t rv_opcode;
40
#define RISCV_U_SOC(obj) \
321
-
41
diff --git a/hw/riscv/sifive_u_prci.c b/hw/misc/sifive_u_prci.c
322
-/* enums */
42
similarity index 99%
323
-
43
rename from hw/riscv/sifive_u_prci.c
324
-typedef enum {
44
rename to hw/misc/sifive_u_prci.c
325
- rv32,
45
index XXXXXXX..XXXXXXX 100644
326
- rv64,
46
--- a/hw/riscv/sifive_u_prci.c
327
- rv128
47
+++ b/hw/misc/sifive_u_prci.c
328
-} rv_isa;
48
@@ -XXX,XX +XXX,XX @@
329
-
49
#include "hw/sysbus.h"
330
-typedef enum {
50
#include "qemu/log.h"
331
- rv_rm_rne = 0,
51
#include "qemu/module.h"
332
- rv_rm_rtz = 1,
52
-#include "hw/riscv/sifive_u_prci.h"
333
- rv_rm_rdn = 2,
53
+#include "hw/misc/sifive_u_prci.h"
334
- rv_rm_rup = 3,
54
335
- rv_rm_rmm = 4,
55
static uint64_t sifive_u_prci_read(void *opaque, hwaddr addr, unsigned int size)
336
- rv_rm_dyn = 7,
56
{
337
-} rv_rm;
57
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
338
-
58
index XXXXXXX..XXXXXXX 100644
339
-typedef enum {
59
--- a/hw/misc/Kconfig
340
- rv_fence_i = 8,
60
+++ b/hw/misc/Kconfig
341
- rv_fence_o = 4,
61
@@ -XXX,XX +XXX,XX @@ config AVR_POWER
342
- rv_fence_r = 2,
62
config SIFIVE_E_PRCI
343
- rv_fence_w = 1,
63
bool
344
-} rv_fence;
64
345
-
65
+config SIFIVE_U_PRCI
346
-typedef enum {
66
+ bool
347
- rv_ireg_zero,
67
+
348
- rv_ireg_ra,
68
source macio/Kconfig
349
- rv_ireg_sp,
69
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
350
- rv_ireg_gp,
70
index XXXXXXX..XXXXXXX 100644
351
- rv_ireg_tp,
71
--- a/hw/misc/meson.build
352
- rv_ireg_t0,
72
+++ b/hw/misc/meson.build
353
- rv_ireg_t1,
73
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_MOS6522', if_true: files('mos6522.c'))
354
- rv_ireg_t2,
74
355
- rv_ireg_s0,
75
# RISC-V devices
356
- rv_ireg_s1,
76
softmmu_ss.add(when: 'CONFIG_SIFIVE_E_PRCI', if_true: files('sifive_e_prci.c'))
357
- rv_ireg_a0,
77
+softmmu_ss.add(when: 'CONFIG_SIFIVE_U_PRCI', if_true: files('sifive_u_prci.c'))
358
- rv_ireg_a1,
78
359
- rv_ireg_a2,
79
# PKUnity SoC devices
360
- rv_ireg_a3,
80
softmmu_ss.add(when: 'CONFIG_PUV3', if_true: files('puv3_pm.c'))
361
- rv_ireg_a4,
81
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
362
- rv_ireg_a5,
82
index XXXXXXX..XXXXXXX 100644
363
- rv_ireg_a6,
83
--- a/hw/riscv/Kconfig
364
- rv_ireg_a7,
84
+++ b/hw/riscv/Kconfig
365
- rv_ireg_s2,
85
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
366
- rv_ireg_s3,
86
select HART
367
- rv_ireg_s4,
87
select SIFIVE
368
- rv_ireg_s5,
88
select SIFIVE_PDMA
369
- rv_ireg_s6,
89
+ select SIFIVE_U_PRCI
370
- rv_ireg_s7,
90
select UNIMP
371
- rv_ireg_s8,
91
372
- rv_ireg_s9,
92
config SPIKE
373
- rv_ireg_s10,
93
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
374
- rv_ireg_s11,
94
index XXXXXXX..XXXXXXX 100644
375
- rv_ireg_t3,
95
--- a/hw/riscv/meson.build
376
- rv_ireg_t4,
96
+++ b/hw/riscv/meson.build
377
- rv_ireg_t5,
97
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
378
- rv_ireg_t6,
98
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
379
-} rv_ireg;
99
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
380
-
100
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_otp.c'))
381
-typedef enum {
101
-riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_prci.c'))
382
- rvc_end,
102
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('riscv_htif.c'))
383
- rvc_rd_eq_ra,
103
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
384
- rvc_rd_eq_x0,
104
riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c'))
385
- rvc_rs1_eq_x0,
386
- rvc_rs2_eq_x0,
387
- rvc_rs2_eq_rs1,
388
- rvc_rs1_eq_ra,
389
- rvc_imm_eq_zero,
390
- rvc_imm_eq_n1,
391
- rvc_imm_eq_p1,
392
- rvc_csr_eq_0x001,
393
- rvc_csr_eq_0x002,
394
- rvc_csr_eq_0x003,
395
- rvc_csr_eq_0xc00,
396
- rvc_csr_eq_0xc01,
397
- rvc_csr_eq_0xc02,
398
- rvc_csr_eq_0xc80,
399
- rvc_csr_eq_0xc81,
400
- rvc_csr_eq_0xc82,
401
-} rvc_constraint;
402
-
403
-typedef enum {
404
- rv_codec_illegal,
405
- rv_codec_none,
406
- rv_codec_u,
407
- rv_codec_uj,
408
- rv_codec_i,
409
- rv_codec_i_sh5,
410
- rv_codec_i_sh6,
411
- rv_codec_i_sh7,
412
- rv_codec_i_csr,
413
- rv_codec_s,
414
- rv_codec_sb,
415
- rv_codec_r,
416
- rv_codec_r_m,
417
- rv_codec_r4_m,
418
- rv_codec_r_a,
419
- rv_codec_r_l,
420
- rv_codec_r_f,
421
- rv_codec_cb,
422
- rv_codec_cb_imm,
423
- rv_codec_cb_sh5,
424
- rv_codec_cb_sh6,
425
- rv_codec_ci,
426
- rv_codec_ci_sh5,
427
- rv_codec_ci_sh6,
428
- rv_codec_ci_16sp,
429
- rv_codec_ci_lwsp,
430
- rv_codec_ci_ldsp,
431
- rv_codec_ci_lqsp,
432
- rv_codec_ci_li,
433
- rv_codec_ci_lui,
434
- rv_codec_ci_none,
435
- rv_codec_ciw_4spn,
436
- rv_codec_cj,
437
- rv_codec_cj_jal,
438
- rv_codec_cl_lw,
439
- rv_codec_cl_ld,
440
- rv_codec_cl_lq,
441
- rv_codec_cr,
442
- rv_codec_cr_mv,
443
- rv_codec_cr_jalr,
444
- rv_codec_cr_jr,
445
- rv_codec_cs,
446
- rv_codec_cs_sw,
447
- rv_codec_cs_sd,
448
- rv_codec_cs_sq,
449
- rv_codec_css_swsp,
450
- rv_codec_css_sdsp,
451
- rv_codec_css_sqsp,
452
- rv_codec_k_bs,
453
- rv_codec_k_rnum,
454
- rv_codec_v_r,
455
- rv_codec_v_ldst,
456
- rv_codec_v_i,
457
- rv_codec_vsetvli,
458
- rv_codec_vsetivli,
459
- rv_codec_zcb_ext,
460
- rv_codec_zcb_mul,
461
- rv_codec_zcb_lb,
462
- rv_codec_zcb_lh,
463
- rv_codec_zcmp_cm_pushpop,
464
- rv_codec_zcmp_cm_mv,
465
- rv_codec_zcmt_jt,
466
-} rv_codec;
467
+#include "disas/riscv.h"
468
469
typedef enum {
470
rv_op_illegal = 0,
471
@@ -XXX,XX +XXX,XX @@ typedef enum {
472
rv_op_czero_nez = 790,
473
} rv_op;
474
475
-/* structures */
476
-
477
-typedef struct {
478
- RISCVCPUConfig *cfg;
479
- uint64_t pc;
480
- uint64_t inst;
481
- int32_t imm;
482
- uint16_t op;
483
- uint8_t codec;
484
- uint8_t rd;
485
- uint8_t rs1;
486
- uint8_t rs2;
487
- uint8_t rs3;
488
- uint8_t rm;
489
- uint8_t pred;
490
- uint8_t succ;
491
- uint8_t aq;
492
- uint8_t rl;
493
- uint8_t bs;
494
- uint8_t rnum;
495
- uint8_t vm;
496
- uint32_t vzimm;
497
- uint8_t rlist;
498
-} rv_decode;
499
-
500
-typedef struct {
501
- const int op;
502
- const rvc_constraint *constraints;
503
-} rv_comp_data;
504
-
505
-enum {
506
- rvcd_imm_nz = 0x1
507
-};
508
-
509
-typedef struct {
510
- const char * const name;
511
- const rv_codec codec;
512
- const char * const format;
513
- const rv_comp_data *pseudo;
514
- const short decomp_rv32;
515
- const short decomp_rv64;
516
- const short decomp_rv128;
517
- const short decomp_data;
518
-} rv_opcode_data;
519
-
520
/* register names */
521
522
static const char rv_ireg_name_sym[32][5] = {
523
@@ -XXX,XX +XXX,XX @@ static const char rv_vreg_name_sym[32][4] = {
524
"v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31"
525
};
526
527
-/* instruction formats */
528
-
529
-#define rv_fmt_none "O\t"
530
-#define rv_fmt_rs1 "O\t1"
531
-#define rv_fmt_offset "O\to"
532
-#define rv_fmt_pred_succ "O\tp,s"
533
-#define rv_fmt_rs1_rs2 "O\t1,2"
534
-#define rv_fmt_rd_imm "O\t0,i"
535
-#define rv_fmt_rd_offset "O\t0,o"
536
-#define rv_fmt_rd_rs1_rs2 "O\t0,1,2"
537
-#define rv_fmt_frd_rs1 "O\t3,1"
538
-#define rv_fmt_frd_frs1 "O\t3,4"
539
-#define rv_fmt_rd_frs1 "O\t0,4"
540
-#define rv_fmt_rd_frs1_frs2 "O\t0,4,5"
541
-#define rv_fmt_frd_frs1_frs2 "O\t3,4,5"
542
-#define rv_fmt_rm_frd_frs1 "O\tr,3,4"
543
-#define rv_fmt_rm_frd_rs1 "O\tr,3,1"
544
-#define rv_fmt_rm_rd_frs1 "O\tr,0,4"
545
-#define rv_fmt_rm_frd_frs1_frs2 "O\tr,3,4,5"
546
-#define rv_fmt_rm_frd_frs1_frs2_frs3 "O\tr,3,4,5,6"
547
-#define rv_fmt_rd_rs1_imm "O\t0,1,i"
548
-#define rv_fmt_rd_rs1_offset "O\t0,1,i"
549
-#define rv_fmt_rd_offset_rs1 "O\t0,i(1)"
550
-#define rv_fmt_frd_offset_rs1 "O\t3,i(1)"
551
-#define rv_fmt_rd_csr_rs1 "O\t0,c,1"
552
-#define rv_fmt_rd_csr_zimm "O\t0,c,7"
553
-#define rv_fmt_rs2_offset_rs1 "O\t2,i(1)"
554
-#define rv_fmt_frs2_offset_rs1 "O\t5,i(1)"
555
-#define rv_fmt_rs1_rs2_offset "O\t1,2,o"
556
-#define rv_fmt_rs2_rs1_offset "O\t2,1,o"
557
-#define rv_fmt_aqrl_rd_rs2_rs1 "OAR\t0,2,(1)"
558
-#define rv_fmt_aqrl_rd_rs1 "OAR\t0,(1)"
559
-#define rv_fmt_rd "O\t0"
560
-#define rv_fmt_rd_zimm "O\t0,7"
561
-#define rv_fmt_rd_rs1 "O\t0,1"
562
-#define rv_fmt_rd_rs2 "O\t0,2"
563
-#define rv_fmt_rs1_offset "O\t1,o"
564
-#define rv_fmt_rs2_offset "O\t2,o"
565
-#define rv_fmt_rs1_rs2_bs "O\t1,2,b"
566
-#define rv_fmt_rd_rs1_rnum "O\t0,1,n"
567
-#define rv_fmt_ldst_vd_rs1_vm "O\tD,(1)m"
568
-#define rv_fmt_ldst_vd_rs1_rs2_vm "O\tD,(1),2m"
569
-#define rv_fmt_ldst_vd_rs1_vs2_vm "O\tD,(1),Fm"
570
-#define rv_fmt_vd_vs2_vs1 "O\tD,F,E"
571
-#define rv_fmt_vd_vs2_vs1_vl "O\tD,F,El"
572
-#define rv_fmt_vd_vs2_vs1_vm "O\tD,F,Em"
573
-#define rv_fmt_vd_vs2_rs1_vl "O\tD,F,1l"
574
-#define rv_fmt_vd_vs2_fs1_vl "O\tD,F,4l"
575
-#define rv_fmt_vd_vs2_rs1_vm "O\tD,F,1m"
576
-#define rv_fmt_vd_vs2_fs1_vm "O\tD,F,4m"
577
-#define rv_fmt_vd_vs2_imm_vl "O\tD,F,il"
578
-#define rv_fmt_vd_vs2_imm_vm "O\tD,F,im"
579
-#define rv_fmt_vd_vs2_uimm_vm "O\tD,F,um"
580
-#define rv_fmt_vd_vs1_vs2_vm "O\tD,E,Fm"
581
-#define rv_fmt_vd_rs1_vs2_vm "O\tD,1,Fm"
582
-#define rv_fmt_vd_fs1_vs2_vm "O\tD,4,Fm"
583
-#define rv_fmt_vd_vs1 "O\tD,E"
584
-#define rv_fmt_vd_rs1 "O\tD,1"
585
-#define rv_fmt_vd_fs1 "O\tD,4"
586
-#define rv_fmt_vd_imm "O\tD,i"
587
-#define rv_fmt_vd_vs2 "O\tD,F"
588
-#define rv_fmt_vd_vs2_vm "O\tD,Fm"
589
-#define rv_fmt_rd_vs2_vm "O\t0,Fm"
590
-#define rv_fmt_rd_vs2 "O\t0,F"
591
-#define rv_fmt_fd_vs2 "O\t3,F"
592
-#define rv_fmt_vd_vm "O\tDm"
593
-#define rv_fmt_vsetvli "O\t0,1,v"
594
-#define rv_fmt_vsetivli "O\t0,u,v"
595
-#define rv_fmt_rs1_rs2_zce_ldst "O\t2,i(1)"
596
-#define rv_fmt_push_rlist "O\tx,-i"
597
-#define rv_fmt_pop_rlist "O\tx,i"
598
-#define rv_fmt_zcmt_index "O\ti"
599
-
600
/* pseudo-instruction constraints */
601
602
static const rvc_constraint rvcc_jal[] = { rvc_rd_eq_ra, rvc_end };
105
--
603
--
106
2.28.0
604
2.40.1
107
605
108
606
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
Microchip PolarFire SoC has 5 MMUARTs, and the Icicle Kit board
3
The enum value 'rv_op_illegal' does not represent an
4
wires 4 of them out. Let's connect all 5 MMUARTs.
4
instruction, but is a catch-all value in case we have
5
no match in the decoder. Let's make the value a shared
6
one, so that other compile units can reuse it.
5
7
6
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
Message-Id: <1598924352-89526-7-git-send-email-bmeng.cn@gmail.com>
9
Reviewed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
10
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
11
Message-Id: <20230612111034.3955227-5-christoph.muellner@vrull.eu>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
---
13
---
11
include/hw/riscv/microchip_pfsoc.h | 20 ++++++++++++++++++++
14
disas/riscv.h | 4 ++++
12
hw/riscv/microchip_pfsoc.c | 30 ++++++++++++++++++++++++++++++
15
disas/riscv.c | 2 +-
13
hw/riscv/Kconfig | 1 +
16
2 files changed, 5 insertions(+), 1 deletion(-)
14
3 files changed, 51 insertions(+)
15
17
16
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
18
diff --git a/disas/riscv.h b/disas/riscv.h
17
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
18
--- a/include/hw/riscv/microchip_pfsoc.h
20
--- a/disas/riscv.h
19
+++ b/include/hw/riscv/microchip_pfsoc.h
21
+++ b/disas/riscv.h
20
@@ -XXX,XX +XXX,XX @@
22
@@ -XXX,XX +XXX,XX @@ typedef struct {
21
#ifndef HW_MICROCHIP_PFSOC_H
23
const rvc_constraint *constraints;
22
#define HW_MICROCHIP_PFSOC_H
24
} rv_comp_data;
23
24
+#include "hw/char/mchp_pfsoc_mmuart.h"
25
+
26
typedef struct MicrochipPFSoCState {
27
/*< private >*/
28
DeviceState parent_obj;
29
@@ -XXX,XX +XXX,XX @@ typedef struct MicrochipPFSoCState {
30
RISCVHartArrayState e_cpus;
31
RISCVHartArrayState u_cpus;
32
DeviceState *plic;
33
+ MchpPfSoCMMUartState *serial0;
34
+ MchpPfSoCMMUartState *serial1;
35
+ MchpPfSoCMMUartState *serial2;
36
+ MchpPfSoCMMUartState *serial3;
37
+ MchpPfSoCMMUartState *serial4;
38
} MicrochipPFSoCState;
39
40
#define TYPE_MICROCHIP_PFSOC "microchip.pfsoc"
41
@@ -XXX,XX +XXX,XX @@ enum {
42
MICROCHIP_PFSOC_L2CC,
43
MICROCHIP_PFSOC_L2LIM,
44
MICROCHIP_PFSOC_PLIC,
45
+ MICROCHIP_PFSOC_MMUART0,
46
MICROCHIP_PFSOC_SYSREG,
47
MICROCHIP_PFSOC_MPUCFG,
48
+ MICROCHIP_PFSOC_MMUART1,
49
+ MICROCHIP_PFSOC_MMUART2,
50
+ MICROCHIP_PFSOC_MMUART3,
51
+ MICROCHIP_PFSOC_MMUART4,
52
MICROCHIP_PFSOC_ENVM_CFG,
53
MICROCHIP_PFSOC_ENVM_DATA,
54
MICROCHIP_PFSOC_IOSCB_CFG,
55
MICROCHIP_PFSOC_DRAM,
56
};
57
25
58
+enum {
26
+enum {
59
+ MICROCHIP_PFSOC_MMUART0_IRQ = 90,
27
+ rv_op_illegal = 0
60
+ MICROCHIP_PFSOC_MMUART1_IRQ = 91,
61
+ MICROCHIP_PFSOC_MMUART2_IRQ = 92,
62
+ MICROCHIP_PFSOC_MMUART3_IRQ = 93,
63
+ MICROCHIP_PFSOC_MMUART4_IRQ = 94,
64
+};
28
+};
65
+
29
+
66
#define MICROCHIP_PFSOC_MANAGEMENT_CPU_COUNT 1
30
enum {
67
#define MICROCHIP_PFSOC_COMPUTE_CPU_COUNT 4
31
rvcd_imm_nz = 0x1
68
32
};
69
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
33
diff --git a/disas/riscv.c b/disas/riscv.c
70
index XXXXXXX..XXXXXXX 100644
34
index XXXXXXX..XXXXXXX 100644
71
--- a/hw/riscv/microchip_pfsoc.c
35
--- a/disas/riscv.c
72
+++ b/hw/riscv/microchip_pfsoc.c
36
+++ b/disas/riscv.c
73
@@ -XXX,XX +XXX,XX @@
37
@@ -XXX,XX +XXX,XX @@
74
* 0) CLINT (Core Level Interruptor)
38
#include "disas/riscv.h"
75
* 1) PLIC (Platform Level Interrupt Controller)
39
76
* 2) eNVM (Embedded Non-Volatile Memory)
40
typedef enum {
77
+ * 3) MMUARTs (Multi-Mode UART)
41
- rv_op_illegal = 0,
78
*
42
+ /* 0 is reserved for rv_op_illegal. */
79
* This board currently generates devicetree dynamically that indicates at least
43
rv_op_lui = 1,
80
* two harts and up to five harts.
44
rv_op_auipc = 2,
81
@@ -XXX,XX +XXX,XX @@
45
rv_op_jal = 3,
82
#include "hw/irq.h"
83
#include "hw/loader.h"
84
#include "hw/sysbus.h"
85
+#include "chardev/char.h"
86
#include "hw/cpu/cluster.h"
87
#include "target/riscv/cpu.h"
88
#include "hw/misc/unimp.h"
89
@@ -XXX,XX +XXX,XX @@
90
#include "hw/riscv/sifive_clint.h"
91
#include "hw/riscv/sifive_plic.h"
92
#include "hw/riscv/microchip_pfsoc.h"
93
+#include "sysemu/sysemu.h"
94
95
/*
96
* The BIOS image used by this machine is called Hart Software Services (HSS).
97
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
98
[MICROCHIP_PFSOC_L2CC] = { 0x2010000, 0x1000 },
99
[MICROCHIP_PFSOC_L2LIM] = { 0x8000000, 0x2000000 },
100
[MICROCHIP_PFSOC_PLIC] = { 0xc000000, 0x4000000 },
101
+ [MICROCHIP_PFSOC_MMUART0] = { 0x20000000, 0x1000 },
102
[MICROCHIP_PFSOC_SYSREG] = { 0x20002000, 0x2000 },
103
[MICROCHIP_PFSOC_MPUCFG] = { 0x20005000, 0x1000 },
104
+ [MICROCHIP_PFSOC_MMUART1] = { 0x20100000, 0x1000 },
105
+ [MICROCHIP_PFSOC_MMUART2] = { 0x20102000, 0x1000 },
106
+ [MICROCHIP_PFSOC_MMUART3] = { 0x20104000, 0x1000 },
107
+ [MICROCHIP_PFSOC_MMUART4] = { 0x20106000, 0x1000 },
108
[MICROCHIP_PFSOC_ENVM_CFG] = { 0x20200000, 0x1000 },
109
[MICROCHIP_PFSOC_ENVM_DATA] = { 0x20220000, 0x20000 },
110
[MICROCHIP_PFSOC_IOSCB_CFG] = { 0x37080000, 0x1000 },
111
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
112
memmap[MICROCHIP_PFSOC_MPUCFG].base,
113
memmap[MICROCHIP_PFSOC_MPUCFG].size);
114
115
+ /* MMUARTs */
116
+ s->serial0 = mchp_pfsoc_mmuart_create(system_memory,
117
+ memmap[MICROCHIP_PFSOC_MMUART0].base,
118
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART0_IRQ),
119
+ serial_hd(0));
120
+ s->serial1 = mchp_pfsoc_mmuart_create(system_memory,
121
+ memmap[MICROCHIP_PFSOC_MMUART1].base,
122
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART1_IRQ),
123
+ serial_hd(1));
124
+ s->serial2 = mchp_pfsoc_mmuart_create(system_memory,
125
+ memmap[MICROCHIP_PFSOC_MMUART2].base,
126
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART2_IRQ),
127
+ serial_hd(2));
128
+ s->serial3 = mchp_pfsoc_mmuart_create(system_memory,
129
+ memmap[MICROCHIP_PFSOC_MMUART3].base,
130
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART3_IRQ),
131
+ serial_hd(3));
132
+ s->serial4 = mchp_pfsoc_mmuart_create(system_memory,
133
+ memmap[MICROCHIP_PFSOC_MMUART4].base,
134
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART4_IRQ),
135
+ serial_hd(4));
136
+
137
/* eNVM */
138
memory_region_init_rom(envm_data, OBJECT(dev), "microchip.pfsoc.envm.data",
139
memmap[MICROCHIP_PFSOC_ENVM_DATA].size,
140
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
141
index XXXXXXX..XXXXXXX 100644
142
--- a/hw/riscv/Kconfig
143
+++ b/hw/riscv/Kconfig
144
@@ -XXX,XX +XXX,XX @@ config MICROCHIP_PFSOC
145
select HART
146
select SIFIVE
147
select UNIMP
148
+ select MCHP_PFSOC_MMUART
149
--
46
--
150
2.28.0
47
2.40.1
151
48
152
49
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
This patch adds a reference to a struct rv_opcode_data object
4
should only contain the RISC-V SoC / machine codes plus generic
4
into struct rv_decode. This further allows to remove all references
5
codes. Let's move sifive_u_otp model to hw/misc directory.
5
to the global variable opcode_data (which is renamed to rvi_opcode_data).
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
This patch does not introduce any functional change, but prepares
8
the code for more struct rv_opcode_data objects in the future.
9
10
This patch is based on previous work from Liu Zhiwei:
11
https://lists.nongnu.org/archive/html/qemu-devel/2022-08/msg03662.html
12
13
Co-developed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
14
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-4-git-send-email-bmeng.cn@gmail.com>
15
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
16
Message-Id: <20230612111034.3955227-6-christoph.muellner@vrull.eu>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
17
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
18
---
12
include/hw/{riscv => misc}/sifive_u_otp.h | 0
19
disas/riscv.h | 33 +++++++++++++++++----------------
13
include/hw/riscv/sifive_u.h | 2 +-
20
disas/riscv.c | 9 ++++++++-
14
hw/{riscv => misc}/sifive_u_otp.c | 2 +-
21
2 files changed, 25 insertions(+), 17 deletions(-)
15
hw/misc/Kconfig | 3 +++
16
hw/misc/meson.build | 1 +
17
hw/riscv/Kconfig | 1 +
18
hw/riscv/meson.build | 1 -
19
7 files changed, 7 insertions(+), 3 deletions(-)
20
rename include/hw/{riscv => misc}/sifive_u_otp.h (100%)
21
rename hw/{riscv => misc}/sifive_u_otp.c (99%)
22
22
23
diff --git a/include/hw/riscv/sifive_u_otp.h b/include/hw/misc/sifive_u_otp.h
23
diff --git a/disas/riscv.h b/disas/riscv.h
24
similarity index 100%
25
rename from include/hw/riscv/sifive_u_otp.h
26
rename to include/hw/misc/sifive_u_otp.h
27
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
28
index XXXXXXX..XXXXXXX 100644
24
index XXXXXXX..XXXXXXX 100644
29
--- a/include/hw/riscv/sifive_u.h
25
--- a/disas/riscv.h
30
+++ b/include/hw/riscv/sifive_u.h
26
+++ b/disas/riscv.h
31
@@ -XXX,XX +XXX,XX @@
27
@@ -XXX,XX +XXX,XX @@ typedef enum {
32
#include "hw/riscv/riscv_hart.h"
28
33
#include "hw/riscv/sifive_cpu.h"
29
/* structures */
34
#include "hw/riscv/sifive_gpio.h"
30
35
-#include "hw/riscv/sifive_u_otp.h"
31
+typedef struct {
36
+#include "hw/misc/sifive_u_otp.h"
32
+ const int op;
37
#include "hw/misc/sifive_u_prci.h"
33
+ const rvc_constraint *constraints;
38
34
+} rv_comp_data;
39
#define TYPE_RISCV_U_SOC "riscv.sifive.u.soc"
35
+
40
diff --git a/hw/riscv/sifive_u_otp.c b/hw/misc/sifive_u_otp.c
36
+typedef struct {
41
similarity index 99%
37
+ const char * const name;
42
rename from hw/riscv/sifive_u_otp.c
38
+ const rv_codec codec;
43
rename to hw/misc/sifive_u_otp.c
39
+ const char * const format;
40
+ const rv_comp_data *pseudo;
41
+ const short decomp_rv32;
42
+ const short decomp_rv64;
43
+ const short decomp_rv128;
44
+ const short decomp_data;
45
+} rv_opcode_data;
46
+
47
typedef struct {
48
RISCVCPUConfig *cfg;
49
uint64_t pc;
50
uint64_t inst;
51
+ const rv_opcode_data *opcode_data;
52
int32_t imm;
53
uint16_t op;
54
uint8_t codec;
55
@@ -XXX,XX +XXX,XX @@ typedef struct {
56
uint8_t rlist;
57
} rv_decode;
58
59
-typedef struct {
60
- const int op;
61
- const rvc_constraint *constraints;
62
-} rv_comp_data;
63
-
64
enum {
65
rv_op_illegal = 0
66
};
67
@@ -XXX,XX +XXX,XX @@ enum {
68
rvcd_imm_nz = 0x1
69
};
70
71
-typedef struct {
72
- const char * const name;
73
- const rv_codec codec;
74
- const char * const format;
75
- const rv_comp_data *pseudo;
76
- const short decomp_rv32;
77
- const short decomp_rv64;
78
- const short decomp_rv128;
79
- const short decomp_data;
80
-} rv_opcode_data;
81
-
82
/* instruction formats */
83
84
#define rv_fmt_none "O\t"
85
diff --git a/disas/riscv.c b/disas/riscv.c
44
index XXXXXXX..XXXXXXX 100644
86
index XXXXXXX..XXXXXXX 100644
45
--- a/hw/riscv/sifive_u_otp.c
87
--- a/disas/riscv.c
46
+++ b/hw/misc/sifive_u_otp.c
88
+++ b/disas/riscv.c
47
@@ -XXX,XX +XXX,XX @@
89
@@ -XXX,XX +XXX,XX @@ static const rv_comp_data rvcp_fsgnjx_q[] = {
48
#include "hw/sysbus.h"
90
49
#include "qemu/log.h"
91
/* instruction metadata */
50
#include "qemu/module.h"
92
51
-#include "hw/riscv/sifive_u_otp.h"
93
-const rv_opcode_data opcode_data[] = {
52
+#include "hw/misc/sifive_u_otp.h"
94
+const rv_opcode_data rvi_opcode_data[] = {
53
95
{ "illegal", rv_codec_illegal, rv_fmt_none, NULL, 0, 0, 0 },
54
static uint64_t sifive_u_otp_read(void *opaque, hwaddr addr, unsigned int size)
96
{ "lui", rv_codec_u, rv_fmt_rd_imm, NULL, 0, 0, 0 },
97
{ "auipc", rv_codec_u, rv_fmt_rd_offset, NULL, 0, 0, 0 },
98
@@ -XXX,XX +XXX,XX @@ static uint32_t operand_tbl_index(rv_inst inst)
99
100
static void decode_inst_operands(rv_decode *dec, rv_isa isa)
55
{
101
{
56
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
102
+ const rv_opcode_data *opcode_data = dec->opcode_data;
57
index XXXXXXX..XXXXXXX 100644
103
rv_inst inst = dec->inst;
58
--- a/hw/misc/Kconfig
104
dec->codec = opcode_data[dec->op].codec;
59
+++ b/hw/misc/Kconfig
105
switch (dec->codec) {
60
@@ -XXX,XX +XXX,XX @@ config AVR_POWER
106
@@ -XXX,XX +XXX,XX @@ static void append(char *s1, const char *s2, size_t n)
61
config SIFIVE_E_PRCI
107
62
bool
108
static void format_inst(char *buf, size_t buflen, size_t tab, rv_decode *dec)
63
109
{
64
+config SIFIVE_U_OTP
110
+ const rv_opcode_data *opcode_data = dec->opcode_data;
65
+ bool
111
char tmp[64];
66
+
112
const char *fmt;
67
config SIFIVE_U_PRCI
113
68
bool
114
@@ -XXX,XX +XXX,XX @@ static void format_inst(char *buf, size_t buflen, size_t tab, rv_decode *dec)
69
115
70
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
116
static void decode_inst_lift_pseudo(rv_decode *dec)
71
index XXXXXXX..XXXXXXX 100644
117
{
72
--- a/hw/misc/meson.build
118
+ const rv_opcode_data *opcode_data = dec->opcode_data;
73
+++ b/hw/misc/meson.build
119
const rv_comp_data *comp_data = opcode_data[dec->op].pseudo;
74
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_MOS6522', if_true: files('mos6522.c'))
120
if (!comp_data) {
75
121
return;
76
# RISC-V devices
122
@@ -XXX,XX +XXX,XX @@ static void decode_inst_lift_pseudo(rv_decode *dec)
77
softmmu_ss.add(when: 'CONFIG_SIFIVE_E_PRCI', if_true: files('sifive_e_prci.c'))
123
78
+softmmu_ss.add(when: 'CONFIG_SIFIVE_U_OTP', if_true: files('sifive_u_otp.c'))
124
static void decode_inst_decompress_rv32(rv_decode *dec)
79
softmmu_ss.add(when: 'CONFIG_SIFIVE_U_PRCI', if_true: files('sifive_u_prci.c'))
125
{
80
126
+ const rv_opcode_data *opcode_data = dec->opcode_data;
81
# PKUnity SoC devices
127
int decomp_op = opcode_data[dec->op].decomp_rv32;
82
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
128
if (decomp_op != rv_op_illegal) {
83
index XXXXXXX..XXXXXXX 100644
129
if ((opcode_data[dec->op].decomp_data & rvcd_imm_nz)
84
--- a/hw/riscv/Kconfig
130
@@ -XXX,XX +XXX,XX @@ static void decode_inst_decompress_rv32(rv_decode *dec)
85
+++ b/hw/riscv/Kconfig
131
86
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
132
static void decode_inst_decompress_rv64(rv_decode *dec)
87
select HART
133
{
88
select SIFIVE
134
+ const rv_opcode_data *opcode_data = dec->opcode_data;
89
select SIFIVE_PDMA
135
int decomp_op = opcode_data[dec->op].decomp_rv64;
90
+ select SIFIVE_U_OTP
136
if (decomp_op != rv_op_illegal) {
91
select SIFIVE_U_PRCI
137
if ((opcode_data[dec->op].decomp_data & rvcd_imm_nz)
92
select UNIMP
138
@@ -XXX,XX +XXX,XX @@ static void decode_inst_decompress_rv64(rv_decode *dec)
93
139
94
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
140
static void decode_inst_decompress_rv128(rv_decode *dec)
95
index XXXXXXX..XXXXXXX 100644
141
{
96
--- a/hw/riscv/meson.build
142
+ const rv_opcode_data *opcode_data = dec->opcode_data;
97
+++ b/hw/riscv/meson.build
143
int decomp_op = opcode_data[dec->op].decomp_rv128;
98
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
144
if (decomp_op != rv_op_illegal) {
99
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
145
if ((opcode_data[dec->op].decomp_data & rvcd_imm_nz)
100
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
146
@@ -XXX,XX +XXX,XX @@ disasm_inst(char *buf, size_t buflen, rv_isa isa, uint64_t pc, rv_inst inst,
101
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
147
rv_decode dec = { 0 };
102
-riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_otp.c'))
148
dec.pc = pc;
103
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('riscv_htif.c'))
149
dec.inst = inst;
104
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
150
+ dec.opcode_data = rvi_opcode_data;
105
riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c'))
151
dec.cfg = cfg;
152
decode_inst_opcode(&dec, isa);
153
decode_inst_operands(&dec, isa);
106
--
154
--
107
2.28.0
155
2.40.1
108
156
109
157
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
The name SIFIVE is too vague to convey the required component of
3
A previous patch provides a pointer to the RISCVCPUConfig data.
4
MSI_NONBROKEN. Let's drop the option, and select MSI_NONBROKEN in
4
Let's use this to add the necessary code for vendor extensions.
5
each machine instead.
5
This patch does not change the current behaviour, but clearly
6
defines how vendor extension support can be added to the disassembler.
6
7
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
8
Reviewed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-12-git-send-email-bmeng.cn@gmail.com>
10
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
11
Message-Id: <20230612111034.3955227-7-christoph.muellner@vrull.eu>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
13
---
12
hw/riscv/Kconfig | 14 +++++---------
14
disas/riscv.c | 28 ++++++++++++++++++++++++++--
13
1 file changed, 5 insertions(+), 9 deletions(-)
15
1 file changed, 26 insertions(+), 2 deletions(-)
14
16
15
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
17
diff --git a/disas/riscv.c b/disas/riscv.c
16
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
17
--- a/hw/riscv/Kconfig
19
--- a/disas/riscv.c
18
+++ b/hw/riscv/Kconfig
20
+++ b/disas/riscv.c
19
@@ -XXX,XX +XXX,XX @@
21
@@ -XXX,XX +XXX,XX @@ disasm_inst(char *buf, size_t buflen, rv_isa isa, uint64_t pc, rv_inst inst,
20
config IBEX
22
rv_decode dec = { 0 };
21
bool
23
dec.pc = pc;
22
24
dec.inst = inst;
23
-config SIFIVE
25
- dec.opcode_data = rvi_opcode_data;
24
- bool
26
dec.cfg = cfg;
25
- select MSI_NONBROKEN
27
- decode_inst_opcode(&dec, isa);
26
-
28
+
27
config SIFIVE_E
29
+ static const struct {
28
bool
30
+ bool (*guard_func)(const RISCVCPUConfig *);
29
- select SIFIVE
31
+ const rv_opcode_data *opcode_data;
30
+ select MSI_NONBROKEN
32
+ void (*decode_func)(rv_decode *, rv_isa);
31
select SIFIVE_CLINT
33
+ } decoders[] = {
32
select SIFIVE_GPIO
34
+ { always_true_p, rvi_opcode_data, decode_inst_opcode },
33
select SIFIVE_PLIC
35
+ };
34
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
36
+
35
config SIFIVE_U
37
+ for (size_t i = 0; i < ARRAY_SIZE(decoders); i++) {
36
bool
38
+ bool (*guard_func)(const RISCVCPUConfig *) = decoders[i].guard_func;
37
select CADENCE
39
+ const rv_opcode_data *opcode_data = decoders[i].opcode_data;
38
- select SIFIVE
40
+ void (*decode_func)(rv_decode *, rv_isa) = decoders[i].decode_func;
39
+ select MSI_NONBROKEN
41
+
40
select SIFIVE_CLINT
42
+ if (guard_func(cfg)) {
41
select SIFIVE_GPIO
43
+ dec.opcode_data = opcode_data;
42
select SIFIVE_PDMA
44
+ decode_func(&dec, isa);
43
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
45
+ if (dec.op != rv_op_illegal)
44
config SPIKE
46
+ break;
45
bool
47
+ }
46
select HTIF
48
+ }
47
- select SIFIVE
49
+
48
+ select MSI_NONBROKEN
50
+ if (dec.op == rv_op_illegal) {
49
select SIFIVE_CLINT
51
+ dec.opcode_data = rvi_opcode_data;
50
select SIFIVE_PLIC
52
+ }
51
53
+
52
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
54
decode_inst_operands(&dec, isa);
53
bool
55
decode_inst_decompress(&dec, isa);
54
imply PCI_DEVICES
56
decode_inst_lift_pseudo(&dec);
55
imply TEST_DEVICES
56
+ select MSI_NONBROKEN
57
select PCI
58
select SERIAL
59
select GOLDFISH_RTC
60
select VIRTIO_MMIO
61
select PCI_EXPRESS_GENERIC_BRIDGE
62
select PFLASH_CFI01
63
- select SIFIVE
64
select SIFIVE_CLINT
65
select SIFIVE_PLIC
66
select SIFIVE_TEST
67
68
config MICROCHIP_PFSOC
69
bool
70
- select SIFIVE
71
+ select MSI_NONBROKEN
72
select SIFIVE_CLINT
73
select UNIMP
74
select MCHP_PFSOC_MMUART
75
--
57
--
76
2.28.0
58
2.40.1
77
59
78
60
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
Cadence SD/SDIO/eMMC Host Controller (SD4HC) is an SDHCI compatible
3
This patch adds XVentanaCondOps support to the RISC-V disassembler.
4
controller. The SDHCI compatible registers start from offset 0x200,
5
which are called Slot Register Set (SRS) in its datasheet.
6
4
7
This creates a Cadence SDHCI model built on top of the existing
5
Co-developed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
8
generic SDHCI model. Cadence specific Host Register Set (HRS) is
9
implemented to make guest software happy.
10
11
Signed-off-by: Bin Meng <bin.meng@windriver.com>
12
Acked-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
13
Acked-by: Alistair Francis <alistair.francis@wdc.com>
6
Acked-by: Alistair Francis <alistair.francis@wdc.com>
14
Message-Id: <1598924352-89526-8-git-send-email-bmeng.cn@gmail.com>
7
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Message-Id: <20230612111034.3955227-8-christoph.muellner@vrull.eu>
15
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
16
---
11
---
17
include/hw/sd/cadence_sdhci.h | 47 +++++++++
12
disas/riscv-xventana.h | 18 ++++++++++++++++++
18
hw/sd/cadence_sdhci.c | 193 ++++++++++++++++++++++++++++++++++
13
disas/riscv-xventana.c | 41 +++++++++++++++++++++++++++++++++++++++++
19
hw/sd/Kconfig | 4 +
14
disas/riscv.c | 4 ++++
20
hw/sd/meson.build | 1 +
15
disas/meson.build | 5 ++++-
21
4 files changed, 245 insertions(+)
16
4 files changed, 67 insertions(+), 1 deletion(-)
22
create mode 100644 include/hw/sd/cadence_sdhci.h
17
create mode 100644 disas/riscv-xventana.h
23
create mode 100644 hw/sd/cadence_sdhci.c
18
create mode 100644 disas/riscv-xventana.c
24
19
25
diff --git a/include/hw/sd/cadence_sdhci.h b/include/hw/sd/cadence_sdhci.h
20
diff --git a/disas/riscv-xventana.h b/disas/riscv-xventana.h
26
new file mode 100644
21
new file mode 100644
27
index XXXXXXX..XXXXXXX
22
index XXXXXXX..XXXXXXX
28
--- /dev/null
23
--- /dev/null
29
+++ b/include/hw/sd/cadence_sdhci.h
24
+++ b/disas/riscv-xventana.h
30
@@ -XXX,XX +XXX,XX @@
25
@@ -XXX,XX +XXX,XX @@
31
+/*
26
+/*
32
+ * Cadence SDHCI emulation
27
+ * QEMU disassembler -- RISC-V specific header (xventana*).
33
+ *
28
+ *
34
+ * Copyright (c) 2020 Wind River Systems, Inc.
29
+ * Copyright (c) 2023 VRULL GmbH
35
+ *
30
+ *
36
+ * Author:
31
+ * SPDX-License-Identifier: GPL-2.0-or-later
37
+ * Bin Meng <bin.meng@windriver.com>
38
+ *
39
+ * This program is free software; you can redistribute it and/or
40
+ * modify it under the terms of the GNU General Public License as
41
+ * published by the Free Software Foundation; either version 2 or
42
+ * (at your option) version 3 of the License.
43
+ *
44
+ * This program is distributed in the hope that it will be useful,
45
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
46
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
47
+ * GNU General Public License for more details.
48
+ *
49
+ * You should have received a copy of the GNU General Public License along
50
+ * with this program; if not, see <http://www.gnu.org/licenses/>.
51
+ */
32
+ */
52
+
33
+
53
+#ifndef CADENCE_SDHCI_H
34
+#ifndef DISAS_RISCV_XVENTANA_H
54
+#define CADENCE_SDHCI_H
35
+#define DISAS_RISCV_XVENTANA_H
55
+
36
+
56
+#include "hw/sd/sdhci.h"
37
+#include "disas/riscv.h"
57
+
38
+
58
+#define CADENCE_SDHCI_REG_SIZE 0x100
39
+extern const rv_opcode_data ventana_opcode_data[];
59
+#define CADENCE_SDHCI_NUM_REGS (CADENCE_SDHCI_REG_SIZE / sizeof(uint32_t))
60
+
40
+
61
+typedef struct CadenceSDHCIState {
41
+void decode_xventanacondops(rv_decode*, rv_isa);
62
+ SysBusDevice parent;
63
+
42
+
64
+ MemoryRegion container;
43
+#endif /* DISAS_RISCV_XVENTANA_H */
65
+ MemoryRegion iomem;
44
diff --git a/disas/riscv-xventana.c b/disas/riscv-xventana.c
66
+ BusState *bus;
67
+
68
+ uint32_t regs[CADENCE_SDHCI_NUM_REGS];
69
+
70
+ SDHCIState sdhci;
71
+} CadenceSDHCIState;
72
+
73
+#define TYPE_CADENCE_SDHCI "cadence.sdhci"
74
+#define CADENCE_SDHCI(obj) OBJECT_CHECK(CadenceSDHCIState, (obj), \
75
+ TYPE_CADENCE_SDHCI)
76
+
77
+#endif /* CADENCE_SDHCI_H */
78
diff --git a/hw/sd/cadence_sdhci.c b/hw/sd/cadence_sdhci.c
79
new file mode 100644
45
new file mode 100644
80
index XXXXXXX..XXXXXXX
46
index XXXXXXX..XXXXXXX
81
--- /dev/null
47
--- /dev/null
82
+++ b/hw/sd/cadence_sdhci.c
48
+++ b/disas/riscv-xventana.c
83
@@ -XXX,XX +XXX,XX @@
49
@@ -XXX,XX +XXX,XX @@
84
+/*
50
+/*
85
+ * Cadence SDHCI emulation
51
+ * QEMU RISC-V Disassembler for xventana.
86
+ *
52
+ *
87
+ * Copyright (c) 2020 Wind River Systems, Inc.
53
+ * SPDX-License-Identifier: GPL-2.0-or-later
88
+ *
89
+ * Author:
90
+ * Bin Meng <bin.meng@windriver.com>
91
+ *
92
+ * This program is free software; you can redistribute it and/or
93
+ * modify it under the terms of the GNU General Public License as
94
+ * published by the Free Software Foundation; either version 2 or
95
+ * (at your option) version 3 of the License.
96
+ *
97
+ * This program is distributed in the hope that it will be useful,
98
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
99
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
100
+ * GNU General Public License for more details.
101
+ *
102
+ * You should have received a copy of the GNU General Public License along
103
+ * with this program; if not, see <http://www.gnu.org/licenses/>.
104
+ */
54
+ */
105
+
55
+
106
+#include "qemu/osdep.h"
56
+#include "disas/riscv.h"
107
+#include "qemu/bitops.h"
57
+#include "disas/riscv-xventana.h"
108
+#include "qemu/error-report.h"
109
+#include "qemu/log.h"
110
+#include "qapi/error.h"
111
+#include "migration/vmstate.h"
112
+#include "hw/irq.h"
113
+#include "hw/sd/cadence_sdhci.h"
114
+#include "sdhci-internal.h"
115
+
58
+
116
+/* HRS - Host Register Set (specific to Cadence) */
59
+typedef enum {
60
+ /* 0 is reserved for rv_op_illegal. */
61
+ ventana_op_vt_maskc = 1,
62
+ ventana_op_vt_maskcn = 2,
63
+} rv_ventana_op;
117
+
64
+
118
+#define CADENCE_SDHCI_HRS00 0x00 /* general information */
65
+const rv_opcode_data ventana_opcode_data[] = {
119
+#define CADENCE_SDHCI_HRS00_SWR BIT(0)
66
+ { "vt.illegal", rv_codec_illegal, rv_fmt_none, NULL, 0, 0, 0 },
120
+#define CADENCE_SDHCI_HRS00_POR_VAL 0x00010000
67
+ { "vt.maskc", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
68
+ { "vt.maskcn", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
69
+};
121
+
70
+
122
+#define CADENCE_SDHCI_HRS04 0x10 /* PHY access port */
71
+void decode_xventanacondops(rv_decode *dec, rv_isa isa)
123
+#define CADENCE_SDHCI_HRS04_WR BIT(24)
72
+{
124
+#define CADENCE_SDHCI_HRS04_RD BIT(25)
73
+ rv_inst inst = dec->inst;
125
+#define CADENCE_SDHCI_HRS04_ACK BIT(26)
74
+ rv_opcode op = rv_op_illegal;
126
+
75
+
127
+#define CADENCE_SDHCI_HRS06 0x18 /* eMMC control */
76
+ switch (((inst >> 0) & 0b11)) {
128
+#define CADENCE_SDHCI_HRS06_TUNE_UP BIT(15)
77
+ case 3:
129
+
78
+ switch (((inst >> 2) & 0b11111)) {
130
+/* SRS - Slot Register Set (SDHCI-compatible) */
79
+ case 30:
131
+
80
+ switch (((inst >> 22) & 0b1111111000) | ((inst >> 12) & 0b0000000111)) {
132
+#define CADENCE_SDHCI_SRS_BASE 0x200
81
+ case 6: op = ventana_op_vt_maskc; break;
133
+
82
+ case 7: op = ventana_op_vt_maskcn; break;
134
+#define TO_REG(addr) ((addr) / sizeof(uint32_t))
83
+ }
135
+
84
+ break;
136
+static void cadence_sdhci_instance_init(Object *obj)
137
+{
138
+ CadenceSDHCIState *s = CADENCE_SDHCI(obj);
139
+
140
+ object_initialize_child(OBJECT(s), "generic-sdhci",
141
+ &s->sdhci, TYPE_SYSBUS_SDHCI);
142
+}
143
+
144
+static void cadence_sdhci_reset(DeviceState *dev)
145
+{
146
+ CadenceSDHCIState *s = CADENCE_SDHCI(dev);
147
+
148
+ memset(s->regs, 0, CADENCE_SDHCI_REG_SIZE);
149
+ s->regs[TO_REG(CADENCE_SDHCI_HRS00)] = CADENCE_SDHCI_HRS00_POR_VAL;
150
+
151
+ device_cold_reset(DEVICE(&s->sdhci));
152
+}
153
+
154
+static uint64_t cadence_sdhci_read(void *opaque, hwaddr addr, unsigned int size)
155
+{
156
+ CadenceSDHCIState *s = opaque;
157
+ uint32_t val;
158
+
159
+ val = s->regs[TO_REG(addr)];
160
+
161
+ return (uint64_t)val;
162
+}
163
+
164
+static void cadence_sdhci_write(void *opaque, hwaddr addr, uint64_t val,
165
+ unsigned int size)
166
+{
167
+ CadenceSDHCIState *s = opaque;
168
+ uint32_t val32 = (uint32_t)val;
169
+
170
+ switch (addr) {
171
+ case CADENCE_SDHCI_HRS00:
172
+ /*
173
+ * The only writable bit is SWR (software reset) and it automatically
174
+ * clears to zero, so essentially this register remains unchanged.
175
+ */
176
+ if (val32 & CADENCE_SDHCI_HRS00_SWR) {
177
+ cadence_sdhci_reset(DEVICE(s));
178
+ }
85
+ }
179
+
180
+ break;
181
+ case CADENCE_SDHCI_HRS04:
182
+ /*
183
+ * Only emulate the ACK bit behavior when read or write transaction
184
+ * are requested.
185
+ */
186
+ if (val32 & (CADENCE_SDHCI_HRS04_WR | CADENCE_SDHCI_HRS04_RD)) {
187
+ val32 |= CADENCE_SDHCI_HRS04_ACK;
188
+ } else {
189
+ val32 &= ~CADENCE_SDHCI_HRS04_ACK;
190
+ }
191
+
192
+ s->regs[TO_REG(addr)] = val32;
193
+ break;
194
+ case CADENCE_SDHCI_HRS06:
195
+ if (val32 & CADENCE_SDHCI_HRS06_TUNE_UP) {
196
+ val32 &= ~CADENCE_SDHCI_HRS06_TUNE_UP;
197
+ }
198
+
199
+ s->regs[TO_REG(addr)] = val32;
200
+ break;
201
+ default:
202
+ s->regs[TO_REG(addr)] = val32;
203
+ break;
86
+ break;
204
+ }
87
+ }
88
+
89
+ dec->op = op;
205
+}
90
+}
91
diff --git a/disas/riscv.c b/disas/riscv.c
92
index XXXXXXX..XXXXXXX 100644
93
--- a/disas/riscv.c
94
+++ b/disas/riscv.c
95
@@ -XXX,XX +XXX,XX @@
96
#include "target/riscv/cpu_cfg.h"
97
#include "disas/riscv.h"
98
99
+/* Vendor extensions */
100
+#include "disas/riscv-xventana.h"
206
+
101
+
207
+static const MemoryRegionOps cadence_sdhci_ops = {
102
typedef enum {
208
+ .read = cadence_sdhci_read,
103
/* 0 is reserved for rv_op_illegal. */
209
+ .write = cadence_sdhci_write,
104
rv_op_lui = 1,
210
+ .endianness = DEVICE_NATIVE_ENDIAN,
105
@@ -XXX,XX +XXX,XX @@ disasm_inst(char *buf, size_t buflen, rv_isa isa, uint64_t pc, rv_inst inst,
211
+ .impl = {
106
void (*decode_func)(rv_decode *, rv_isa);
212
+ .min_access_size = 4,
107
} decoders[] = {
213
+ .max_access_size = 4,
108
{ always_true_p, rvi_opcode_data, decode_inst_opcode },
214
+ },
109
+ { has_XVentanaCondOps_p, ventana_opcode_data, decode_xventanacondops },
215
+ .valid = {
110
};
216
+ .min_access_size = 4,
111
217
+ .max_access_size = 4,
112
for (size_t i = 0; i < ARRAY_SIZE(decoders); i++) {
218
+ }
113
diff --git a/disas/meson.build b/disas/meson.build
219
+};
220
+
221
+static void cadence_sdhci_realize(DeviceState *dev, Error **errp)
222
+{
223
+ CadenceSDHCIState *s = CADENCE_SDHCI(dev);
224
+ SysBusDevice *sbd = SYS_BUS_DEVICE(dev);
225
+ SysBusDevice *sbd_sdhci = SYS_BUS_DEVICE(&s->sdhci);
226
+
227
+ memory_region_init(&s->container, OBJECT(s),
228
+ "cadence.sdhci-container", 0x1000);
229
+ sysbus_init_mmio(sbd, &s->container);
230
+
231
+ memory_region_init_io(&s->iomem, OBJECT(s), &cadence_sdhci_ops,
232
+ s, TYPE_CADENCE_SDHCI, CADENCE_SDHCI_REG_SIZE);
233
+ memory_region_add_subregion(&s->container, 0, &s->iomem);
234
+
235
+ sysbus_realize(sbd_sdhci, errp);
236
+ memory_region_add_subregion(&s->container, CADENCE_SDHCI_SRS_BASE,
237
+ sysbus_mmio_get_region(sbd_sdhci, 0));
238
+
239
+ /* propagate irq and "sd-bus" from generic-sdhci */
240
+ sysbus_pass_irq(sbd, sbd_sdhci);
241
+ s->bus = qdev_get_child_bus(DEVICE(sbd_sdhci), "sd-bus");
242
+}
243
+
244
+static const VMStateDescription vmstate_cadence_sdhci = {
245
+ .name = TYPE_CADENCE_SDHCI,
246
+ .version_id = 1,
247
+ .fields = (VMStateField[]) {
248
+ VMSTATE_UINT32_ARRAY(regs, CadenceSDHCIState, CADENCE_SDHCI_NUM_REGS),
249
+ VMSTATE_END_OF_LIST(),
250
+ },
251
+};
252
+
253
+static void cadence_sdhci_class_init(ObjectClass *classp, void *data)
254
+{
255
+ DeviceClass *dc = DEVICE_CLASS(classp);
256
+
257
+ dc->desc = "Cadence SD/SDIO/eMMC Host Controller (SD4HC)";
258
+ dc->realize = cadence_sdhci_realize;
259
+ dc->reset = cadence_sdhci_reset;
260
+ dc->vmsd = &vmstate_cadence_sdhci;
261
+}
262
+
263
+static TypeInfo cadence_sdhci_info = {
264
+ .name = TYPE_CADENCE_SDHCI,
265
+ .parent = TYPE_SYS_BUS_DEVICE,
266
+ .instance_size = sizeof(CadenceSDHCIState),
267
+ .instance_init = cadence_sdhci_instance_init,
268
+ .class_init = cadence_sdhci_class_init,
269
+};
270
+
271
+static void cadence_sdhci_register_types(void)
272
+{
273
+ type_register_static(&cadence_sdhci_info);
274
+}
275
+
276
+type_init(cadence_sdhci_register_types)
277
diff --git a/hw/sd/Kconfig b/hw/sd/Kconfig
278
index XXXXXXX..XXXXXXX 100644
114
index XXXXXXX..XXXXXXX 100644
279
--- a/hw/sd/Kconfig
115
--- a/disas/meson.build
280
+++ b/hw/sd/Kconfig
116
+++ b/disas/meson.build
281
@@ -XXX,XX +XXX,XX @@ config SDHCI_PCI
117
@@ -XXX,XX +XXX,XX @@ common_ss.add(when: 'CONFIG_M68K_DIS', if_true: files('m68k.c'))
282
default y if PCI_DEVICES
118
common_ss.add(when: 'CONFIG_MICROBLAZE_DIS', if_true: files('microblaze.c'))
283
depends on PCI
119
common_ss.add(when: 'CONFIG_MIPS_DIS', if_true: files('mips.c', 'nanomips.c'))
284
select SDHCI
120
common_ss.add(when: 'CONFIG_NIOS2_DIS', if_true: files('nios2.c'))
285
+
121
-common_ss.add(when: 'CONFIG_RISCV_DIS', if_true: files('riscv.c'))
286
+config CADENCE_SDHCI
122
+common_ss.add(when: 'CONFIG_RISCV_DIS', if_true: files(
287
+ bool
123
+ 'riscv.c',
288
+ select SDHCI
124
+ 'riscv-xventana.c'
289
diff --git a/hw/sd/meson.build b/hw/sd/meson.build
125
+))
290
index XXXXXXX..XXXXXXX 100644
126
common_ss.add(when: 'CONFIG_SH4_DIS', if_true: files('sh4.c'))
291
--- a/hw/sd/meson.build
127
common_ss.add(when: 'CONFIG_SPARC_DIS', if_true: files('sparc.c'))
292
+++ b/hw/sd/meson.build
128
common_ss.add(when: 'CONFIG_XTENSA_DIS', if_true: files('xtensa.c'))
293
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_PXA2XX', if_true: files('pxa2xx_mmci.c'))
294
softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_sdhost.c'))
295
softmmu_ss.add(when: 'CONFIG_ASPEED_SOC', if_true: files('aspeed_sdhci.c'))
296
softmmu_ss.add(when: 'CONFIG_ALLWINNER_H3', if_true: files('allwinner-sdhost.c'))
297
+softmmu_ss.add(when: 'CONFIG_CADENCE_SDHCI', if_true: files('cadence_sdhci.c'))
298
--
129
--
299
2.28.0
130
2.40.1
300
131
301
132
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
Microchip PolarFire SoC MMUART is ns16550 compatible, with some
3
Support for emulating XThead* instruction has been added recently.
4
additional registers. Create a simple MMUART model built on top
4
This patch adds support for these instructions to the RISC-V disassembler.
5
of the existing ns16550 model.
6
5
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
6
Co-developed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
Acked-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1598924352-89526-6-git-send-email-bmeng.cn@gmail.com>
8
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
9
Message-Id: <20230612111034.3955227-9-christoph.muellner@vrull.eu>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
11
---
12
include/hw/char/mchp_pfsoc_mmuart.h | 61 ++++++++++++++++++++
12
disas/riscv-xthead.h | 28 ++
13
hw/char/mchp_pfsoc_mmuart.c | 86 +++++++++++++++++++++++++++++
13
disas/riscv.h | 12 +
14
MAINTAINERS | 2 +
14
target/riscv/cpu_cfg.h | 11 +
15
hw/char/Kconfig | 3 +
15
disas/riscv-xthead.c | 707 +++++++++++++++++++++++++++++++++++++++++
16
hw/char/meson.build | 1 +
16
disas/riscv.c | 69 ++++
17
5 files changed, 153 insertions(+)
17
disas/meson.build | 1 +
18
create mode 100644 include/hw/char/mchp_pfsoc_mmuart.h
18
6 files changed, 828 insertions(+)
19
create mode 100644 hw/char/mchp_pfsoc_mmuart.c
19
create mode 100644 disas/riscv-xthead.h
20
create mode 100644 disas/riscv-xthead.c
20
21
21
diff --git a/include/hw/char/mchp_pfsoc_mmuart.h b/include/hw/char/mchp_pfsoc_mmuart.h
22
diff --git a/disas/riscv-xthead.h b/disas/riscv-xthead.h
22
new file mode 100644
23
new file mode 100644
23
index XXXXXXX..XXXXXXX
24
index XXXXXXX..XXXXXXX
24
--- /dev/null
25
--- /dev/null
25
+++ b/include/hw/char/mchp_pfsoc_mmuart.h
26
+++ b/disas/riscv-xthead.h
26
@@ -XXX,XX +XXX,XX @@
27
@@ -XXX,XX +XXX,XX @@
27
+/*
28
+/*
28
+ * Microchip PolarFire SoC MMUART emulation
29
+ * QEMU disassembler -- RISC-V specific header (xthead*).
29
+ *
30
+ *
30
+ * Copyright (c) 2020 Wind River Systems, Inc.
31
+ * Copyright (c) 2023 VRULL GmbH
31
+ *
32
+ *
32
+ * Author:
33
+ * SPDX-License-Identifier: GPL-2.0-or-later
33
+ * Bin Meng <bin.meng@windriver.com>
34
+ *
35
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
36
+ * of this software and associated documentation files (the "Software"), to deal
37
+ * in the Software without restriction, including without limitation the rights
38
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
39
+ * copies of the Software, and to permit persons to whom the Software is
40
+ * furnished to do so, subject to the following conditions:
41
+ *
42
+ * The above copyright notice and this permission notice shall be included in
43
+ * all copies or substantial portions of the Software.
44
+ *
45
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
46
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
47
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
48
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
49
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
50
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
51
+ * THE SOFTWARE.
52
+ */
34
+ */
53
+
35
+
54
+#ifndef HW_MCHP_PFSOC_MMUART_H
36
+#ifndef DISAS_RISCV_XTHEAD_H
55
+#define HW_MCHP_PFSOC_MMUART_H
37
+#define DISAS_RISCV_XTHEAD_H
56
+
38
+
57
+#include "hw/char/serial.h"
39
+#include "disas/riscv.h"
58
+
40
+
59
+#define MCHP_PFSOC_MMUART_REG_SIZE 52
41
+extern const rv_opcode_data xthead_opcode_data[];
60
+
42
+
61
+typedef struct MchpPfSoCMMUartState {
43
+void decode_xtheadba(rv_decode *, rv_isa);
62
+ MemoryRegion iomem;
44
+void decode_xtheadbb(rv_decode *, rv_isa);
63
+ hwaddr base;
45
+void decode_xtheadbs(rv_decode *, rv_isa);
64
+ qemu_irq irq;
46
+void decode_xtheadcmo(rv_decode *, rv_isa);
65
+
47
+void decode_xtheadcondmov(rv_decode *, rv_isa);
66
+ SerialMM *serial;
48
+void decode_xtheadfmemidx(rv_decode *, rv_isa);
67
+
49
+void decode_xtheadfmv(rv_decode *, rv_isa);
68
+ uint32_t reg[MCHP_PFSOC_MMUART_REG_SIZE / sizeof(uint32_t)];
50
+void decode_xtheadmac(rv_decode *, rv_isa);
69
+} MchpPfSoCMMUartState;
51
+void decode_xtheadmemidx(rv_decode *, rv_isa);
70
+
52
+void decode_xtheadmempair(rv_decode *, rv_isa);
71
+/**
53
+void decode_xtheadsync(rv_decode *, rv_isa);
72
+ * mchp_pfsoc_mmuart_create - Create a Microchip PolarFire SoC MMUART
54
+
73
+ *
55
+#endif /* DISAS_RISCV_XTHEAD_H */
74
+ * This is a helper routine for board to create a MMUART device that is
56
diff --git a/disas/riscv.h b/disas/riscv.h
75
+ * compatible with Microchip PolarFire SoC.
57
index XXXXXXX..XXXXXXX 100644
76
+ *
58
--- a/disas/riscv.h
77
+ * @sysmem: system memory region to map
59
+++ b/disas/riscv.h
78
+ * @base: base address of the MMUART registers
60
@@ -XXX,XX +XXX,XX @@ typedef enum {
79
+ * @irq: IRQ number of the MMUART device
61
rv_codec_zcmp_cm_pushpop,
80
+ * @chr: character device to associate to
62
rv_codec_zcmp_cm_mv,
81
+ *
63
rv_codec_zcmt_jt,
82
+ * @return: a pointer to the device specific control structure
64
+ rv_codec_r2_imm5,
83
+ */
65
+ rv_codec_r2,
84
+MchpPfSoCMMUartState *mchp_pfsoc_mmuart_create(MemoryRegion *sysmem,
66
+ rv_codec_r2_imm6,
85
+ hwaddr base, qemu_irq irq, Chardev *chr);
67
+ rv_codec_r_imm2,
86
+
68
+ rv_codec_r2_immhl,
87
+#endif /* HW_MCHP_PFSOC_MMUART_H */
69
+ rv_codec_r2_imm2_imm5,
88
diff --git a/hw/char/mchp_pfsoc_mmuart.c b/hw/char/mchp_pfsoc_mmuart.c
70
} rv_codec;
71
72
/* structures */
73
@@ -XXX,XX +XXX,XX @@ typedef struct {
74
uint64_t inst;
75
const rv_opcode_data *opcode_data;
76
int32_t imm;
77
+ int32_t imm1;
78
uint16_t op;
79
uint8_t codec;
80
uint8_t rd;
81
@@ -XXX,XX +XXX,XX @@ enum {
82
#define rv_fmt_push_rlist "O\tx,-i"
83
#define rv_fmt_pop_rlist "O\tx,i"
84
#define rv_fmt_zcmt_index "O\ti"
85
+#define rv_fmt_rd_rs1_rs2_imm "O\t0,1,2,i"
86
+#define rv_fmt_frd_rs1_rs2_imm "O\t3,1,2,i"
87
+#define rv_fmt_rd_rs1_immh_imml "O\t0,1,i,j"
88
+#define rv_fmt_rd_rs1_immh_imml_addr "O\t0,(1),i,j"
89
+#define rv_fmt_rd2_imm "O\t0,2,(1),i"
90
91
#endif /* DISAS_RISCV_H */
92
diff --git a/target/riscv/cpu_cfg.h b/target/riscv/cpu_cfg.h
93
index XXXXXXX..XXXXXXX 100644
94
--- a/target/riscv/cpu_cfg.h
95
+++ b/target/riscv/cpu_cfg.h
96
@@ -XXX,XX +XXX,XX @@ static inline bool has_xthead_p(const RISCVCPUConfig *cfg)
97
return cfg->ext_ ## ext ; \
98
}
99
100
+MATERIALISE_EXT_PREDICATE(xtheadba)
101
+MATERIALISE_EXT_PREDICATE(xtheadbb)
102
+MATERIALISE_EXT_PREDICATE(xtheadbs)
103
+MATERIALISE_EXT_PREDICATE(xtheadcmo)
104
+MATERIALISE_EXT_PREDICATE(xtheadcondmov)
105
+MATERIALISE_EXT_PREDICATE(xtheadfmemidx)
106
+MATERIALISE_EXT_PREDICATE(xtheadfmv)
107
+MATERIALISE_EXT_PREDICATE(xtheadmac)
108
+MATERIALISE_EXT_PREDICATE(xtheadmemidx)
109
+MATERIALISE_EXT_PREDICATE(xtheadmempair)
110
+MATERIALISE_EXT_PREDICATE(xtheadsync)
111
MATERIALISE_EXT_PREDICATE(XVentanaCondOps)
112
113
#endif
114
diff --git a/disas/riscv-xthead.c b/disas/riscv-xthead.c
89
new file mode 100644
115
new file mode 100644
90
index XXXXXXX..XXXXXXX
116
index XXXXXXX..XXXXXXX
91
--- /dev/null
117
--- /dev/null
92
+++ b/hw/char/mchp_pfsoc_mmuart.c
118
+++ b/disas/riscv-xthead.c
93
@@ -XXX,XX +XXX,XX @@
119
@@ -XXX,XX +XXX,XX @@
94
+/*
120
+/*
95
+ * Microchip PolarFire SoC MMUART emulation
121
+ * QEMU RISC-V Disassembler for xthead.
96
+ *
122
+ *
97
+ * Copyright (c) 2020 Wind River Systems, Inc.
123
+ * SPDX-License-Identifier: GPL-2.0-or-later
98
+ *
99
+ * Author:
100
+ * Bin Meng <bin.meng@windriver.com>
101
+ *
102
+ * This program is free software; you can redistribute it and/or
103
+ * modify it under the terms of the GNU General Public License as
104
+ * published by the Free Software Foundation; either version 2 or
105
+ * (at your option) version 3 of the License.
106
+ *
107
+ * This program is distributed in the hope that it will be useful,
108
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
109
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
110
+ * GNU General Public License for more details.
111
+ *
112
+ * You should have received a copy of the GNU General Public License along
113
+ * with this program; if not, see <http://www.gnu.org/licenses/>.
114
+ */
124
+ */
115
+
125
+
116
+#include "qemu/osdep.h"
126
+#include "disas/riscv.h"
117
+#include "qemu/log.h"
127
+#include "disas/riscv-xthead.h"
118
+#include "chardev/char.h"
128
+
119
+#include "exec/address-spaces.h"
129
+typedef enum {
120
+#include "hw/char/mchp_pfsoc_mmuart.h"
130
+ /* 0 is reserved for rv_op_illegal. */
121
+
131
+ /* XTheadBa */
122
+static uint64_t mchp_pfsoc_mmuart_read(void *opaque, hwaddr addr, unsigned size)
132
+ rv_op_th_addsl = 1,
123
+{
133
+ /* XTheadBb */
124
+ MchpPfSoCMMUartState *s = opaque;
134
+ rv_op_th_srri,
125
+
135
+ rv_op_th_srriw,
126
+ if (addr >= MCHP_PFSOC_MMUART_REG_SIZE) {
136
+ rv_op_th_ext,
127
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: read: addr=0x%" HWADDR_PRIx "\n",
137
+ rv_op_th_extu,
128
+ __func__, addr);
138
+ rv_op_th_ff0,
129
+ return 0;
139
+ rv_op_th_ff1,
130
+ }
140
+ rv_op_th_rev,
131
+
141
+ rv_op_th_revw,
132
+ return s->reg[addr / sizeof(uint32_t)];
142
+ rv_op_th_tstnbz,
133
+}
143
+ /* XTheadBs */
134
+
144
+ rv_op_th_tst,
135
+static void mchp_pfsoc_mmuart_write(void *opaque, hwaddr addr,
145
+ /* XTheadCmo */
136
+ uint64_t value, unsigned size)
146
+ rv_op_th_dcache_call,
137
+{
147
+ rv_op_th_dcache_ciall,
138
+ MchpPfSoCMMUartState *s = opaque;
148
+ rv_op_th_dcache_iall,
139
+ uint32_t val32 = (uint32_t)value;
149
+ rv_op_th_dcache_cpa,
140
+
150
+ rv_op_th_dcache_cipa,
141
+ if (addr >= MCHP_PFSOC_MMUART_REG_SIZE) {
151
+ rv_op_th_dcache_ipa,
142
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: bad write: addr=0x%" HWADDR_PRIx
152
+ rv_op_th_dcache_cva,
143
+ " v=0x%x\n", __func__, addr, val32);
153
+ rv_op_th_dcache_civa,
144
+ return;
154
+ rv_op_th_dcache_iva,
145
+ }
155
+ rv_op_th_dcache_csw,
146
+
156
+ rv_op_th_dcache_cisw,
147
+ s->reg[addr / sizeof(uint32_t)] = val32;
157
+ rv_op_th_dcache_isw,
148
+}
158
+ rv_op_th_dcache_cpal1,
149
+
159
+ rv_op_th_dcache_cval1,
150
+static const MemoryRegionOps mchp_pfsoc_mmuart_ops = {
160
+ rv_op_th_icache_iall,
151
+ .read = mchp_pfsoc_mmuart_read,
161
+ rv_op_th_icache_ialls,
152
+ .write = mchp_pfsoc_mmuart_write,
162
+ rv_op_th_icache_ipa,
153
+ .endianness = DEVICE_LITTLE_ENDIAN,
163
+ rv_op_th_icache_iva,
154
+ .impl = {
164
+ rv_op_th_l2cache_call,
155
+ .min_access_size = 4,
165
+ rv_op_th_l2cache_ciall,
156
+ .max_access_size = 4,
166
+ rv_op_th_l2cache_iall,
157
+ },
167
+ /* XTheadCondMov */
168
+ rv_op_th_mveqz,
169
+ rv_op_th_mvnez,
170
+ /* XTheadFMemIdx */
171
+ rv_op_th_flrd,
172
+ rv_op_th_flrw,
173
+ rv_op_th_flurd,
174
+ rv_op_th_flurw,
175
+ rv_op_th_fsrd,
176
+ rv_op_th_fsrw,
177
+ rv_op_th_fsurd,
178
+ rv_op_th_fsurw,
179
+ /* XTheadFmv */
180
+ rv_op_th_fmv_hw_x,
181
+ rv_op_th_fmv_x_hw,
182
+ /* XTheadMac */
183
+ rv_op_th_mula,
184
+ rv_op_th_mulah,
185
+ rv_op_th_mulaw,
186
+ rv_op_th_muls,
187
+ rv_op_th_mulsw,
188
+ rv_op_th_mulsh,
189
+ /* XTheadMemIdx */
190
+ rv_op_th_lbia,
191
+ rv_op_th_lbib,
192
+ rv_op_th_lbuia,
193
+ rv_op_th_lbuib,
194
+ rv_op_th_lhia,
195
+ rv_op_th_lhib,
196
+ rv_op_th_lhuia,
197
+ rv_op_th_lhuib,
198
+ rv_op_th_lwia,
199
+ rv_op_th_lwib,
200
+ rv_op_th_lwuia,
201
+ rv_op_th_lwuib,
202
+ rv_op_th_ldia,
203
+ rv_op_th_ldib,
204
+ rv_op_th_sbia,
205
+ rv_op_th_sbib,
206
+ rv_op_th_shia,
207
+ rv_op_th_shib,
208
+ rv_op_th_swia,
209
+ rv_op_th_swib,
210
+ rv_op_th_sdia,
211
+ rv_op_th_sdib,
212
+ rv_op_th_lrb,
213
+ rv_op_th_lrbu,
214
+ rv_op_th_lrh,
215
+ rv_op_th_lrhu,
216
+ rv_op_th_lrw,
217
+ rv_op_th_lrwu,
218
+ rv_op_th_lrd,
219
+ rv_op_th_srb,
220
+ rv_op_th_srh,
221
+ rv_op_th_srw,
222
+ rv_op_th_srd,
223
+ rv_op_th_lurb,
224
+ rv_op_th_lurbu,
225
+ rv_op_th_lurh,
226
+ rv_op_th_lurhu,
227
+ rv_op_th_lurw,
228
+ rv_op_th_lurwu,
229
+ rv_op_th_lurd,
230
+ rv_op_th_surb,
231
+ rv_op_th_surh,
232
+ rv_op_th_surw,
233
+ rv_op_th_surd,
234
+ /* XTheadMemPair */
235
+ rv_op_th_ldd,
236
+ rv_op_th_lwd,
237
+ rv_op_th_lwud,
238
+ rv_op_th_sdd,
239
+ rv_op_th_swd,
240
+ /* XTheadSync */
241
+ rv_op_th_sfence_vmas,
242
+ rv_op_th_sync,
243
+ rv_op_th_sync_i,
244
+ rv_op_th_sync_is,
245
+ rv_op_th_sync_s,
246
+} rv_xthead_op;
247
+
248
+const rv_opcode_data xthead_opcode_data[] = {
249
+ { "th.illegal", rv_codec_illegal, rv_fmt_none, NULL, 0, 0, 0 },
250
+ /* XTheadBa */
251
+ { "th.addsl", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
252
+ /* XTheadBb */
253
+ { "th.srri", rv_codec_r2_imm6, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
254
+ { "th.srriw", rv_codec_r2_imm5, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
255
+ { "th.ext", rv_codec_r2_immhl, rv_fmt_rd_rs1_immh_imml, NULL, 0, 0, 0 },
256
+ { "th.extu", rv_codec_r2_immhl, rv_fmt_rd_rs1_immh_imml, NULL, 0, 0, 0 },
257
+ { "th.ff0", rv_codec_r2, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
258
+ { "th.ff1", rv_codec_r2, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
259
+ { "th.rev", rv_codec_r2, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
260
+ { "th.revw", rv_codec_r2, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
261
+ { "th.tstnbz", rv_codec_r2, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
262
+ /* XTheadBs */
263
+ { "th.tst", rv_codec_r2_imm6, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
264
+ /* XTheadCmo */
265
+ { "th.dcache.call", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
266
+ { "th.dcache.ciall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
267
+ { "th.dcache.iall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
268
+ { "th.dcache.cpa", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
269
+ { "th.dcache.cipa", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
270
+ { "th.dcache.ipa", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
271
+ { "th.dcache.cva", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
272
+ { "th.dcache.civa", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
273
+ { "th.dcache.iva", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
274
+ { "th.dcache.csw", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
275
+ { "th.dcache.cisw", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
276
+ { "th.dcache.isw", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
277
+ { "th.dcache.cpal1", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
278
+ { "th.dcache.cval1", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
279
+ { "th.icache.iall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
280
+ { "th.icache.ialls", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
281
+ { "th.icache.ipa", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
282
+ { "th.icache.iva", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
283
+ { "th.l2cache.call", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
284
+ { "th.l2cache.ciall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
285
+ { "th.l2cache.iall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
286
+ /* XTheadCondMov */
287
+ { "th.mveqz", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
288
+ { "th.mvnez", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
289
+ /* XTheadFMemIdx */
290
+ { "th.flrd", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
291
+ { "th.flrw", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
292
+ { "th.flurd", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
293
+ { "th.flurw", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
294
+ { "th.fsrd", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
295
+ { "th.fsrw", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
296
+ { "th.fsurd", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
297
+ { "th.fsurw", rv_codec_r_imm2, rv_fmt_frd_rs1_rs2_imm, NULL, 0, 0, 0 },
298
+ /* XTheadFmv */
299
+ { "th.fmv.hw.x", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
300
+ { "th.fmv.x.hw", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
301
+ /* XTheadMac */
302
+ { "th.mula", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
303
+ { "th.mulaw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
304
+ { "th.mulah", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
305
+ { "th.muls", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
306
+ { "th.mulsw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
307
+ { "th.mulsh", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
308
+ /* XTheadMemIdx */
309
+ { "th.lbia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
310
+ { "th.lbib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml, NULL, 0, 0, 0 },
311
+ { "th.lbuia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
312
+ { "th.lbuib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
313
+ { "th.lhia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
314
+ { "th.lhib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
315
+ { "th.lhuia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
316
+ { "th.lhuib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
317
+ { "th.lwia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
318
+ { "th.lwib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
319
+ { "th.lwuia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
320
+ { "th.lwuib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
321
+ { "th.ldia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
322
+ { "th.ldib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
323
+ { "th.sbia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
324
+ { "th.sbib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
325
+ { "th.shia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
326
+ { "th.shib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
327
+ { "th.swia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
328
+ { "th.swib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
329
+ { "th.sdia", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
330
+ { "th.sdib", rv_codec_r2_imm2_imm5, rv_fmt_rd_rs1_immh_imml_addr, NULL, 0, 0, 0 },
331
+ { "th.lrb", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
332
+ { "th.lrbu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
333
+ { "th.lrh", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
334
+ { "th.lrhu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
335
+ { "th.lrw", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
336
+ { "th.lrwu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
337
+ { "th.lrd", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
338
+ { "th.srb", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
339
+ { "th.srh", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
340
+ { "th.srw", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
341
+ { "th.srd", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
342
+ { "th.lurb", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
343
+ { "th.lurbu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
344
+ { "th.lurh", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
345
+ { "th.lurhu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
346
+ { "th.lurw", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
347
+ { "th.lurwu", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
348
+ { "th.lurd", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
349
+ { "th.surb", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
350
+ { "th.surh", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
351
+ { "th.surw", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
352
+ { "th.surd", rv_codec_r_imm2, rv_fmt_rd_rs1_rs2_imm, NULL, 0, 0, 0 },
353
+ /* XTheadMemPair */
354
+ { "th.ldd", rv_codec_r_imm2, rv_fmt_rd2_imm, NULL, 0, 0, 0 },
355
+ { "th.lwd", rv_codec_r_imm2, rv_fmt_rd2_imm, NULL, 0, 0, 0 },
356
+ { "th.lwud", rv_codec_r_imm2, rv_fmt_rd2_imm, NULL, 0, 0, 0 },
357
+ { "th.sdd", rv_codec_r_imm2, rv_fmt_rd2_imm, NULL, 0, 0, 0 },
358
+ { "th.swd", rv_codec_r_imm2, rv_fmt_rd2_imm, NULL, 0, 0, 0 },
359
+ /* XTheadSync */
360
+ { "th.sfence.vmas", rv_codec_r, rv_fmt_rs1_rs2, NULL, 0, 0, 0 },
361
+ { "th.sync", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
362
+ { "th.sync.i", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
363
+ { "th.sync.is", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
364
+ { "th.sync.s", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
158
+};
365
+};
159
+
366
+
160
+MchpPfSoCMMUartState *mchp_pfsoc_mmuart_create(MemoryRegion *sysmem,
367
+void decode_xtheadba(rv_decode *dec, rv_isa isa)
161
+ hwaddr base, qemu_irq irq, Chardev *chr)
368
+{
162
+{
369
+ rv_inst inst = dec->inst;
163
+ MchpPfSoCMMUartState *s;
370
+ rv_opcode op = rv_op_illegal;
164
+
371
+
165
+ s = g_new0(MchpPfSoCMMUartState, 1);
372
+ switch (((inst >> 0) & 0b11)) {
166
+
373
+ case 3:
167
+ memory_region_init_io(&s->iomem, NULL, &mchp_pfsoc_mmuart_ops, s,
374
+ switch (((inst >> 2) & 0b11111)) {
168
+ "mchp.pfsoc.mmuart", 0x1000);
375
+ case 2:
169
+
376
+ /* custom-0 */
170
+ s->base = base;
377
+ switch ((inst >> 12) & 0b111) {
171
+ s->irq = irq;
378
+ case 1:
172
+
379
+ switch ((inst >> 25) & 0b1111111) {
173
+ s->serial = serial_mm_init(sysmem, base, 2, irq, 399193, chr,
380
+ case 0b0000000:
174
+ DEVICE_LITTLE_ENDIAN);
381
+ case 0b0000001:
175
+
382
+ case 0b0000010:
176
+ memory_region_add_subregion(sysmem, base + 0x20, &s->iomem);
383
+ case 0b0000011: op = rv_op_th_addsl; break;
177
+
384
+ }
178
+ return s;
385
+ break;
179
+}
386
+ }
180
diff --git a/MAINTAINERS b/MAINTAINERS
387
+ break;
388
+ /* custom-0 */
389
+ }
390
+ break;
391
+ }
392
+
393
+ dec->op = op;
394
+}
395
+
396
+void decode_xtheadbb(rv_decode *dec, rv_isa isa)
397
+{
398
+ rv_inst inst = dec->inst;
399
+ rv_opcode op = rv_op_illegal;
400
+
401
+ switch (((inst >> 0) & 0b11)) {
402
+ case 3:
403
+ switch (((inst >> 2) & 0b11111)) {
404
+ case 2:
405
+ /* custom-0 */
406
+ switch ((inst >> 12) & 0b111) {
407
+ case 1:
408
+ switch ((inst >> 25) & 0b1111111) {
409
+ case 0b0001010: op = rv_op_th_srriw; break;
410
+ case 0b1000000:
411
+ if (((inst >> 20) & 0b11111) == 0) {
412
+ op = rv_op_th_tstnbz;
413
+ }
414
+ break;
415
+ case 0b1000001:
416
+ if (((inst >> 20) & 0b11111) == 0) {
417
+ op = rv_op_th_rev;
418
+ }
419
+ break;
420
+ case 0b1000010:
421
+ if (((inst >> 20) & 0b11111) == 0) {
422
+ op = rv_op_th_ff0;
423
+ }
424
+ break;
425
+ case 0b1000011:
426
+ if (((inst >> 20) & 0b11111) == 0) {
427
+ op = rv_op_th_ff1;
428
+ }
429
+ break;
430
+ case 0b1000100:
431
+ case 0b1001000:
432
+ if (((inst >> 20) & 0b11111) == 0) {
433
+ op = rv_op_th_revw;
434
+ }
435
+ break;
436
+ case 0b0000100:
437
+ case 0b0000101: op = rv_op_th_srri; break;
438
+ }
439
+ break;
440
+ case 2: op = rv_op_th_ext; break;
441
+ case 3: op = rv_op_th_extu; break;
442
+ }
443
+ break;
444
+ /* custom-0 */
445
+ }
446
+ break;
447
+ }
448
+
449
+ dec->op = op;
450
+}
451
+
452
+void decode_xtheadbs(rv_decode *dec, rv_isa isa)
453
+{
454
+ rv_inst inst = dec->inst;
455
+ rv_opcode op = rv_op_illegal;
456
+
457
+ switch (((inst >> 0) & 0b11)) {
458
+ case 3:
459
+ switch (((inst >> 2) & 0b11111)) {
460
+ case 2:
461
+ /* custom-0 */
462
+ switch ((inst >> 12) & 0b111) {
463
+ case 1:
464
+ switch ((inst >> 26) & 0b111111) {
465
+ case 0b100010: op = rv_op_th_tst; break;
466
+ }
467
+ break;
468
+ }
469
+ break;
470
+ /* custom-0 */
471
+ }
472
+ break;
473
+ }
474
+
475
+ dec->op = op;
476
+}
477
+
478
+void decode_xtheadcmo(rv_decode *dec, rv_isa isa)
479
+{
480
+ rv_inst inst = dec->inst;
481
+ rv_opcode op = rv_op_illegal;
482
+
483
+ switch (((inst >> 0) & 0b11)) {
484
+ case 3:
485
+ switch (((inst >> 2) & 0b11111)) {
486
+ case 2:
487
+ /* custom-0 */
488
+ switch ((inst >> 12) & 0b111) {
489
+ case 0:
490
+ switch ((inst >> 20 & 0b111111111111)) {
491
+ case 0b000000000001:
492
+ if (((inst >> 20) & 0b11111) == 0) {
493
+ op = rv_op_th_dcache_call;
494
+ }
495
+ break;
496
+ case 0b000000000011:
497
+ if (((inst >> 20) & 0b11111) == 0) {
498
+ op = rv_op_th_dcache_ciall;
499
+ }
500
+ break;
501
+ case 0b000000000010:
502
+ if (((inst >> 20) & 0b11111) == 0) {
503
+ op = rv_op_th_dcache_iall;
504
+ }
505
+ break;
506
+ case 0b000000101001: op = rv_op_th_dcache_cpa; break;
507
+ case 0b000000101011: op = rv_op_th_dcache_cipa; break;
508
+ case 0b000000101010: op = rv_op_th_dcache_ipa; break;
509
+ case 0b000000100101: op = rv_op_th_dcache_cva; break;
510
+ case 0b000000100111: op = rv_op_th_dcache_civa; break;
511
+ case 0b000000100110: op = rv_op_th_dcache_iva; break;
512
+ case 0b000000100001: op = rv_op_th_dcache_csw; break;
513
+ case 0b000000100011: op = rv_op_th_dcache_cisw; break;
514
+ case 0b000000100010: op = rv_op_th_dcache_isw; break;
515
+ case 0b000000101000: op = rv_op_th_dcache_cpal1; break;
516
+ case 0b000000100100: op = rv_op_th_dcache_cval1; break;
517
+ case 0b000000010000:
518
+ if (((inst >> 20) & 0b11111) == 0) {
519
+ op = rv_op_th_icache_iall;
520
+ }
521
+ break;
522
+ case 0b000000010001:
523
+ if (((inst >> 20) & 0b11111) == 0) {
524
+ op = rv_op_th_icache_ialls;
525
+ }
526
+ break;
527
+ case 0b000000111000: op = rv_op_th_icache_ipa; break;
528
+ case 0b000000110000: op = rv_op_th_icache_iva; break;
529
+ case 0b000000010101:
530
+ if (((inst >> 20) & 0b11111) == 0) {
531
+ op = rv_op_th_l2cache_call;
532
+ }
533
+ break;
534
+ case 0b000000010111:
535
+ if (((inst >> 20) & 0b11111) == 0) {
536
+ op = rv_op_th_l2cache_ciall;
537
+ }
538
+ break;
539
+ case 0b000000010110:
540
+ if (((inst >> 20) & 0b11111) == 0) {
541
+ op = rv_op_th_l2cache_iall;
542
+ }
543
+ break;
544
+ }
545
+ break;
546
+ }
547
+ break;
548
+ /* custom-0 */
549
+ }
550
+ break;
551
+ }
552
+
553
+ dec->op = op;
554
+}
555
+
556
+void decode_xtheadcondmov(rv_decode *dec, rv_isa isa)
557
+{
558
+ rv_inst inst = dec->inst;
559
+ rv_opcode op = rv_op_illegal;
560
+
561
+ switch (((inst >> 0) & 0b11)) {
562
+ case 3:
563
+ switch (((inst >> 2) & 0b11111)) {
564
+ case 2:
565
+ /* custom-0 */
566
+ switch ((inst >> 12) & 0b111) {
567
+ case 1:
568
+ switch ((inst >> 25) & 0b1111111) {
569
+ case 0b0100000: op = rv_op_th_mveqz; break;
570
+ case 0b0100001: op = rv_op_th_mvnez; break;
571
+ }
572
+ break;
573
+ }
574
+ break;
575
+ /* custom-0 */
576
+ }
577
+ break;
578
+ }
579
+
580
+ dec->op = op;
581
+}
582
+
583
+void decode_xtheadfmemidx(rv_decode *dec, rv_isa isa)
584
+{
585
+ rv_inst inst = dec->inst;
586
+ rv_opcode op = rv_op_illegal;
587
+
588
+ switch (((inst >> 0) & 0b11)) {
589
+ case 3:
590
+ switch (((inst >> 2) & 0b11111)) {
591
+ case 2:
592
+ /* custom-0 */
593
+ switch ((inst >> 12) & 0b111) {
594
+ case 6:
595
+ switch ((inst >> 27) & 0b11111) {
596
+ case 8: op = rv_op_th_flrw; break;
597
+ case 10: op = rv_op_th_flurw; break;
598
+ case 12: op = rv_op_th_flrd; break;
599
+ case 14: op = rv_op_th_flurd; break;
600
+ }
601
+ break;
602
+ case 7:
603
+ switch ((inst >> 27) & 0b11111) {
604
+ case 8: op = rv_op_th_fsrw; break;
605
+ case 10: op = rv_op_th_fsurw; break;
606
+ case 12: op = rv_op_th_fsrd; break;
607
+ case 14: op = rv_op_th_fsurd; break;
608
+ }
609
+ break;
610
+ }
611
+ break;
612
+ /* custom-0 */
613
+ }
614
+ break;
615
+ }
616
+
617
+ dec->op = op;
618
+}
619
+
620
+void decode_xtheadfmv(rv_decode *dec, rv_isa isa)
621
+{
622
+ rv_inst inst = dec->inst;
623
+ rv_opcode op = rv_op_illegal;
624
+
625
+ switch (((inst >> 0) & 0b11)) {
626
+ case 3:
627
+ switch (((inst >> 2) & 0b11111)) {
628
+ case 2:
629
+ /* custom-0 */
630
+ switch ((inst >> 12) & 0b111) {
631
+ case 1:
632
+ switch ((inst >> 25) & 0b1111111) {
633
+ case 0b1010000:
634
+ if (((inst >> 20) & 0b11111) == 0) {
635
+ op = rv_op_th_fmv_hw_x;
636
+ }
637
+ break;
638
+ case 0b1100000:
639
+ if (((inst >> 20) & 0b11111) == 0) {
640
+ op = rv_op_th_fmv_x_hw;
641
+ }
642
+ break;
643
+ }
644
+ break;
645
+ }
646
+ break;
647
+ /* custom-0 */
648
+ }
649
+ break;
650
+ }
651
+
652
+ dec->op = op;
653
+}
654
+
655
+void decode_xtheadmac(rv_decode *dec, rv_isa isa)
656
+{
657
+ rv_inst inst = dec->inst;
658
+ rv_opcode op = rv_op_illegal;
659
+
660
+ switch (((inst >> 0) & 0b11)) {
661
+ case 3:
662
+ switch (((inst >> 2) & 0b11111)) {
663
+ case 2:
664
+ /* custom-0 */
665
+ switch ((inst >> 12) & 0b111) {
666
+ case 1:
667
+ switch ((inst >> 25) & 0b1111111) {
668
+ case 0b0010000: op = rv_op_th_mula; break;
669
+ case 0b0010001: op = rv_op_th_muls; break;
670
+ case 0b0010010: op = rv_op_th_mulaw; break;
671
+ case 0b0010011: op = rv_op_th_mulsw; break;
672
+ case 0b0010100: op = rv_op_th_mulah; break;
673
+ case 0b0010101: op = rv_op_th_mulsh; break;
674
+ }
675
+ break;
676
+ }
677
+ break;
678
+ /* custom-0 */
679
+ }
680
+ break;
681
+ }
682
+
683
+ dec->op = op;
684
+}
685
+
686
+void decode_xtheadmemidx(rv_decode *dec, rv_isa isa)
687
+{
688
+ rv_inst inst = dec->inst;
689
+ rv_opcode op = rv_op_illegal;
690
+
691
+ switch (((inst >> 0) & 0b11)) {
692
+ case 3:
693
+ switch (((inst >> 2) & 0b11111)) {
694
+ case 2:
695
+ /* custom-0 */
696
+ switch ((inst >> 12) & 0b111) {
697
+ case 4:
698
+ switch ((inst >> 27) & 0b11111) {
699
+ case 0: op = rv_op_th_lrb; break;
700
+ case 1: op = rv_op_th_lbib; break;
701
+ case 2: op = rv_op_th_lurb; break;
702
+ case 3: op = rv_op_th_lbia; break;
703
+ case 4: op = rv_op_th_lrh; break;
704
+ case 5: op = rv_op_th_lhib; break;
705
+ case 6: op = rv_op_th_lurh; break;
706
+ case 7: op = rv_op_th_lhia; break;
707
+ case 8: op = rv_op_th_lrw; break;
708
+ case 9: op = rv_op_th_lwib; break;
709
+ case 10: op = rv_op_th_lurw; break;
710
+ case 11: op = rv_op_th_lwia; break;
711
+ case 12: op = rv_op_th_lrd; break;
712
+ case 13: op = rv_op_th_ldib; break;
713
+ case 14: op = rv_op_th_lurd; break;
714
+ case 15: op = rv_op_th_ldia; break;
715
+ case 16: op = rv_op_th_lrbu; break;
716
+ case 17: op = rv_op_th_lbuib; break;
717
+ case 18: op = rv_op_th_lurbu; break;
718
+ case 19: op = rv_op_th_lbuia; break;
719
+ case 20: op = rv_op_th_lrhu; break;
720
+ case 21: op = rv_op_th_lhuib; break;
721
+ case 22: op = rv_op_th_lurhu; break;
722
+ case 23: op = rv_op_th_lhuia; break;
723
+ case 24: op = rv_op_th_lrwu; break;
724
+ case 25: op = rv_op_th_lwuib; break;
725
+ case 26: op = rv_op_th_lurwu; break;
726
+ case 27: op = rv_op_th_lwuia; break;
727
+ }
728
+ break;
729
+ case 5:
730
+ switch ((inst >> 27) & 0b11111) {
731
+ case 0: op = rv_op_th_srb; break;
732
+ case 1: op = rv_op_th_sbib; break;
733
+ case 2: op = rv_op_th_surb; break;
734
+ case 3: op = rv_op_th_sbia; break;
735
+ case 4: op = rv_op_th_srh; break;
736
+ case 5: op = rv_op_th_shib; break;
737
+ case 6: op = rv_op_th_surh; break;
738
+ case 7: op = rv_op_th_shia; break;
739
+ case 8: op = rv_op_th_srw; break;
740
+ case 9: op = rv_op_th_swib; break;
741
+ case 10: op = rv_op_th_surw; break;
742
+ case 11: op = rv_op_th_swia; break;
743
+ case 12: op = rv_op_th_srd; break;
744
+ case 13: op = rv_op_th_sdib; break;
745
+ case 14: op = rv_op_th_surd; break;
746
+ case 15: op = rv_op_th_sdia; break;
747
+ }
748
+ break;
749
+ break;
750
+ }
751
+ break;
752
+ /* custom-0 */
753
+ }
754
+ break;
755
+ }
756
+
757
+ dec->op = op;
758
+}
759
+
760
+void decode_xtheadmempair(rv_decode *dec, rv_isa isa)
761
+{
762
+ rv_inst inst = dec->inst;
763
+ rv_opcode op = rv_op_illegal;
764
+
765
+ switch (((inst >> 0) & 0b11)) {
766
+ case 3:
767
+ switch (((inst >> 2) & 0b11111)) {
768
+ case 2:
769
+ /* custom-0 */
770
+ switch ((inst >> 12) & 0b111) {
771
+ case 4:
772
+ switch ((inst >> 27) & 0b11111) {
773
+ case 28: op = rv_op_th_lwd; break;
774
+ case 30: op = rv_op_th_lwud; break;
775
+ case 31: op = rv_op_th_ldd; break;
776
+ }
777
+ break;
778
+ case 5:
779
+ switch ((inst >> 27) & 0b11111) {
780
+ case 28: op = rv_op_th_swd; break;
781
+ case 31: op = rv_op_th_sdd; break;
782
+ }
783
+ break;
784
+ }
785
+ break;
786
+ /* custom-0 */
787
+ }
788
+ break;
789
+ }
790
+
791
+ dec->op = op;
792
+}
793
+
794
+void decode_xtheadsync(rv_decode *dec, rv_isa isa)
795
+{
796
+ rv_inst inst = dec->inst;
797
+ rv_opcode op = rv_op_illegal;
798
+
799
+ switch (((inst >> 0) & 0b11)) {
800
+ case 3:
801
+ switch (((inst >> 2) & 0b11111)) {
802
+ case 2:
803
+ /* custom-0 */
804
+ switch ((inst >> 12) & 0b111) {
805
+ case 0:
806
+ switch ((inst >> 25) & 0b1111111) {
807
+ case 0b0000010: op = rv_op_th_sfence_vmas; break;
808
+ case 0b0000000:
809
+ switch ((inst >> 20) & 0b11111) {
810
+ case 0b11000: op = rv_op_th_sync; break;
811
+ case 0b11010: op = rv_op_th_sync_i; break;
812
+ case 0b11011: op = rv_op_th_sync_is; break;
813
+ case 0b11001: op = rv_op_th_sync_s; break;
814
+ }
815
+ break;
816
+ }
817
+ break;
818
+ }
819
+ break;
820
+ /* custom-0 */
821
+ }
822
+ break;
823
+ }
824
+
825
+ dec->op = op;
826
+}
827
diff --git a/disas/riscv.c b/disas/riscv.c
181
index XXXXXXX..XXXXXXX 100644
828
index XXXXXXX..XXXXXXX 100644
182
--- a/MAINTAINERS
829
--- a/disas/riscv.c
183
+++ b/MAINTAINERS
830
+++ b/disas/riscv.c
184
@@ -XXX,XX +XXX,XX @@ M: Bin Meng <bin.meng@windriver.com>
831
@@ -XXX,XX +XXX,XX @@
185
L: qemu-riscv@nongnu.org
832
*/
186
S: Supported
833
187
F: hw/riscv/microchip_pfsoc.c
834
#include "qemu/osdep.h"
188
+F: hw/char/mchp_pfsoc_mmuart.c
835
+#include "qemu/bitops.h"
189
F: include/hw/riscv/microchip_pfsoc.h
836
#include "disas/dis-asm.h"
190
+F: include/hw/char/mchp_pfsoc_mmuart.h
837
#include "target/riscv/cpu_cfg.h"
191
838
#include "disas/riscv.h"
192
RX Machines
839
193
-----------
840
/* Vendor extensions */
194
diff --git a/hw/char/Kconfig b/hw/char/Kconfig
841
+#include "disas/riscv-xthead.h"
842
#include "disas/riscv-xventana.h"
843
844
typedef enum {
845
@@ -XXX,XX +XXX,XX @@ static uint32_t operand_zcmp_rlist(rv_inst inst)
846
return ((inst << 56) >> 60);
847
}
848
849
+static uint32_t operand_imm6(rv_inst inst)
850
+{
851
+ return (inst << 38) >> 60;
852
+}
853
+
854
+static uint32_t operand_imm2(rv_inst inst)
855
+{
856
+ return (inst << 37) >> 62;
857
+}
858
+
859
+static uint32_t operand_immh(rv_inst inst)
860
+{
861
+ return (inst << 32) >> 58;
862
+}
863
+
864
+static uint32_t operand_imml(rv_inst inst)
865
+{
866
+ return (inst << 38) >> 58;
867
+}
868
+
869
static uint32_t calculate_stack_adj(rv_isa isa, uint32_t rlist, uint32_t spimm)
870
{
871
int xlen_bytes_log2 = isa == rv64 ? 3 : 2;
872
@@ -XXX,XX +XXX,XX @@ static void decode_inst_operands(rv_decode *dec, rv_isa isa)
873
case rv_codec_zcmt_jt:
874
dec->imm = operand_tbl_index(inst);
875
break;
876
+ case rv_codec_r2_imm5:
877
+ dec->rd = operand_rd(inst);
878
+ dec->rs1 = operand_rs1(inst);
879
+ dec->imm = operand_rs2(inst);
880
+ break;
881
+ case rv_codec_r2:
882
+ dec->rd = operand_rd(inst);
883
+ dec->rs1 = operand_rs1(inst);
884
+ break;
885
+ case rv_codec_r2_imm6:
886
+ dec->rd = operand_rd(inst);
887
+ dec->rs1 = operand_rs1(inst);
888
+ dec->imm = operand_imm6(inst);
889
+ break;
890
+ case rv_codec_r_imm2:
891
+ dec->rd = operand_rd(inst);
892
+ dec->rs1 = operand_rs1(inst);
893
+ dec->rs2 = operand_rs2(inst);
894
+ dec->imm = operand_imm2(inst);
895
+ break;
896
+ case rv_codec_r2_immhl:
897
+ dec->rd = operand_rd(inst);
898
+ dec->rs1 = operand_rs1(inst);
899
+ dec->imm = operand_immh(inst);
900
+ dec->imm1 = operand_imml(inst);
901
+ break;
902
+ case rv_codec_r2_imm2_imm5:
903
+ dec->rd = operand_rd(inst);
904
+ dec->rs1 = operand_rs1(inst);
905
+ dec->imm = sextract32(operand_rs2(inst), 0, 5);
906
+ dec->imm1 = operand_imm2(inst);
907
+ break;
908
};
909
}
910
911
@@ -XXX,XX +XXX,XX @@ static void format_inst(char *buf, size_t buflen, size_t tab, rv_decode *dec)
912
snprintf(tmp, sizeof(tmp), "%u", ((uint32_t)dec->imm & 0b11111));
913
append(buf, tmp, buflen);
914
break;
915
+ case 'j':
916
+ snprintf(tmp, sizeof(tmp), "%d", dec->imm1);
917
+ append(buf, tmp, buflen);
918
+ break;
919
case 'o':
920
snprintf(tmp, sizeof(tmp), "%d", dec->imm);
921
append(buf, tmp, buflen);
922
@@ -XXX,XX +XXX,XX @@ disasm_inst(char *buf, size_t buflen, rv_isa isa, uint64_t pc, rv_inst inst,
923
void (*decode_func)(rv_decode *, rv_isa);
924
} decoders[] = {
925
{ always_true_p, rvi_opcode_data, decode_inst_opcode },
926
+ { has_xtheadba_p, xthead_opcode_data, decode_xtheadba },
927
+ { has_xtheadbb_p, xthead_opcode_data, decode_xtheadbb },
928
+ { has_xtheadbs_p, xthead_opcode_data, decode_xtheadbs },
929
+ { has_xtheadcmo_p, xthead_opcode_data, decode_xtheadcmo },
930
+ { has_xtheadcondmov_p, xthead_opcode_data, decode_xtheadcondmov },
931
+ { has_xtheadfmemidx_p, xthead_opcode_data, decode_xtheadfmemidx },
932
+ { has_xtheadfmv_p, xthead_opcode_data, decode_xtheadfmv },
933
+ { has_xtheadmac_p, xthead_opcode_data, decode_xtheadmac },
934
+ { has_xtheadmemidx_p, xthead_opcode_data, decode_xtheadmemidx },
935
+ { has_xtheadmempair_p, xthead_opcode_data, decode_xtheadmempair },
936
+ { has_xtheadsync_p, xthead_opcode_data, decode_xtheadsync },
937
{ has_XVentanaCondOps_p, ventana_opcode_data, decode_xventanacondops },
938
};
939
940
diff --git a/disas/meson.build b/disas/meson.build
195
index XXXXXXX..XXXXXXX 100644
941
index XXXXXXX..XXXXXXX 100644
196
--- a/hw/char/Kconfig
942
--- a/disas/meson.build
197
+++ b/hw/char/Kconfig
943
+++ b/disas/meson.build
198
@@ -XXX,XX +XXX,XX @@ config RENESAS_SCI
944
@@ -XXX,XX +XXX,XX @@ common_ss.add(when: 'CONFIG_MIPS_DIS', if_true: files('mips.c', 'nanomips.c'))
199
945
common_ss.add(when: 'CONFIG_NIOS2_DIS', if_true: files('nios2.c'))
200
config AVR_USART
946
common_ss.add(when: 'CONFIG_RISCV_DIS', if_true: files(
201
bool
947
'riscv.c',
202
+
948
+ 'riscv-xthead.c',
203
+config MCHP_PFSOC_MMUART
949
'riscv-xventana.c'
204
+ bool
950
))
205
diff --git a/hw/char/meson.build b/hw/char/meson.build
951
common_ss.add(when: 'CONFIG_SH4_DIS', if_true: files('sh4.c'))
206
index XXXXXXX..XXXXXXX 100644
207
--- a/hw/char/meson.build
208
+++ b/hw/char/meson.build
209
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_aux.c'))
210
softmmu_ss.add(when: 'CONFIG_RENESAS_SCI', if_true: files('renesas_sci.c'))
211
softmmu_ss.add(when: 'CONFIG_SH4', if_true: files('sh_serial.c'))
212
softmmu_ss.add(when: 'CONFIG_STM32F2XX_USART', if_true: files('stm32f2xx_usart.c'))
213
+softmmu_ss.add(when: 'CONFIG_MCHP_PFSOC_MMUART', if_true: files('mchp_pfsoc_mmuart.c'))
214
215
specific_ss.add(when: 'CONFIG_TERMINAL3270', if_true: files('terminal3270.c'))
216
specific_ss.add(when: 'CONFIG_VIRTIO', if_true: files('virtio-serial-bus.c'))
217
--
952
--
218
2.28.0
953
2.40.1
219
954
220
955
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Upon MRET or explicit memory access with MPRV=1, MPV should be ignored
4
when MPP=PRV_M.
5
6
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
7
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Message-Id: <20230603134236.15719-2-liweiwei@iscas.ac.cn>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
---
13
target/riscv/cpu_helper.c | 3 ++-
14
target/riscv/op_helper.c | 3 ++-
15
2 files changed, 4 insertions(+), 2 deletions(-)
16
17
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
18
index XXXXXXX..XXXXXXX 100644
19
--- a/target/riscv/cpu_helper.c
20
+++ b/target/riscv/cpu_helper.c
21
@@ -XXX,XX +XXX,XX @@ int riscv_cpu_mmu_index(CPURISCVState *env, bool ifetch)
22
23
if (mode == PRV_M && get_field(status, MSTATUS_MPRV)) {
24
mode = get_field(env->mstatus, MSTATUS_MPP);
25
- virt = get_field(env->mstatus, MSTATUS_MPV);
26
+ virt = get_field(env->mstatus, MSTATUS_MPV) &&
27
+ (mode != PRV_M);
28
if (virt) {
29
status = env->vsstatus;
30
}
31
diff --git a/target/riscv/op_helper.c b/target/riscv/op_helper.c
32
index XXXXXXX..XXXXXXX 100644
33
--- a/target/riscv/op_helper.c
34
+++ b/target/riscv/op_helper.c
35
@@ -XXX,XX +XXX,XX @@ target_ulong helper_mret(CPURISCVState *env)
36
riscv_raise_exception(env, RISCV_EXCP_INST_ACCESS_FAULT, GETPC());
37
}
38
39
- target_ulong prev_virt = get_field(env->mstatus, MSTATUS_MPV);
40
+ target_ulong prev_virt = get_field(env->mstatus, MSTATUS_MPV) &&
41
+ (prev_priv != PRV_M);
42
mstatus = set_field(mstatus, MSTATUS_MIE,
43
get_field(mstatus, MSTATUS_MPIE));
44
mstatus = set_field(mstatus, MSTATUS_MPIE, 1);
45
--
46
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
MPV and GVA bits are added by hypervisor extension to mstatus
4
and mstatush (if MXLEN=32).
5
6
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
7
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Message-Id: <20230603134236.15719-3-liweiwei@iscas.ac.cn>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
---
13
target/riscv/csr.c | 10 ++++------
14
1 file changed, 4 insertions(+), 6 deletions(-)
15
16
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
17
index XXXXXXX..XXXXXXX 100644
18
--- a/target/riscv/csr.c
19
+++ b/target/riscv/csr.c
20
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
21
}
22
23
if (xl != MXL_RV32 || env->debugger) {
24
- /*
25
- * RV32: MPV and GVA are not in mstatus. The current plan is to
26
- * add them to mstatush. For now, we just don't support it.
27
- */
28
- mask |= MSTATUS_MPV | MSTATUS_GVA;
29
+ if (riscv_has_ext(env, RVH)) {
30
+ mask |= MSTATUS_MPV | MSTATUS_GVA;
31
+ }
32
if ((val & MSTATUS64_UXL) != 0) {
33
mask |= MSTATUS64_UXL;
34
}
35
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mstatush(CPURISCVState *env, int csrno,
36
target_ulong val)
37
{
38
uint64_t valh = (uint64_t)val << 32;
39
- uint64_t mask = MSTATUS_MPV | MSTATUS_GVA;
40
+ uint64_t mask = riscv_has_ext(env, RVH) ? MSTATUS_MPV | MSTATUS_GVA : 0;
41
42
env->mstatus = (env->mstatus & ~mask) | (valh & mask);
43
44
--
45
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
SXL is initialized as env->misa_mxl which is also the mxl value.
4
So we can just remain it unchanged to keep it read-only.
5
6
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
7
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Message-Id: <20230603134236.15719-4-liweiwei@iscas.ac.cn>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
---
13
target/riscv/csr.c | 4 ----
14
1 file changed, 4 deletions(-)
15
16
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
17
index XXXXXXX..XXXXXXX 100644
18
--- a/target/riscv/csr.c
19
+++ b/target/riscv/csr.c
20
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
21
22
mstatus = (mstatus & ~mask) | (val & mask);
23
24
- if (xl > MXL_RV32) {
25
- /* SXL field is for now read only */
26
- mstatus = set_field(mstatus, MSTATUS64_SXL, xl);
27
- }
28
env->mstatus = mstatus;
29
30
/*
31
--
32
2.40.1
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
Commit 7f0bdfb5bfc2 ("target/riscv/cpu.c: remove cfg setup from
4
riscv_cpu_init()") removed code that was enabling mmu, pmp, ext_ifencei
5
and ext_icsr from riscv_cpu_init(), the init() function of
6
TYPE_RISCV_CPU, parent type of all RISC-V CPUss. This was done to force
7
CPUs to explictly enable all extensions and features it requires,
8
without any 'magic values' that were inherited by the parent type.
9
10
This commit failed to make appropriate changes in the 'veyron-v1' CPU,
11
added earlier by commit e1d084a8524a. The result is that the veyron-v1
12
CPU has ext_ifencei, ext_icsr and pmp set to 'false', which is not the
13
case.
14
15
The reason why it took this long to notice (thanks LIU Zhiwei for
16
reporting it) is because Linux doesn't mind 'ifencei' and 'icsr' being
17
absent in the 'riscv,isa' DT, implying that they're both present if the
18
'i' extension is enabled. OpenSBI also doesn't error out or warns about
19
the lack of 'pmp', it'll just not protect memory pages.
20
21
Fix it by setting them to 'true' in rv64_veyron_v1_cpu_init() like
22
7f0bdfb5bfc2 already did with other CPUs.
23
24
Reported-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
25
Fixes: 7f0bdfb5bfc2 ("target/riscv/cpu.c: remove cfg setup from riscv_cpu_init()")
26
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
27
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
28
Reviewed-by: LIU Zhiwei <zhiwei_liu@linux.alibaba.com>
29
Message-Id: <20230620152443.137079-1-dbarboza@ventanamicro.com>
30
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
31
---
32
target/riscv/cpu.c | 3 +++
33
1 file changed, 3 insertions(+)
34
35
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
36
index XXXXXXX..XXXXXXX 100644
37
--- a/target/riscv/cpu.c
38
+++ b/target/riscv/cpu.c
39
@@ -XXX,XX +XXX,XX @@ static void rv64_veyron_v1_cpu_init(Object *obj)
40
41
/* Enable ISA extensions */
42
cpu->cfg.mmu = true;
43
+ cpu->cfg.ext_ifencei = true;
44
+ cpu->cfg.ext_icsr = true;
45
+ cpu->cfg.pmp = true;
46
cpu->cfg.ext_icbom = true;
47
cpu->cfg.cbom_blocksize = 64;
48
cpu->cfg.cboz_blocksize = 64;
49
--
50
2.40.1
diff view generated by jsdifflib
1
From: Yifei Jiang <jiangyifei@huawei.com>
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
2
2
3
When the cause number is equal to or greater than 23, print "(unknown)" in
3
As specified in privilege spec:"When MPRV=1, load and store memory
4
trace_riscv_trap. The max valid number of riscv_excp_names is 23, so the last
4
addresses are treated as though the current XLEN were set to MPP’s
5
excpetion "guest_store_page_fault" can not be printed.
5
XLEN". So the xlen for address may be different from current xlen.
6
6
7
In addition, the current check of cause is invalid for riscv_intr_names. So
7
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
8
introduce riscv_cpu_get_trap_name to get the trap cause name.
8
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
9
9
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
10
Signed-off-by: Yifei Jiang <jiangyifei@huawei.com>
10
Message-Id: <20230614032547.35895-2-liweiwei@iscas.ac.cn>
11
Signed-off-by: Yipeng Yin <yinyipeng1@huawei.com>
12
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
13
Message-Id: <20200814035819.1214-1-jiangyifei@huawei.com>
14
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
15
---
12
---
16
target/riscv/cpu.h | 1 +
13
target/riscv/cpu.h | 49 +++++++++++++++++++++++++++++++++------
17
target/riscv/cpu.c | 11 +++++++++++
14
target/riscv/cpu_helper.c | 1 +
18
target/riscv/cpu_helper.c | 4 ++--
15
target/riscv/translate.c | 13 ++++++++++-
19
3 files changed, 14 insertions(+), 2 deletions(-)
16
3 files changed, 55 insertions(+), 8 deletions(-)
20
17
21
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
18
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
22
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
23
--- a/target/riscv/cpu.h
20
--- a/target/riscv/cpu.h
24
+++ b/target/riscv/cpu.h
21
+++ b/target/riscv/cpu.h
25
@@ -XXX,XX +XXX,XX @@ extern const char * const riscv_fpr_regnames[];
22
@@ -XXX,XX +XXX,XX @@ FIELD(TB_FLAGS, ITRIGGER, 22, 1)
26
extern const char * const riscv_excp_names[];
23
/* Virtual mode enabled */
27
extern const char * const riscv_intr_names[];
24
FIELD(TB_FLAGS, VIRT_ENABLED, 23, 1)
28
25
FIELD(TB_FLAGS, PRIV, 24, 2)
29
+const char *riscv_cpu_get_trap_name(target_ulong cause, bool async);
26
+FIELD(TB_FLAGS, AXL, 26, 2)
30
void riscv_cpu_do_interrupt(CPUState *cpu);
27
31
int riscv_cpu_gdb_read_register(CPUState *cpu, GByteArray *buf, int reg);
28
#ifdef TARGET_RISCV32
32
int riscv_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg);
29
#define riscv_cpu_mxl(env) ((void)(env), MXL_RV32)
33
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
30
@@ -XXX,XX +XXX,XX @@ static inline const RISCVCPUConfig *riscv_cpu_cfg(CPURISCVState *env)
34
index XXXXXXX..XXXXXXX 100644
31
return &env_archcpu(env)->cfg;
35
--- a/target/riscv/cpu.c
32
}
36
+++ b/target/riscv/cpu.c
33
37
@@ -XXX,XX +XXX,XX @@ const char * const riscv_intr_names[] = {
34
-#if defined(TARGET_RISCV32)
38
"reserved"
35
-#define cpu_recompute_xl(env) ((void)(env), MXL_RV32)
39
};
36
-#else
40
37
-static inline RISCVMXL cpu_recompute_xl(CPURISCVState *env)
41
+const char *riscv_cpu_get_trap_name(target_ulong cause, bool async)
38
+#if !defined(CONFIG_USER_ONLY)
39
+static inline int cpu_address_mode(CPURISCVState *env)
42
+{
40
+{
43
+ if (async) {
41
+ int mode = env->priv;
44
+ return (cause < ARRAY_SIZE(riscv_intr_names)) ?
42
+
45
+ riscv_intr_names[cause] : "(unknown)";
43
+ if (mode == PRV_M && get_field(env->mstatus, MSTATUS_MPRV)) {
46
+ } else {
44
+ mode = get_field(env->mstatus, MSTATUS_MPP);
47
+ return (cause < ARRAY_SIZE(riscv_excp_names)) ?
48
+ riscv_excp_names[cause] : "(unknown)";
49
+ }
45
+ }
46
+ return mode;
50
+}
47
+}
51
+
48
+
52
static void set_misa(CPURISCVState *env, target_ulong misa)
49
+static inline RISCVMXL cpu_get_xl(CPURISCVState *env, target_ulong mode)
53
{
50
{
54
env->misa_mask = env->misa = misa;
51
RISCVMXL xl = env->misa_mxl;
52
-#if !defined(CONFIG_USER_ONLY)
53
/*
54
* When emulating a 32-bit-only cpu, use RV32.
55
* When emulating a 64-bit cpu, and MXL has been reduced to RV32,
56
@@ -XXX,XX +XXX,XX @@ static inline RISCVMXL cpu_recompute_xl(CPURISCVState *env)
57
* back to RV64 for lower privs.
58
*/
59
if (xl != MXL_RV32) {
60
- switch (env->priv) {
61
+ switch (mode) {
62
case PRV_M:
63
break;
64
case PRV_U:
65
@@ -XXX,XX +XXX,XX @@ static inline RISCVMXL cpu_recompute_xl(CPURISCVState *env)
66
break;
67
}
68
}
69
-#endif
70
return xl;
71
}
72
#endif
73
74
+#if defined(TARGET_RISCV32)
75
+#define cpu_recompute_xl(env) ((void)(env), MXL_RV32)
76
+#else
77
+static inline RISCVMXL cpu_recompute_xl(CPURISCVState *env)
78
+{
79
+#if !defined(CONFIG_USER_ONLY)
80
+ return cpu_get_xl(env, env->priv);
81
+#else
82
+ return env->misa_mxl;
83
+#endif
84
+}
85
+#endif
86
+
87
+#if defined(TARGET_RISCV32)
88
+#define cpu_address_xl(env) ((void)(env), MXL_RV32)
89
+#else
90
+static inline RISCVMXL cpu_address_xl(CPURISCVState *env)
91
+{
92
+#ifdef CONFIG_USER_ONLY
93
+ return env->xl;
94
+#else
95
+ int mode = cpu_address_mode(env);
96
+
97
+ return cpu_get_xl(env, mode);
98
+#endif
99
+}
100
+#endif
101
+
102
static inline int riscv_cpu_xlen(CPURISCVState *env)
103
{
104
return 16 << env->xl;
55
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
105
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
56
index XXXXXXX..XXXXXXX 100644
106
index XXXXXXX..XXXXXXX 100644
57
--- a/target/riscv/cpu_helper.c
107
--- a/target/riscv/cpu_helper.c
58
+++ b/target/riscv/cpu_helper.c
108
+++ b/target/riscv/cpu_helper.c
59
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_do_interrupt(CPUState *cs)
109
@@ -XXX,XX +XXX,XX @@ void cpu_get_tb_cpu_state(CPURISCVState *env, vaddr *pc,
60
}
110
flags = FIELD_DP32(flags, TB_FLAGS, FS, fs);
111
flags = FIELD_DP32(flags, TB_FLAGS, VS, vs);
112
flags = FIELD_DP32(flags, TB_FLAGS, XL, env->xl);
113
+ flags = FIELD_DP32(flags, TB_FLAGS, AXL, cpu_address_xl(env));
114
if (env->cur_pmmask != 0) {
115
flags = FIELD_DP32(flags, TB_FLAGS, PM_MASK_ENABLED, 1);
61
}
116
}
62
117
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
63
- trace_riscv_trap(env->mhartid, async, cause, env->pc, tval, cause < 23 ?
118
index XXXXXXX..XXXXXXX 100644
64
- (async ? riscv_intr_names : riscv_excp_names)[cause] : "(unknown)");
119
--- a/target/riscv/translate.c
65
+ trace_riscv_trap(env->mhartid, async, cause, env->pc, tval,
120
+++ b/target/riscv/translate.c
66
+ riscv_cpu_get_trap_name(cause, async));
121
@@ -XXX,XX +XXX,XX @@ typedef struct DisasContext {
67
122
target_ulong priv_ver;
68
if (env->priv <= PRV_S &&
123
RISCVMXL misa_mxl_max;
69
cause < TARGET_LONG_BITS && ((deleg >> cause) & 1)) {
124
RISCVMXL xl;
125
+ RISCVMXL address_xl;
126
uint32_t misa_ext;
127
uint32_t opcode;
128
RISCVExtStatus mstatus_fs;
129
@@ -XXX,XX +XXX,XX @@ static inline bool has_ext(DisasContext *ctx, uint32_t ext)
130
#define get_xl(ctx) ((ctx)->xl)
131
#endif
132
133
+#ifdef TARGET_RISCV32
134
+#define get_address_xl(ctx) MXL_RV32
135
+#elif defined(CONFIG_USER_ONLY)
136
+#define get_address_xl(ctx) MXL_RV64
137
+#else
138
+#define get_address_xl(ctx) ((ctx)->address_xl)
139
+#endif
140
+
141
/* The word size for this machine mode. */
142
static inline int __attribute__((unused)) get_xlen(DisasContext *ctx)
143
{
144
@@ -XXX,XX +XXX,XX @@ static TCGv get_address(DisasContext *ctx, int rs1, int imm)
145
tcg_gen_addi_tl(addr, src1, imm);
146
if (ctx->pm_mask_enabled) {
147
tcg_gen_andc_tl(addr, addr, pm_mask);
148
- } else if (get_xl(ctx) == MXL_RV32) {
149
+ } else if (get_address_xl(ctx) == MXL_RV32) {
150
tcg_gen_ext32u_tl(addr, addr);
151
}
152
if (ctx->pm_base_enabled) {
153
tcg_gen_or_tl(addr, addr, pm_base);
154
}
155
+
156
return addr;
157
}
158
159
@@ -XXX,XX +XXX,XX @@ static void riscv_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
160
ctx->vl_eq_vlmax = FIELD_EX32(tb_flags, TB_FLAGS, VL_EQ_VLMAX);
161
ctx->misa_mxl_max = env->misa_mxl_max;
162
ctx->xl = FIELD_EX32(tb_flags, TB_FLAGS, XL);
163
+ ctx->address_xl = FIELD_EX32(tb_flags, TB_FLAGS, AXL);
164
ctx->cs = cs;
165
ctx->pm_mask_enabled = FIELD_EX32(tb_flags, TB_FLAGS, PM_MASK_ENABLED);
166
ctx->pm_base_enabled = FIELD_EX32(tb_flags, TB_FLAGS, PM_BASE_ENABLED);
70
--
167
--
71
2.28.0
168
2.40.1
72
169
73
170
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
2
2
3
At present the CLINT timestamp is using a hard-coded timebase
3
Pointer mask is also affected by MPRV which means cur_pmbase/pmmask
4
frequency value SIFIVE_CLINT_TIMEBASE_FREQ. This might not be
4
should also take MPRV into consideration. As pointer mask for instruction
5
true for all boards.
5
is not supported currently, so we can directly update cur_pmbase/pmmask
6
based on address related mode and xlen affected by MPRV now.
6
7
7
Add a new 'timebase-freq' property to the CLINT device, and
8
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
8
update various functions to accept this as a parameter.
9
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
9
10
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
10
Signed-off-by: Bin Meng <bin.meng@windriver.com>
11
Message-Id: <20230614032547.35895-3-liweiwei@iscas.ac.cn>
11
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
12
Message-Id: <1598924352-89526-16-git-send-email-bmeng.cn@gmail.com>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
14
---
13
---
15
include/hw/riscv/sifive_clint.h | 4 +++-
14
target/riscv/cpu_helper.c | 7 +++++--
16
target/riscv/cpu.h | 6 ++++--
15
target/riscv/csr.c | 27 ++++++++++++++++++++-------
17
hw/riscv/microchip_pfsoc.c | 6 +++++-
16
2 files changed, 25 insertions(+), 9 deletions(-)
18
hw/riscv/sifive_clint.c | 26 +++++++++++++++-----------
19
hw/riscv/sifive_e.c | 3 ++-
20
hw/riscv/sifive_u.c | 3 ++-
21
hw/riscv/spike.c | 3 ++-
22
hw/riscv/virt.c | 3 ++-
23
target/riscv/cpu_helper.c | 4 +++-
24
target/riscv/csr.c | 4 ++--
25
10 files changed, 40 insertions(+), 22 deletions(-)
26
17
27
diff --git a/include/hw/riscv/sifive_clint.h b/include/hw/riscv/sifive_clint.h
28
index XXXXXXX..XXXXXXX 100644
29
--- a/include/hw/riscv/sifive_clint.h
30
+++ b/include/hw/riscv/sifive_clint.h
31
@@ -XXX,XX +XXX,XX @@ typedef struct SiFiveCLINTState {
32
uint32_t timecmp_base;
33
uint32_t time_base;
34
uint32_t aperture_size;
35
+ uint32_t timebase_freq;
36
} SiFiveCLINTState;
37
38
DeviceState *sifive_clint_create(hwaddr addr, hwaddr size,
39
uint32_t hartid_base, uint32_t num_harts, uint32_t sip_base,
40
- uint32_t timecmp_base, uint32_t time_base, bool provide_rdtime);
41
+ uint32_t timecmp_base, uint32_t time_base, uint32_t timebase_freq,
42
+ bool provide_rdtime);
43
44
enum {
45
SIFIVE_SIP_BASE = 0x0,
46
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
47
index XXXXXXX..XXXXXXX 100644
48
--- a/target/riscv/cpu.h
49
+++ b/target/riscv/cpu.h
50
@@ -XXX,XX +XXX,XX @@ struct CPURISCVState {
51
pmp_table_t pmp_state;
52
53
/* machine specific rdtime callback */
54
- uint64_t (*rdtime_fn)(void);
55
+ uint64_t (*rdtime_fn)(uint32_t);
56
+ uint32_t rdtime_fn_arg;
57
58
/* True if in debugger mode. */
59
bool debugger;
60
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_swap_hypervisor_regs(CPURISCVState *env);
61
int riscv_cpu_claim_interrupts(RISCVCPU *cpu, uint32_t interrupts);
62
uint32_t riscv_cpu_update_mip(RISCVCPU *cpu, uint32_t mask, uint32_t value);
63
#define BOOL_TO_MASK(x) (-!!(x)) /* helper for riscv_cpu_update_mip value */
64
-void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(void));
65
+void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(uint32_t),
66
+ uint32_t arg);
67
#endif
68
void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv);
69
70
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
71
index XXXXXXX..XXXXXXX 100644
72
--- a/hw/riscv/microchip_pfsoc.c
73
+++ b/hw/riscv/microchip_pfsoc.c
74
@@ -XXX,XX +XXX,XX @@
75
#define BIOS_FILENAME "hss.bin"
76
#define RESET_VECTOR 0x20220000
77
78
+/* CLINT timebase frequency */
79
+#define CLINT_TIMEBASE_FREQ 1000000
80
+
81
/* GEM version */
82
#define GEM_REVISION 0x0107010c
83
84
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
85
/* CLINT */
86
sifive_clint_create(memmap[MICROCHIP_PFSOC_CLINT].base,
87
memmap[MICROCHIP_PFSOC_CLINT].size, 0, ms->smp.cpus,
88
- SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, false);
89
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE,
90
+ CLINT_TIMEBASE_FREQ, false);
91
92
/* L2 cache controller */
93
create_unimplemented_device("microchip.pfsoc.l2cc",
94
diff --git a/hw/riscv/sifive_clint.c b/hw/riscv/sifive_clint.c
95
index XXXXXXX..XXXXXXX 100644
96
--- a/hw/riscv/sifive_clint.c
97
+++ b/hw/riscv/sifive_clint.c
98
@@ -XXX,XX +XXX,XX @@
99
#include "hw/riscv/sifive_clint.h"
100
#include "qemu/timer.h"
101
102
-static uint64_t cpu_riscv_read_rtc(void)
103
+static uint64_t cpu_riscv_read_rtc(uint32_t timebase_freq)
104
{
105
return muldiv64(qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL),
106
- SIFIVE_CLINT_TIMEBASE_FREQ, NANOSECONDS_PER_SECOND);
107
+ timebase_freq, NANOSECONDS_PER_SECOND);
108
}
109
110
/*
111
* Called when timecmp is written to update the QEMU timer or immediately
112
* trigger timer interrupt if mtimecmp <= current timer value.
113
*/
114
-static void sifive_clint_write_timecmp(RISCVCPU *cpu, uint64_t value)
115
+static void sifive_clint_write_timecmp(RISCVCPU *cpu, uint64_t value,
116
+ uint32_t timebase_freq)
117
{
118
uint64_t next;
119
uint64_t diff;
120
121
- uint64_t rtc_r = cpu_riscv_read_rtc();
122
+ uint64_t rtc_r = cpu_riscv_read_rtc(timebase_freq);
123
124
cpu->env.timecmp = value;
125
if (cpu->env.timecmp <= rtc_r) {
126
@@ -XXX,XX +XXX,XX @@ static void sifive_clint_write_timecmp(RISCVCPU *cpu, uint64_t value)
127
diff = cpu->env.timecmp - rtc_r;
128
/* back to ns (note args switched in muldiv64) */
129
next = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) +
130
- muldiv64(diff, NANOSECONDS_PER_SECOND, SIFIVE_CLINT_TIMEBASE_FREQ);
131
+ muldiv64(diff, NANOSECONDS_PER_SECOND, timebase_freq);
132
timer_mod(cpu->env.timer, next);
133
}
134
135
@@ -XXX,XX +XXX,XX @@ static uint64_t sifive_clint_read(void *opaque, hwaddr addr, unsigned size)
136
}
137
} else if (addr == clint->time_base) {
138
/* time_lo */
139
- return cpu_riscv_read_rtc() & 0xFFFFFFFF;
140
+ return cpu_riscv_read_rtc(clint->timebase_freq) & 0xFFFFFFFF;
141
} else if (addr == clint->time_base + 4) {
142
/* time_hi */
143
- return (cpu_riscv_read_rtc() >> 32) & 0xFFFFFFFF;
144
+ return (cpu_riscv_read_rtc(clint->timebase_freq) >> 32) & 0xFFFFFFFF;
145
}
146
147
error_report("clint: invalid read: %08x", (uint32_t)addr);
148
@@ -XXX,XX +XXX,XX @@ static void sifive_clint_write(void *opaque, hwaddr addr, uint64_t value,
149
/* timecmp_lo */
150
uint64_t timecmp_hi = env->timecmp >> 32;
151
sifive_clint_write_timecmp(RISCV_CPU(cpu),
152
- timecmp_hi << 32 | (value & 0xFFFFFFFF));
153
+ timecmp_hi << 32 | (value & 0xFFFFFFFF), clint->timebase_freq);
154
return;
155
} else if ((addr & 0x7) == 4) {
156
/* timecmp_hi */
157
uint64_t timecmp_lo = env->timecmp;
158
sifive_clint_write_timecmp(RISCV_CPU(cpu),
159
- value << 32 | (timecmp_lo & 0xFFFFFFFF));
160
+ value << 32 | (timecmp_lo & 0xFFFFFFFF), clint->timebase_freq);
161
} else {
162
error_report("clint: invalid timecmp write: %08x", (uint32_t)addr);
163
}
164
@@ -XXX,XX +XXX,XX @@ static Property sifive_clint_properties[] = {
165
DEFINE_PROP_UINT32("timecmp-base", SiFiveCLINTState, timecmp_base, 0),
166
DEFINE_PROP_UINT32("time-base", SiFiveCLINTState, time_base, 0),
167
DEFINE_PROP_UINT32("aperture-size", SiFiveCLINTState, aperture_size, 0),
168
+ DEFINE_PROP_UINT32("timebase-freq", SiFiveCLINTState, timebase_freq, 0),
169
DEFINE_PROP_END_OF_LIST(),
170
};
171
172
@@ -XXX,XX +XXX,XX @@ type_init(sifive_clint_register_types)
173
*/
174
DeviceState *sifive_clint_create(hwaddr addr, hwaddr size,
175
uint32_t hartid_base, uint32_t num_harts, uint32_t sip_base,
176
- uint32_t timecmp_base, uint32_t time_base, bool provide_rdtime)
177
+ uint32_t timecmp_base, uint32_t time_base, uint32_t timebase_freq,
178
+ bool provide_rdtime)
179
{
180
int i;
181
for (i = 0; i < num_harts; i++) {
182
@@ -XXX,XX +XXX,XX @@ DeviceState *sifive_clint_create(hwaddr addr, hwaddr size,
183
continue;
184
}
185
if (provide_rdtime) {
186
- riscv_cpu_set_rdtime_fn(env, cpu_riscv_read_rtc);
187
+ riscv_cpu_set_rdtime_fn(env, cpu_riscv_read_rtc, timebase_freq);
188
}
189
env->timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
190
&sifive_clint_timer_cb, cpu);
191
@@ -XXX,XX +XXX,XX @@ DeviceState *sifive_clint_create(hwaddr addr, hwaddr size,
192
qdev_prop_set_uint32(dev, "timecmp-base", timecmp_base);
193
qdev_prop_set_uint32(dev, "time-base", time_base);
194
qdev_prop_set_uint32(dev, "aperture-size", size);
195
+ qdev_prop_set_uint32(dev, "timebase-freq", timebase_freq);
196
sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
197
sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, addr);
198
return dev;
199
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
200
index XXXXXXX..XXXXXXX 100644
201
--- a/hw/riscv/sifive_e.c
202
+++ b/hw/riscv/sifive_e.c
203
@@ -XXX,XX +XXX,XX @@ static void sifive_e_soc_realize(DeviceState *dev, Error **errp)
204
memmap[SIFIVE_E_PLIC].size);
205
sifive_clint_create(memmap[SIFIVE_E_CLINT].base,
206
memmap[SIFIVE_E_CLINT].size, 0, ms->smp.cpus,
207
- SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, false);
208
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE,
209
+ SIFIVE_CLINT_TIMEBASE_FREQ, false);
210
create_unimplemented_device("riscv.sifive.e.aon",
211
memmap[SIFIVE_E_AON].base, memmap[SIFIVE_E_AON].size);
212
sifive_e_prci_create(memmap[SIFIVE_E_PRCI].base);
213
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
214
index XXXXXXX..XXXXXXX 100644
215
--- a/hw/riscv/sifive_u.c
216
+++ b/hw/riscv/sifive_u.c
217
@@ -XXX,XX +XXX,XX @@ static void sifive_u_soc_realize(DeviceState *dev, Error **errp)
218
serial_hd(1), qdev_get_gpio_in(DEVICE(s->plic), SIFIVE_U_UART1_IRQ));
219
sifive_clint_create(memmap[SIFIVE_U_CLINT].base,
220
memmap[SIFIVE_U_CLINT].size, 0, ms->smp.cpus,
221
- SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, false);
222
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE,
223
+ SIFIVE_CLINT_TIMEBASE_FREQ, false);
224
225
if (!sysbus_realize(SYS_BUS_DEVICE(&s->prci), errp)) {
226
return;
227
diff --git a/hw/riscv/spike.c b/hw/riscv/spike.c
228
index XXXXXXX..XXXXXXX 100644
229
--- a/hw/riscv/spike.c
230
+++ b/hw/riscv/spike.c
231
@@ -XXX,XX +XXX,XX @@ static void spike_board_init(MachineState *machine)
232
sifive_clint_create(
233
memmap[SPIKE_CLINT].base + i * memmap[SPIKE_CLINT].size,
234
memmap[SPIKE_CLINT].size, base_hartid, hart_count,
235
- SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, false);
236
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE,
237
+ SIFIVE_CLINT_TIMEBASE_FREQ, false);
238
}
239
240
/* register system main memory (actual RAM) */
241
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
242
index XXXXXXX..XXXXXXX 100644
243
--- a/hw/riscv/virt.c
244
+++ b/hw/riscv/virt.c
245
@@ -XXX,XX +XXX,XX @@ static void virt_machine_init(MachineState *machine)
246
sifive_clint_create(
247
memmap[VIRT_CLINT].base + i * memmap[VIRT_CLINT].size,
248
memmap[VIRT_CLINT].size, base_hartid, hart_count,
249
- SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, true);
250
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE,
251
+ SIFIVE_CLINT_TIMEBASE_FREQ, true);
252
253
/* Per-socket PLIC hart topology configuration string */
254
plic_hart_config_len =
255
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
18
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
256
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
257
--- a/target/riscv/cpu_helper.c
20
--- a/target/riscv/cpu_helper.c
258
+++ b/target/riscv/cpu_helper.c
21
+++ b/target/riscv/cpu_helper.c
259
@@ -XXX,XX +XXX,XX @@ uint32_t riscv_cpu_update_mip(RISCVCPU *cpu, uint32_t mask, uint32_t value)
22
@@ -XXX,XX +XXX,XX @@ void cpu_get_tb_cpu_state(CPURISCVState *env, vaddr *pc,
260
return old;
23
void riscv_cpu_update_mask(CPURISCVState *env)
261
}
262
263
-void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(void))
264
+void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(uint32_t),
265
+ uint32_t arg)
266
{
24
{
267
env->rdtime_fn = fn;
25
target_ulong mask = 0, base = 0;
268
+ env->rdtime_fn_arg = arg;
26
+ RISCVMXL xl = env->xl;
269
}
27
/*
270
28
* TODO: Current RVJ spec does not specify
271
void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv)
29
* how the extension interacts with XLEN.
30
*/
31
#ifndef CONFIG_USER_ONLY
32
+ int mode = cpu_address_mode(env);
33
+ xl = cpu_get_xl(env, mode);
34
if (riscv_has_ext(env, RVJ)) {
35
- switch (env->priv) {
36
+ switch (mode) {
37
case PRV_M:
38
if (env->mmte & M_PM_ENABLE) {
39
mask = env->mpmmask;
40
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_update_mask(CPURISCVState *env)
41
}
42
}
43
#endif
44
- if (env->xl == MXL_RV32) {
45
+ if (xl == MXL_RV32) {
46
env->cur_pmmask = mask & UINT32_MAX;
47
env->cur_pmbase = base & UINT32_MAX;
48
} else {
272
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
49
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
273
index XXXXXXX..XXXXXXX 100644
50
index XXXXXXX..XXXXXXX 100644
274
--- a/target/riscv/csr.c
51
--- a/target/riscv/csr.c
275
+++ b/target/riscv/csr.c
52
+++ b/target/riscv/csr.c
276
@@ -XXX,XX +XXX,XX @@ static int read_time(CPURISCVState *env, int csrno, target_ulong *val)
53
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
277
return -RISCV_EXCP_ILLEGAL_INST;
54
*/
55
if (env->debugger) {
56
env->xl = cpu_recompute_xl(env);
57
- riscv_cpu_update_mask(env);
278
}
58
}
279
59
+
280
- *val = env->rdtime_fn() + delta;
60
+ riscv_cpu_update_mask(env);
281
+ *val = env->rdtime_fn(env->rdtime_fn_arg) + delta;
61
return RISCV_EXCP_NONE;
282
return 0;
283
}
62
}
284
63
285
@@ -XXX,XX +XXX,XX @@ static int read_timeh(CPURISCVState *env, int csrno, target_ulong *val)
64
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mpmmask(CPURISCVState *env, int csrno,
286
return -RISCV_EXCP_ILLEGAL_INST;
65
uint64_t mstatus;
66
67
env->mpmmask = val;
68
- if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
69
+ if ((cpu_address_mode(env) == PRV_M) && (env->mmte & M_PM_ENABLE)) {
70
env->cur_pmmask = val;
287
}
71
}
288
72
env->mmte |= EXT_STATUS_DIRTY;
289
- *val = (env->rdtime_fn() + delta) >> 32;
73
@@ -XXX,XX +XXX,XX @@ static RISCVException write_spmmask(CPURISCVState *env, int csrno,
290
+ *val = (env->rdtime_fn(env->rdtime_fn_arg) + delta) >> 32;
74
return RISCV_EXCP_NONE;
291
return 0;
75
}
292
}
76
env->spmmask = val;
293
#endif
77
- if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
78
+ if ((cpu_address_mode(env) == PRV_S) && (env->mmte & S_PM_ENABLE)) {
79
env->cur_pmmask = val;
80
+ if (cpu_get_xl(env, PRV_S) == MXL_RV32) {
81
+ env->cur_pmmask &= UINT32_MAX;
82
+ }
83
}
84
env->mmte |= EXT_STATUS_DIRTY;
85
86
@@ -XXX,XX +XXX,XX @@ static RISCVException write_upmmask(CPURISCVState *env, int csrno,
87
return RISCV_EXCP_NONE;
88
}
89
env->upmmask = val;
90
- if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
91
+ if ((cpu_address_mode(env) == PRV_U) && (env->mmte & U_PM_ENABLE)) {
92
env->cur_pmmask = val;
93
+ if (cpu_get_xl(env, PRV_U) == MXL_RV32) {
94
+ env->cur_pmmask &= UINT32_MAX;
95
+ }
96
}
97
env->mmte |= EXT_STATUS_DIRTY;
98
99
@@ -XXX,XX +XXX,XX @@ static RISCVException write_mpmbase(CPURISCVState *env, int csrno,
100
uint64_t mstatus;
101
102
env->mpmbase = val;
103
- if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
104
+ if ((cpu_address_mode(env) == PRV_M) && (env->mmte & M_PM_ENABLE)) {
105
env->cur_pmbase = val;
106
}
107
env->mmte |= EXT_STATUS_DIRTY;
108
@@ -XXX,XX +XXX,XX @@ static RISCVException write_spmbase(CPURISCVState *env, int csrno,
109
return RISCV_EXCP_NONE;
110
}
111
env->spmbase = val;
112
- if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
113
+ if ((cpu_address_mode(env) == PRV_S) && (env->mmte & S_PM_ENABLE)) {
114
env->cur_pmbase = val;
115
+ if (cpu_get_xl(env, PRV_S) == MXL_RV32) {
116
+ env->cur_pmbase &= UINT32_MAX;
117
+ }
118
}
119
env->mmte |= EXT_STATUS_DIRTY;
120
121
@@ -XXX,XX +XXX,XX @@ static RISCVException write_upmbase(CPURISCVState *env, int csrno,
122
return RISCV_EXCP_NONE;
123
}
124
env->upmbase = val;
125
- if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
126
+ if ((cpu_address_mode(env) == PRV_U) && (env->mmte & U_PM_ENABLE)) {
127
env->cur_pmbase = val;
128
+ if (cpu_get_xl(env, PRV_U) == MXL_RV32) {
129
+ env->cur_pmbase &= UINT32_MAX;
130
+ }
131
}
132
env->mmte |= EXT_STATUS_DIRTY;
133
294
--
134
--
295
2.28.0
135
2.40.1
296
297
diff view generated by jsdifflib
New patch
1
From: Bin Meng <bmeng@tinylab.org>
1
2
3
Upgrade OpenSBI from v1.2 to v1.3 and the pre-built bios images.
4
5
The v1.3 release includes the following commits:
6
7
440fa81 treewide: Replace TRUE/FALSE with true/false
8
6509127 Makefile: Remove -N ldflag to prevent linker RWX warning
9
65638f8 lib: utils/sys: Allow custom HTIF base address for RV32
10
f14595a lib: sbi: Allow platform to influence cold boot HART selection
11
6957ae0 platform: generic: Allow platform_override to select cold boot HART
12
cb7e7c3 platform: generic: Allow platform_override to perform firmware init
13
8020df8 generic/starfive: Add Starfive JH7110 platform implementation
14
6997552 lib: sbi_hsm: Rename 'priv' argument to 'arg1'
15
9e397e3 docs: domain_support: Use capital letter for privilege modes
16
9e0ba09 include: sbi: Fine grain the permissions for M and SU modes
17
aace1e1 lib: sbi: Use finer permission semantics for address validation
18
22dbdb3 lib: sbi: Add permissions for the firmware start till end
19
1ac14f1 lib: sbi: Use finer permission sematics to decide on PMP bits
20
44f736c lib: sbi: Modify the boot time region flag prints
21
20646e0 lib: utils: Use SU-{R/W/X} flags for region permissions during parsing
22
3e2f573 lib: utils: Disallow non-root domains from adding M-mode regions
23
59a08cd lib: utils: Add M-mode {R/W} flags to the MMIO regions
24
001106d docs: Update domain's region permissions and requirements
25
da5594b platform: generic: allwinner: Fix PLIC array bounds
26
ce2a834 docs: generic.md: fix typo of andes-ae350
27
8ecbe6d lib: sbi_hsm: handle failure when hart_stop returns SBI_ENOTSUPP
28
b1818ee include: types: add always inline compiler attribute
29
9c4eb35 lib: utils: atcsmu: Add Andes System Management Unit support
30
787296a platform: andes/ae350: Implement hart hotplug using HSM extension
31
7aaeeab lib: reset/fdt_reset_atcwdt200: Use defined macros and function in atcsmu.h
32
a990309 lib: utils: Fix reserved memory node for firmware memory
33
fefa548 firmware: Split RO/RX and RW sections
34
2f40a99 firmware: Move dynsym and reladyn sections to RX section
35
c10e3fe firmware: Add RW section offset in scratch
36
b666760 lib: sbi: Print the RW section offset
37
230278d lib: sbi: Add separate entries for firmware RX and RW regions
38
dea0922 platform: renesas/rzfive: Configure Local memory regions as part of root domain
39
33bf917 lib: utils: Add fdt_add_cpu_idle_states() helper function
40
c45992c platform: generic: allwinner: Advertise nonretentive suspend
41
c8ea836 firmware: Fix fw_rw_offset computation in fw_base.S
42
8050081 firmware: Not to clear all the MIP
43
84d15f4 lib: sbi_hsm: Use csr_set to restore the MIP
44
199189b lib: utils: Mark only the largest region as reserved in FDT
45
66b0e23 lib: sbi: Ensure domidx_to_domain_table is null-terminated
46
642f3de Makefile: Add missing .dep files for fw_*.elf.ld
47
09b34d8 include: Add support for byteorder/endianness conversion
48
680bea0 lib: utils/fdt: Use byteorder conversion functions in libfdt_env.h
49
b224ddb include: types: Add typedefs for endianness
50
aa5dafc include: sbi: Fix BSWAPx() macros for big-endian host
51
e3bf1af include: Add defines for SBI debug console extension
52
0ee3a86 lib: sbi: Add sbi_nputs() function
53
4e0572f lib: sbi: Add sbi_ngets() function
54
eab48c3 lib: sbi: Add sbi_domain_check_addr_range() function
55
5a41a38 lib: sbi: Implement SBI debug console extension
56
c43903c lib: sbi: Add console_puts() callback in the console device
57
29285ae lib: utils/serial: Implement console_puts() for semihosting
58
65c2190 lib: sbi: Speed-up sbi_printf() and friends using nputs()
59
321293c lib: utils/fdt: Fix fdt_pmu.c header dependency
60
aafcc90 platform: generic/allwinner: Fix sun20i-d1.c header dependency
61
745aaec platform: generic/andes: Fix ae350.c header dependency
62
99d09b6 include: fdt/fdt_helper: Change fdt_get_address() to return root.next_arg1
63
6861ee9 lib: utils: fdt_fixup: Fix compile error
64
4f2be40 docs: fix typo in fw.md
65
30ea806 lib: sbi_hart: Enable hcontext and scontext
66
81adc62 lib: sbi: Align SBI vendor extension id with mvendorid CSR
67
31b82e0 include: sbi: Remove extid parameter from vendor_ext_provider() callback
68
c100951 platform: generic: renesas: rzfive: Add support to configure the PMA
69
2491242 platform: generic: renesas: rzfive: Configure the PMA region
70
67b2a40 lib: sbi: sbi_ecall: Check the range of SBI error
71
5a75f53 lib: sbi/sbi_domain: cosmetic style fixes
72
bc06ff6 lib: utils/fdt/fdt_domain: Simplify region access permission check
73
17b3776 docs: domain_support: Update the DT example
74
1364d5a lib: sbi_hsm: Factor out invalid state detection
75
40f16a8 lib: sbi_hsm: Don't try to restore state on failed change
76
c88e039 lib: sbi_hsm: Ensure errors are consistent with spec
77
b1ae6ef lib: sbi_hsm: Move misplaced comment
78
07673fc lib: sbi_hsm: Remove unnecessary include
79
8a40306 lib: sbi_hsm: Export some functions
80
73623a0 lib: sbi: Add system suspend skeleton
81
c9917b6 lib: sbi: Add system_suspend_allowed domain property
82
7c964e2 lib: sbi: Implement system suspend
83
37558dc docs: Correct opensbi-domain property name
84
5ccebf0 platform: generic: Add system suspend test
85
908be1b gpio/starfive: add gpio driver and support gpio reset
86
4b28afc make: Add a command line option for debugging OpenSBI
87
e9d08bd lib: utils/i2c: Add minimal StarFive jh7110 I2C driver
88
568ea49 platform: starfive: add PMIC power ops in JH7110 visionfive2 board
89
506144f lib: serial: Cadence: Enable compatibility for cdns,uart-r1p8
90
1fe8dc9 lib: sbi_pmu: add callback for counter width
91
51951d9 lib: sbi_pmu: Implement sbi_pmu_counter_fw_read_hi
92
60c358e lib: sbi_pmu: Reserve space for implementation specific firmware events
93
548e4b4 lib: sbi_pmu: Rename fw_counter_value
94
b51ddff lib: sbi_pmu: Update sbi_pmu dev ops
95
641d2e9 lib: sbi_pmu: Use dedicated event code for platform firmware events
96
57d3aa3 lib: sbi_pmu: Introduce fw_counter_write_value API
97
c631a7d lib: sbi_pmu: Add hartid parameter PMU device ops
98
d56049e lib: sbi: Refactor the calls to sbi_hart_switch_mode()
99
e8e9ed3 lib: sbi: Set the state of a hart to START_PENDING after the hart is ready
100
c6a092c lib: sbi: Clear IPIs before init_warm_startup in non-boot harts
101
ed88a63 lib: sbi_scratch: Optimize the alignment code for alloc size
102
73ab11d lib: sbi: Fix how to check whether the domain contains fw_region
103
f64dfcd lib: sbi: Introduce sbi_entry_count() function
104
30b9e7e lib: sbi_hsm: Fix sbi_hsm_hart_start() for platform with hart hotplug
105
8e90259 lib: sbi_hart: clear mip csr during hart init
106
45ba2b2 include: Add defines for SBI CPPC extension
107
33caae8 lib: sbi: Implement SBI CPPC extension
108
91767d0 lib: sbi: Print the CPPC device name
109
edc9914 lib: sbi_pmu: Align the event type offset as per SBI specification
110
ee016a7 docs: Correct FW_JUMP_FDT_ADDR calculation example
111
2868f26 lib: utils: fdt_fixup: avoid buffer overrun
112
66fa925 lib: sbi: Optimize sbi_tlb
113
24dde46 lib: sbi: Optimize sbi_ipi
114
80078ab sbi: tlb: Simplify to tlb_process_count/tlb_process function
115
bf40e07 lib: sbi: Optimize sbi_tlb queue waiting
116
eeab500 platform: generic: andes/renesas: Add SBI EXT to check for enabling IOCP errata
117
f692289 firmware: Optimize loading relocation type
118
e41dbb5 firmware: Change to use positive offset to access relocation entries
119
bdb3c42 lib: sbi: Do not clear active_events for cycle/instret when stopping
120
674e019 lib: sbi: Fix counter index calculation for SBI_PMU_CFG_FLAG_SKIP_MATCH
121
f5dfd99 lib: sbi: Don't check SBI error range for legacy console getchar
122
7919530 lib: sbi: Add debug print when sbi_pmu_init fails
123
4e33530 lib: sbi: Remove unnecessary semicolon
124
6bc02de lib: sbi: Simplify sbi_ipi_process remove goto
125
dc1c7db lib: sbi: Simplify BITS_PER_LONG definition
126
f58c140 lib: sbi: Introduce register_extensions extension callback
127
e307ba7 lib: sbi: Narrow vendor extension range
128
042f0c3 lib: sbi: pmu: Remove unnecessary probe function
129
8b952d4 lib: sbi: Only register available extensions
130
767b5fc lib: sbi: Optimize probe of srst/susp
131
c3e31cb lib: sbi: Remove 0/1 probe implementations
132
33f1722 lib: sbi: Document sbi_ecall_extension members
133
d4c46e0 Makefile: Dereference symlinks on install
134
8b99a7f lib: sbi: Fix return of sbi_console_init
135
264d0be lib: utils: Improve fdt_serial_init
136
9a0bdd0 lib: utils: Improve fdt_ipi
137
122f226 lib: utils: Improve fdt_timer
138
df75e09 lib: utils/ipi: buffer overrun aclint_mswi_cold_init
139
bdde2ec lib: sbi: Align system suspend errors with spec
140
aad7a37 include: sbi_scratch: Add helper macros to access data type
141
5cf9a54 platform: Allow platforms to specify heap size
142
40d36a6 lib: sbi: Introduce simple heap allocator
143
2a04f70 lib: sbi: Print scratch size and usage at boot time
144
bbff53f lib: sbi_pmu: Use heap for per-HART PMU state
145
ef4542d lib: sbi: Use heap for root domain creation
146
66daafe lib: sbi: Use scratch space to save per-HART domain pointer
147
fa5ad2e lib: utils/gpio: Use heap in SiFive and StartFive GPIO drivers
148
903e88c lib: utils/i2c: Use heap in DesignWare and SiFive I2C drivers
149
5a8cfcd lib: utils/ipi: Use heap in ACLINT MSWI driver
150
3013716 lib: utils/irqchip: Use heap in PLIC, APLIC and IMSIC drivers
151
7e5636a lib: utils/timer: Use heap in ACLINT MTIMER driver
152
3c1c972 lib: utils/fdt: Use heap in FDT domain parsing
153
acbd8fc lib: utils/ipi: Use scratch space to save per-HART MSWI pointer
154
f0516be lib: utils/timer: Use scratch space to save per-HART MTIMER pointer
155
b3594ac lib: utils/irqchip: Use scratch space to save per-HART PLIC pointer
156
1df52fa lib: utils/irqchip: Don't check hartid in imsic_update_hartid_table()
157
355796c lib: utils/irqchip: Use scratch space to save per-HART IMSIC pointer
158
524feec docs: Add OpenSBI logo and use it in the top-level README.md
159
932be2c README.md: Improve project copyright information
160
8153b26 platform/lib: Set no-map attribute on all PMP regions
161
d64942f firmware: Fix find hart index
162
27c957a lib: reset: Move fdt_reset_init into generic_early_init
163
8bd666a lib: sbi: check A2 register in ecall_dbcn_handler.
164
2552799 include: Bump-up version to 1.3
165
166
Signed-off-by: Bin Meng <bmeng@tinylab.org>
167
Message-Id: <20230630160717.843044-1-bmeng@tinylab.org>
168
Tested-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
169
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
170
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
171
---
172
.../opensbi-riscv32-generic-fw_dynamic.bin | Bin 123072 -> 135344 bytes
173
.../opensbi-riscv64-generic-fw_dynamic.bin | Bin 121800 -> 138304 bytes
174
roms/opensbi | 2 +-
175
3 files changed, 1 insertion(+), 1 deletion(-)
176
177
diff --git a/pc-bios/opensbi-riscv32-generic-fw_dynamic.bin b/pc-bios/opensbi-riscv32-generic-fw_dynamic.bin
178
index XXXXXXX..XXXXXXX 100644
179
Binary files a/pc-bios/opensbi-riscv32-generic-fw_dynamic.bin and b/pc-bios/opensbi-riscv32-generic-fw_dynamic.bin differ
180
diff --git a/pc-bios/opensbi-riscv64-generic-fw_dynamic.bin b/pc-bios/opensbi-riscv64-generic-fw_dynamic.bin
181
index XXXXXXX..XXXXXXX 100644
182
Binary files a/pc-bios/opensbi-riscv64-generic-fw_dynamic.bin and b/pc-bios/opensbi-riscv64-generic-fw_dynamic.bin differ
183
diff --git a/roms/opensbi b/roms/opensbi
184
index XXXXXXX..XXXXXXX 160000
185
--- a/roms/opensbi
186
+++ b/roms/opensbi
187
@@ -1 +1 @@
188
-Subproject commit 6b5188ca14e59ce7bf71afe4e7d3d557c3d31bf8
189
+Subproject commit 2552799a1df30a3dcd2321a8b75d61d06f5fb9fc
190
--
191
2.40.1
diff view generated by jsdifflib
New patch
1
From: Bin Meng <bmeng@tinylab.org>
1
2
3
The 32-bit Spike boot issue has been fixed in the OpenSBI v1.3.
4
Let's enable the 32-bit Spike OpenSBI boot testing.
5
6
Signed-off-by: Bin Meng <bmeng@tinylab.org>
7
Message-Id: <20230630160717.843044-2-bmeng@tinylab.org>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
12
tests/avocado/riscv_opensbi.py | 2 --
13
1 file changed, 2 deletions(-)
14
15
diff --git a/tests/avocado/riscv_opensbi.py b/tests/avocado/riscv_opensbi.py
16
index XXXXXXX..XXXXXXX 100644
17
--- a/tests/avocado/riscv_opensbi.py
18
+++ b/tests/avocado/riscv_opensbi.py
19
@@ -XXX,XX +XXX,XX @@
20
# later. See the COPYING file in the top-level directory.
21
22
from avocado_qemu import QemuSystemTest
23
-from avocado import skip
24
from avocado_qemu import wait_for_console_pattern
25
26
class RiscvOpenSBI(QemuSystemTest):
27
@@ -XXX,XX +XXX,XX @@ def boot_opensbi(self):
28
wait_for_console_pattern(self, 'Platform Name')
29
wait_for_console_pattern(self, 'Boot HART MEDELEG')
30
31
- @skip("requires OpenSBI fix to work")
32
def test_riscv32_spike(self):
33
"""
34
:avocado: tags=arch:riscv32
35
--
36
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Tommy Wu <tommy.wu@sifive.com>
2
2
3
This is an initial support for Microchip PolarFire SoC Icicle Kit.
3
The watchdog timer is in the always-on domain device of HiFive 1 rev b,
4
The Icicle Kit board integrates a PolarFire SoC, with one SiFive's
4
so this patch added the AON device to the sifive_e machine. This patch
5
E51 plus four U54 cores and many on-chip peripherals and an FPGA.
5
only implemented the functionality of the watchdog timer.
6
6
7
For more details about Microchip PolarFire Soc, please see:
7
Signed-off-by: Tommy Wu <tommy.wu@sifive.com>
8
https://www.microsemi.com/product-directory/soc-fpgas/5498-polarfire-soc-fpga
8
Reviewed-by: Frank Chang <frank.chang@sifive.com>
9
9
Acked-by: Alistair Francis <alistair.francis@wdc.com>
10
Unlike SiFive FU540, the RISC-V core resect vector is at 0x20220000.
10
Message-Id: <20230627141216.3962299-2-tommy.wu@sifive.com>
11
The following perepherals are created as an unimplemented device:
12
13
- Bus Error Uint 0/1/2/3/4
14
- L2 cache controller
15
- SYSREG
16
- MPUCFG
17
- IOSCBCFG
18
19
More devices will be added later.
20
21
The BIOS image used by this machine is hss.bin, aka Hart Software
22
Services, which can be built from:
23
https://github.com/polarfire-soc/hart-software-services
24
25
To launch this machine:
26
$ qemu-system-riscv64 -nographic -M microchip-icicle-kit
27
28
The memory is set to 1 GiB by default to match the hardware.
29
A sanity check on ram size is performed in the machine init routine
30
to prompt user to increase the RAM size to > 1 GiB when less than
31
1 GiB ram is detected.
32
33
Signed-off-by: Bin Meng <bin.meng@windriver.com>
34
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
35
Message-Id: <1598924352-89526-5-git-send-email-bmeng.cn@gmail.com>
36
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
37
---
12
---
38
default-configs/riscv64-softmmu.mak | 1 +
13
include/hw/misc/sifive_e_aon.h | 60 +++++++
39
include/hw/riscv/microchip_pfsoc.h | 88 ++++++++
14
hw/misc/sifive_e_aon.c | 319 +++++++++++++++++++++++++++++++++
40
hw/riscv/microchip_pfsoc.c | 312 ++++++++++++++++++++++++++++
15
hw/misc/Kconfig | 3 +
41
MAINTAINERS | 7 +
16
hw/misc/meson.build | 1 +
42
hw/riscv/Kconfig | 6 +
17
4 files changed, 383 insertions(+)
43
hw/riscv/meson.build | 1 +
18
create mode 100644 include/hw/misc/sifive_e_aon.h
44
6 files changed, 415 insertions(+)
19
create mode 100644 hw/misc/sifive_e_aon.c
45
create mode 100644 include/hw/riscv/microchip_pfsoc.h
46
create mode 100644 hw/riscv/microchip_pfsoc.c
47
20
48
diff --git a/default-configs/riscv64-softmmu.mak b/default-configs/riscv64-softmmu.mak
21
diff --git a/include/hw/misc/sifive_e_aon.h b/include/hw/misc/sifive_e_aon.h
49
index XXXXXXX..XXXXXXX 100644
50
--- a/default-configs/riscv64-softmmu.mak
51
+++ b/default-configs/riscv64-softmmu.mak
52
@@ -XXX,XX +XXX,XX @@ CONFIG_SPIKE=y
53
CONFIG_SIFIVE_E=y
54
CONFIG_SIFIVE_U=y
55
CONFIG_RISCV_VIRT=y
56
+CONFIG_MICROCHIP_PFSOC=y
57
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
58
new file mode 100644
22
new file mode 100644
59
index XXXXXXX..XXXXXXX
23
index XXXXXXX..XXXXXXX
60
--- /dev/null
24
--- /dev/null
61
+++ b/include/hw/riscv/microchip_pfsoc.h
25
+++ b/include/hw/misc/sifive_e_aon.h
62
@@ -XXX,XX +XXX,XX @@
26
@@ -XXX,XX +XXX,XX @@
63
+/*
27
+/*
64
+ * Microchip PolarFire SoC machine interface
28
+ * SiFive HiFive1 AON (Always On Domain) interface.
65
+ *
29
+ *
66
+ * Copyright (c) 2020 Wind River Systems, Inc.
30
+ * Copyright (c) 2022 SiFive, Inc. All rights reserved.
67
+ *
68
+ * Author:
69
+ * Bin Meng <bin.meng@windriver.com>
70
+ *
31
+ *
71
+ * This program is free software; you can redistribute it and/or modify it
32
+ * This program is free software; you can redistribute it and/or modify it
72
+ * under the terms and conditions of the GNU General Public License,
33
+ * under the terms and conditions of the GNU General Public License,
73
+ * version 2 or later, as published by the Free Software Foundation.
34
+ * version 2 or later, as published by the Free Software Foundation.
74
+ *
35
+ *
...
...
79
+ *
40
+ *
80
+ * You should have received a copy of the GNU General Public License along with
41
+ * You should have received a copy of the GNU General Public License along with
81
+ * this program. If not, see <http://www.gnu.org/licenses/>.
42
+ * this program. If not, see <http://www.gnu.org/licenses/>.
82
+ */
43
+ */
83
+
44
+
84
+#ifndef HW_MICROCHIP_PFSOC_H
45
+#ifndef HW_SIFIVE_AON_H
85
+#define HW_MICROCHIP_PFSOC_H
46
+#define HW_SIFIVE_AON_H
86
+
47
+
87
+typedef struct MicrochipPFSoCState {
48
+#include "hw/sysbus.h"
49
+#include "qom/object.h"
50
+
51
+#define TYPE_SIFIVE_E_AON "riscv.sifive.e.aon"
52
+OBJECT_DECLARE_SIMPLE_TYPE(SiFiveEAONState, SIFIVE_E_AON)
53
+
54
+#define SIFIVE_E_AON_WDOGKEY (0x51F15E)
55
+#define SIFIVE_E_AON_WDOGFEED (0xD09F00D)
56
+#define SIFIVE_E_LFCLK_DEFAULT_FREQ (32768)
57
+
58
+enum {
59
+ SIFIVE_E_AON_WDT = 0x0,
60
+ SIFIVE_E_AON_RTC = 0x40,
61
+ SIFIVE_E_AON_LFROSC = 0x70,
62
+ SIFIVE_E_AON_BACKUP = 0x80,
63
+ SIFIVE_E_AON_PMU = 0x100,
64
+ SIFIVE_E_AON_MAX = 0x150
65
+};
66
+
67
+struct SiFiveEAONState {
88
+ /*< private >*/
68
+ /*< private >*/
89
+ DeviceState parent_obj;
69
+ SysBusDevice parent_obj;
90
+
70
+
91
+ /*< public >*/
71
+ /*< public >*/
92
+ CPUClusterState e_cluster;
72
+ MemoryRegion mmio;
93
+ CPUClusterState u_cluster;
73
+
94
+ RISCVHartArrayState e_cpus;
74
+ /*< watchdog timer >*/
95
+ RISCVHartArrayState u_cpus;
75
+ QEMUTimer *wdog_timer;
96
+ DeviceState *plic;
76
+ qemu_irq wdog_irq;
97
+} MicrochipPFSoCState;
77
+ uint64_t wdog_restart_time;
98
+
78
+ uint64_t wdogclk_freq;
99
+#define TYPE_MICROCHIP_PFSOC "microchip.pfsoc"
79
+
100
+#define MICROCHIP_PFSOC(obj) \
80
+ uint32_t wdogcfg;
101
+ OBJECT_CHECK(MicrochipPFSoCState, (obj), TYPE_MICROCHIP_PFSOC)
81
+ uint16_t wdogcmp0;
102
+
82
+ uint32_t wdogcount;
103
+typedef struct MicrochipIcicleKitState {
83
+ uint8_t wdogunlock;
104
+ /*< private >*/
105
+ MachineState parent_obj;
106
+
107
+ /*< public >*/
108
+ MicrochipPFSoCState soc;
109
+} MicrochipIcicleKitState;
110
+
111
+#define TYPE_MICROCHIP_ICICLE_KIT_MACHINE \
112
+ MACHINE_TYPE_NAME("microchip-icicle-kit")
113
+#define MICROCHIP_ICICLE_KIT_MACHINE(obj) \
114
+ OBJECT_CHECK(MicrochipIcicleKitState, (obj), \
115
+ TYPE_MICROCHIP_ICICLE_KIT_MACHINE)
116
+
117
+enum {
118
+ MICROCHIP_PFSOC_DEBUG,
119
+ MICROCHIP_PFSOC_E51_DTIM,
120
+ MICROCHIP_PFSOC_BUSERR_UNIT0,
121
+ MICROCHIP_PFSOC_BUSERR_UNIT1,
122
+ MICROCHIP_PFSOC_BUSERR_UNIT2,
123
+ MICROCHIP_PFSOC_BUSERR_UNIT3,
124
+ MICROCHIP_PFSOC_BUSERR_UNIT4,
125
+ MICROCHIP_PFSOC_CLINT,
126
+ MICROCHIP_PFSOC_L2CC,
127
+ MICROCHIP_PFSOC_L2LIM,
128
+ MICROCHIP_PFSOC_PLIC,
129
+ MICROCHIP_PFSOC_SYSREG,
130
+ MICROCHIP_PFSOC_MPUCFG,
131
+ MICROCHIP_PFSOC_ENVM_CFG,
132
+ MICROCHIP_PFSOC_ENVM_DATA,
133
+ MICROCHIP_PFSOC_IOSCB_CFG,
134
+ MICROCHIP_PFSOC_DRAM,
135
+};
84
+};
136
+
85
+
137
+#define MICROCHIP_PFSOC_MANAGEMENT_CPU_COUNT 1
86
+#endif
138
+#define MICROCHIP_PFSOC_COMPUTE_CPU_COUNT 4
87
diff --git a/hw/misc/sifive_e_aon.c b/hw/misc/sifive_e_aon.c
139
+
140
+#define MICROCHIP_PFSOC_PLIC_HART_CONFIG "MS"
141
+#define MICROCHIP_PFSOC_PLIC_NUM_SOURCES 185
142
+#define MICROCHIP_PFSOC_PLIC_NUM_PRIORITIES 7
143
+#define MICROCHIP_PFSOC_PLIC_PRIORITY_BASE 0x04
144
+#define MICROCHIP_PFSOC_PLIC_PENDING_BASE 0x1000
145
+#define MICROCHIP_PFSOC_PLIC_ENABLE_BASE 0x2000
146
+#define MICROCHIP_PFSOC_PLIC_ENABLE_STRIDE 0x80
147
+#define MICROCHIP_PFSOC_PLIC_CONTEXT_BASE 0x200000
148
+#define MICROCHIP_PFSOC_PLIC_CONTEXT_STRIDE 0x1000
149
+
150
+#endif /* HW_MICROCHIP_PFSOC_H */
151
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
152
new file mode 100644
88
new file mode 100644
153
index XXXXXXX..XXXXXXX
89
index XXXXXXX..XXXXXXX
154
--- /dev/null
90
--- /dev/null
155
+++ b/hw/riscv/microchip_pfsoc.c
91
+++ b/hw/misc/sifive_e_aon.c
156
@@ -XXX,XX +XXX,XX @@
92
@@ -XXX,XX +XXX,XX @@
157
+/*
93
+/*
158
+ * QEMU RISC-V Board Compatible with Microchip PolarFire SoC Icicle Kit
94
+ * SiFive HiFive1 AON (Always On Domain) for QEMU.
159
+ *
95
+ *
160
+ * Copyright (c) 2020 Wind River Systems, Inc.
96
+ * Copyright (c) 2022 SiFive, Inc. All rights reserved.
161
+ *
162
+ * Author:
163
+ * Bin Meng <bin.meng@windriver.com>
164
+ *
165
+ * Provides a board compatible with the Microchip PolarFire SoC Icicle Kit
166
+ *
167
+ * 0) CLINT (Core Level Interruptor)
168
+ * 1) PLIC (Platform Level Interrupt Controller)
169
+ * 2) eNVM (Embedded Non-Volatile Memory)
170
+ *
171
+ * This board currently generates devicetree dynamically that indicates at least
172
+ * two harts and up to five harts.
173
+ *
97
+ *
174
+ * This program is free software; you can redistribute it and/or modify it
98
+ * This program is free software; you can redistribute it and/or modify it
175
+ * under the terms and conditions of the GNU General Public License,
99
+ * under the terms and conditions of the GNU General Public License,
176
+ * version 2 or later, as published by the Free Software Foundation.
100
+ * version 2 or later, as published by the Free Software Foundation.
177
+ *
101
+ *
...
...
183
+ * You should have received a copy of the GNU General Public License along with
107
+ * You should have received a copy of the GNU General Public License along with
184
+ * this program. If not, see <http://www.gnu.org/licenses/>.
108
+ * this program. If not, see <http://www.gnu.org/licenses/>.
185
+ */
109
+ */
186
+
110
+
187
+#include "qemu/osdep.h"
111
+#include "qemu/osdep.h"
188
+#include "qemu/error-report.h"
112
+#include "qemu/timer.h"
189
+#include "qemu/log.h"
113
+#include "qemu/log.h"
190
+#include "qemu/units.h"
114
+#include "hw/irq.h"
191
+#include "qemu/cutils.h"
115
+#include "hw/registerfields.h"
116
+#include "hw/misc/sifive_e_aon.h"
117
+#include "qapi/visitor.h"
192
+#include "qapi/error.h"
118
+#include "qapi/error.h"
193
+#include "hw/boards.h"
119
+#include "sysemu/watchdog.h"
194
+#include "hw/irq.h"
120
+#include "hw/qdev-properties.h"
195
+#include "hw/loader.h"
121
+
196
+#include "hw/sysbus.h"
122
+REG32(AON_WDT_WDOGCFG, 0x0)
197
+#include "hw/cpu/cluster.h"
123
+ FIELD(AON_WDT_WDOGCFG, SCALE, 0, 4)
198
+#include "target/riscv/cpu.h"
124
+ FIELD(AON_WDT_WDOGCFG, RSVD0, 4, 4)
199
+#include "hw/misc/unimp.h"
125
+ FIELD(AON_WDT_WDOGCFG, RSTEN, 8, 1)
200
+#include "hw/riscv/boot.h"
126
+ FIELD(AON_WDT_WDOGCFG, ZEROCMP, 9, 1)
201
+#include "hw/riscv/riscv_hart.h"
127
+ FIELD(AON_WDT_WDOGCFG, RSVD1, 10, 2)
202
+#include "hw/riscv/sifive_clint.h"
128
+ FIELD(AON_WDT_WDOGCFG, EN_ALWAYS, 12, 1)
203
+#include "hw/riscv/sifive_plic.h"
129
+ FIELD(AON_WDT_WDOGCFG, EN_CORE_AWAKE, 13, 1)
204
+#include "hw/riscv/microchip_pfsoc.h"
130
+ FIELD(AON_WDT_WDOGCFG, RSVD2, 14, 14)
131
+ FIELD(AON_WDT_WDOGCFG, IP0, 28, 1)
132
+ FIELD(AON_WDT_WDOGCFG, RSVD3, 29, 3)
133
+REG32(AON_WDT_WDOGCOUNT, 0x8)
134
+ FIELD(AON_WDT_WDOGCOUNT, VALUE, 0, 31)
135
+REG32(AON_WDT_WDOGS, 0x10)
136
+REG32(AON_WDT_WDOGFEED, 0x18)
137
+REG32(AON_WDT_WDOGKEY, 0x1c)
138
+REG32(AON_WDT_WDOGCMP0, 0x20)
139
+
140
+static void sifive_e_aon_wdt_update_wdogcount(SiFiveEAONState *r)
141
+{
142
+ int64_t now;
143
+ if (FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, EN_ALWAYS) == 0 &&
144
+ FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE) == 0) {
145
+ return;
146
+ }
147
+
148
+ now = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
149
+ r->wdogcount += muldiv64(now - r->wdog_restart_time,
150
+ r->wdogclk_freq, NANOSECONDS_PER_SECOND);
151
+
152
+ /* Clean the most significant bit. */
153
+ r->wdogcount &= R_AON_WDT_WDOGCOUNT_VALUE_MASK;
154
+ r->wdog_restart_time = now;
155
+}
156
+
157
+static void sifive_e_aon_wdt_update_state(SiFiveEAONState *r)
158
+{
159
+ uint16_t wdogs;
160
+ bool cmp_signal = false;
161
+ sifive_e_aon_wdt_update_wdogcount(r);
162
+ wdogs = (uint16_t)(r->wdogcount >>
163
+ FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, SCALE));
164
+
165
+ if (wdogs >= r->wdogcmp0) {
166
+ cmp_signal = true;
167
+ if (FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, ZEROCMP) == 1) {
168
+ r->wdogcount = 0;
169
+ wdogs = 0;
170
+ }
171
+ }
172
+
173
+ if (cmp_signal) {
174
+ if (FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, RSTEN) == 1) {
175
+ watchdog_perform_action();
176
+ }
177
+ r->wdogcfg = FIELD_DP32(r->wdogcfg, AON_WDT_WDOGCFG, IP0, 1);
178
+ }
179
+
180
+ qemu_set_irq(r->wdog_irq, FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, IP0));
181
+
182
+ if (wdogs < r->wdogcmp0 &&
183
+ (FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, EN_ALWAYS) == 1 ||
184
+ FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE) == 1)) {
185
+ int64_t next = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
186
+ next += muldiv64((r->wdogcmp0 - wdogs) <<
187
+ FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, SCALE),
188
+ NANOSECONDS_PER_SECOND, r->wdogclk_freq);
189
+ timer_mod(r->wdog_timer, next);
190
+ } else {
191
+ timer_mod(r->wdog_timer, INT64_MAX);
192
+ }
193
+}
205
+
194
+
206
+/*
195
+/*
207
+ * The BIOS image used by this machine is called Hart Software Services (HSS).
196
+ * Callback used when the timer set using timer_mod expires.
208
+ * See https://github.com/polarfire-soc/hart-software-services
209
+ */
197
+ */
210
+#define BIOS_FILENAME "hss.bin"
198
+static void sifive_e_aon_wdt_expired_cb(void *opaque)
211
+#define RESET_VECTOR 0x20220000
199
+{
212
+
200
+ SiFiveEAONState *r = SIFIVE_E_AON(opaque);
213
+static const struct MemmapEntry {
201
+ sifive_e_aon_wdt_update_state(r);
214
+ hwaddr base;
202
+}
215
+ hwaddr size;
203
+
216
+} microchip_pfsoc_memmap[] = {
204
+static uint64_t
217
+ [MICROCHIP_PFSOC_DEBUG] = { 0x0, 0x1000 },
205
+sifive_e_aon_wdt_read(void *opaque, hwaddr addr, unsigned int size)
218
+ [MICROCHIP_PFSOC_E51_DTIM] = { 0x1000000, 0x2000 },
206
+{
219
+ [MICROCHIP_PFSOC_BUSERR_UNIT0] = { 0x1700000, 0x1000 },
207
+ SiFiveEAONState *r = SIFIVE_E_AON(opaque);
220
+ [MICROCHIP_PFSOC_BUSERR_UNIT1] = { 0x1701000, 0x1000 },
208
+
221
+ [MICROCHIP_PFSOC_BUSERR_UNIT2] = { 0x1702000, 0x1000 },
209
+ switch (addr) {
222
+ [MICROCHIP_PFSOC_BUSERR_UNIT3] = { 0x1703000, 0x1000 },
210
+ case A_AON_WDT_WDOGCFG:
223
+ [MICROCHIP_PFSOC_BUSERR_UNIT4] = { 0x1704000, 0x1000 },
211
+ return r->wdogcfg;
224
+ [MICROCHIP_PFSOC_CLINT] = { 0x2000000, 0x10000 },
212
+ case A_AON_WDT_WDOGCOUNT:
225
+ [MICROCHIP_PFSOC_L2CC] = { 0x2010000, 0x1000 },
213
+ sifive_e_aon_wdt_update_wdogcount(r);
226
+ [MICROCHIP_PFSOC_L2LIM] = { 0x8000000, 0x2000000 },
214
+ return r->wdogcount;
227
+ [MICROCHIP_PFSOC_PLIC] = { 0xc000000, 0x4000000 },
215
+ case A_AON_WDT_WDOGS:
228
+ [MICROCHIP_PFSOC_SYSREG] = { 0x20002000, 0x2000 },
216
+ sifive_e_aon_wdt_update_wdogcount(r);
229
+ [MICROCHIP_PFSOC_MPUCFG] = { 0x20005000, 0x1000 },
217
+ return r->wdogcount >>
230
+ [MICROCHIP_PFSOC_ENVM_CFG] = { 0x20200000, 0x1000 },
218
+ FIELD_EX32(r->wdogcfg,
231
+ [MICROCHIP_PFSOC_ENVM_DATA] = { 0x20220000, 0x20000 },
219
+ AON_WDT_WDOGCFG,
232
+ [MICROCHIP_PFSOC_IOSCB_CFG] = { 0x37080000, 0x1000 },
220
+ SCALE);
233
+ [MICROCHIP_PFSOC_DRAM] = { 0x80000000, 0x0 },
221
+ case A_AON_WDT_WDOGFEED:
222
+ return 0;
223
+ case A_AON_WDT_WDOGKEY:
224
+ return r->wdogunlock;
225
+ case A_AON_WDT_WDOGCMP0:
226
+ return r->wdogcmp0;
227
+ default:
228
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: bad read: addr=0x%x\n",
229
+ __func__, (int)addr);
230
+ }
231
+
232
+ return 0;
233
+}
234
+
235
+static void
236
+sifive_e_aon_wdt_write(void *opaque, hwaddr addr,
237
+ uint64_t val64, unsigned int size)
238
+{
239
+ SiFiveEAONState *r = SIFIVE_E_AON(opaque);
240
+ uint32_t value = val64;
241
+
242
+ switch (addr) {
243
+ case A_AON_WDT_WDOGCFG: {
244
+ uint8_t new_en_always;
245
+ uint8_t new_en_core_awake;
246
+ uint8_t old_en_always;
247
+ uint8_t old_en_core_awake;
248
+ if (r->wdogunlock == 0) {
249
+ return;
250
+ }
251
+
252
+ new_en_always = FIELD_EX32(value, AON_WDT_WDOGCFG, EN_ALWAYS);
253
+ new_en_core_awake = FIELD_EX32(value, AON_WDT_WDOGCFG, EN_CORE_AWAKE);
254
+ old_en_always = FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG, EN_ALWAYS);
255
+ old_en_core_awake = FIELD_EX32(r->wdogcfg, AON_WDT_WDOGCFG,
256
+ EN_CORE_AWAKE);
257
+
258
+ if ((old_en_always ||
259
+ old_en_core_awake) == 1 &&
260
+ (new_en_always ||
261
+ new_en_core_awake) == 0) {
262
+ sifive_e_aon_wdt_update_wdogcount(r);
263
+ } else if ((old_en_always ||
264
+ old_en_core_awake) == 0 &&
265
+ (new_en_always ||
266
+ new_en_core_awake) == 1) {
267
+ r->wdog_restart_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
268
+ }
269
+ r->wdogcfg = value;
270
+ r->wdogunlock = 0;
271
+ break;
272
+ }
273
+ case A_AON_WDT_WDOGCOUNT:
274
+ if (r->wdogunlock == 0) {
275
+ return;
276
+ }
277
+ r->wdogcount = value & R_AON_WDT_WDOGCOUNT_VALUE_MASK;
278
+ r->wdog_restart_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
279
+ r->wdogunlock = 0;
280
+ break;
281
+ case A_AON_WDT_WDOGS:
282
+ return;
283
+ case A_AON_WDT_WDOGFEED:
284
+ if (r->wdogunlock == 0) {
285
+ return;
286
+ }
287
+ if (value == SIFIVE_E_AON_WDOGFEED) {
288
+ r->wdogcount = 0;
289
+ r->wdog_restart_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
290
+ }
291
+ r->wdogunlock = 0;
292
+ break;
293
+ case A_AON_WDT_WDOGKEY:
294
+ if (value == SIFIVE_E_AON_WDOGKEY) {
295
+ r->wdogunlock = 1;
296
+ }
297
+ break;
298
+ case A_AON_WDT_WDOGCMP0:
299
+ if (r->wdogunlock == 0) {
300
+ return;
301
+ }
302
+ r->wdogcmp0 = (uint16_t) value;
303
+ r->wdogunlock = 0;
304
+ break;
305
+ default:
306
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: bad write: addr=0x%x v=0x%x\n",
307
+ __func__, (int)addr, (int)value);
308
+ }
309
+ sifive_e_aon_wdt_update_state(r);
310
+}
311
+
312
+static uint64_t
313
+sifive_e_aon_read(void *opaque, hwaddr addr, unsigned int size)
314
+{
315
+ if (addr < SIFIVE_E_AON_RTC) {
316
+ return sifive_e_aon_wdt_read(opaque, addr, size);
317
+ } else if (addr < SIFIVE_E_AON_MAX) {
318
+ qemu_log_mask(LOG_UNIMP, "%s: Unimplemented read: addr=0x%x\n",
319
+ __func__, (int)addr);
320
+ } else {
321
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: bad read: addr=0x%x\n",
322
+ __func__, (int)addr);
323
+ }
324
+ return 0;
325
+}
326
+
327
+static void
328
+sifive_e_aon_write(void *opaque, hwaddr addr,
329
+ uint64_t val64, unsigned int size)
330
+{
331
+ if (addr < SIFIVE_E_AON_RTC) {
332
+ sifive_e_aon_wdt_write(opaque, addr, val64, size);
333
+ } else if (addr < SIFIVE_E_AON_MAX) {
334
+ qemu_log_mask(LOG_UNIMP, "%s: Unimplemented write: addr=0x%x\n",
335
+ __func__, (int)addr);
336
+ } else {
337
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: bad write: addr=0x%x\n",
338
+ __func__, (int)addr);
339
+ }
340
+}
341
+
342
+static const MemoryRegionOps sifive_e_aon_ops = {
343
+ .read = sifive_e_aon_read,
344
+ .write = sifive_e_aon_write,
345
+ .endianness = DEVICE_NATIVE_ENDIAN,
346
+ .impl = {
347
+ .min_access_size = 4,
348
+ .max_access_size = 4
349
+ },
350
+ .valid = {
351
+ .min_access_size = 4,
352
+ .max_access_size = 4
353
+ }
234
+};
354
+};
235
+
355
+
236
+static void microchip_pfsoc_soc_instance_init(Object *obj)
356
+static void sifive_e_aon_reset(DeviceState *dev)
237
+{
357
+{
238
+ MachineState *ms = MACHINE(qdev_get_machine());
358
+ SiFiveEAONState *r = SIFIVE_E_AON(dev);
239
+ MicrochipPFSoCState *s = MICROCHIP_PFSOC(obj);
359
+
240
+
360
+ r->wdogcfg = FIELD_DP32(r->wdogcfg, AON_WDT_WDOGCFG, RSTEN, 0);
241
+ object_initialize_child(obj, "e-cluster", &s->e_cluster, TYPE_CPU_CLUSTER);
361
+ r->wdogcfg = FIELD_DP32(r->wdogcfg, AON_WDT_WDOGCFG, EN_ALWAYS, 0);
242
+ qdev_prop_set_uint32(DEVICE(&s->e_cluster), "cluster-id", 0);
362
+ r->wdogcfg = FIELD_DP32(r->wdogcfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE, 0);
243
+
363
+ r->wdogcmp0 = 0xbeef;
244
+ object_initialize_child(OBJECT(&s->e_cluster), "e-cpus", &s->e_cpus,
364
+
245
+ TYPE_RISCV_HART_ARRAY);
365
+ sifive_e_aon_wdt_update_state(r);
246
+ qdev_prop_set_uint32(DEVICE(&s->e_cpus), "num-harts", 1);
366
+}
247
+ qdev_prop_set_uint32(DEVICE(&s->e_cpus), "hartid-base", 0);
367
+
248
+ qdev_prop_set_string(DEVICE(&s->e_cpus), "cpu-type",
368
+static void sifive_e_aon_init(Object *obj)
249
+ TYPE_RISCV_CPU_SIFIVE_E51);
369
+{
250
+ qdev_prop_set_uint64(DEVICE(&s->e_cpus), "resetvec", RESET_VECTOR);
370
+ SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
251
+
371
+ SiFiveEAONState *r = SIFIVE_E_AON(obj);
252
+ object_initialize_child(obj, "u-cluster", &s->u_cluster, TYPE_CPU_CLUSTER);
372
+
253
+ qdev_prop_set_uint32(DEVICE(&s->u_cluster), "cluster-id", 1);
373
+ memory_region_init_io(&r->mmio, OBJECT(r), &sifive_e_aon_ops, r,
254
+
374
+ TYPE_SIFIVE_E_AON, SIFIVE_E_AON_MAX);
255
+ object_initialize_child(OBJECT(&s->u_cluster), "u-cpus", &s->u_cpus,
375
+ sysbus_init_mmio(sbd, &r->mmio);
256
+ TYPE_RISCV_HART_ARRAY);
376
+
257
+ qdev_prop_set_uint32(DEVICE(&s->u_cpus), "num-harts", ms->smp.cpus - 1);
377
+ /* watchdog timer */
258
+ qdev_prop_set_uint32(DEVICE(&s->u_cpus), "hartid-base", 1);
378
+ r->wdog_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
259
+ qdev_prop_set_string(DEVICE(&s->u_cpus), "cpu-type",
379
+ sifive_e_aon_wdt_expired_cb, r);
260
+ TYPE_RISCV_CPU_SIFIVE_U54);
380
+ r->wdogclk_freq = SIFIVE_E_LFCLK_DEFAULT_FREQ;
261
+ qdev_prop_set_uint64(DEVICE(&s->u_cpus), "resetvec", RESET_VECTOR);
381
+ sysbus_init_irq(sbd, &r->wdog_irq);
262
+}
382
+}
263
+
383
+
264
+static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
384
+static Property sifive_e_aon_properties[] = {
265
+{
385
+ DEFINE_PROP_UINT64("wdogclk-frequency", SiFiveEAONState, wdogclk_freq,
266
+ MachineState *ms = MACHINE(qdev_get_machine());
386
+ SIFIVE_E_LFCLK_DEFAULT_FREQ),
267
+ MicrochipPFSoCState *s = MICROCHIP_PFSOC(dev);
387
+ DEFINE_PROP_END_OF_LIST(),
268
+ const struct MemmapEntry *memmap = microchip_pfsoc_memmap;
388
+};
269
+ MemoryRegion *system_memory = get_system_memory();
389
+
270
+ MemoryRegion *e51_dtim_mem = g_new(MemoryRegion, 1);
390
+static void sifive_e_aon_class_init(ObjectClass *oc, void *data)
271
+ MemoryRegion *l2lim_mem = g_new(MemoryRegion, 1);
272
+ MemoryRegion *envm_data = g_new(MemoryRegion, 1);
273
+ char *plic_hart_config;
274
+ size_t plic_hart_config_len;
275
+ int i;
276
+
277
+ sysbus_realize(SYS_BUS_DEVICE(&s->e_cpus), &error_abort);
278
+ sysbus_realize(SYS_BUS_DEVICE(&s->u_cpus), &error_abort);
279
+ /*
280
+ * The cluster must be realized after the RISC-V hart array container,
281
+ * as the container's CPU object is only created on realize, and the
282
+ * CPU must exist and have been parented into the cluster before the
283
+ * cluster is realized.
284
+ */
285
+ qdev_realize(DEVICE(&s->e_cluster), NULL, &error_abort);
286
+ qdev_realize(DEVICE(&s->u_cluster), NULL, &error_abort);
287
+
288
+ /* E51 DTIM */
289
+ memory_region_init_ram(e51_dtim_mem, NULL, "microchip.pfsoc.e51_dtim_mem",
290
+ memmap[MICROCHIP_PFSOC_E51_DTIM].size, &error_fatal);
291
+ memory_region_add_subregion(system_memory,
292
+ memmap[MICROCHIP_PFSOC_E51_DTIM].base,
293
+ e51_dtim_mem);
294
+
295
+ /* Bus Error Units */
296
+ create_unimplemented_device("microchip.pfsoc.buserr_unit0_mem",
297
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT0].base,
298
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT0].size);
299
+ create_unimplemented_device("microchip.pfsoc.buserr_unit1_mem",
300
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT1].base,
301
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT1].size);
302
+ create_unimplemented_device("microchip.pfsoc.buserr_unit2_mem",
303
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT2].base,
304
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT2].size);
305
+ create_unimplemented_device("microchip.pfsoc.buserr_unit3_mem",
306
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT3].base,
307
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT3].size);
308
+ create_unimplemented_device("microchip.pfsoc.buserr_unit4_mem",
309
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT4].base,
310
+ memmap[MICROCHIP_PFSOC_BUSERR_UNIT4].size);
311
+
312
+ /* CLINT */
313
+ sifive_clint_create(memmap[MICROCHIP_PFSOC_CLINT].base,
314
+ memmap[MICROCHIP_PFSOC_CLINT].size, 0, ms->smp.cpus,
315
+ SIFIVE_SIP_BASE, SIFIVE_TIMECMP_BASE, SIFIVE_TIME_BASE, false);
316
+
317
+ /* L2 cache controller */
318
+ create_unimplemented_device("microchip.pfsoc.l2cc",
319
+ memmap[MICROCHIP_PFSOC_L2CC].base, memmap[MICROCHIP_PFSOC_L2CC].size);
320
+
321
+ /*
322
+ * Add L2-LIM at reset size.
323
+ * This should be reduced in size as the L2 Cache Controller WayEnable
324
+ * register is incremented. Unfortunately I don't see a nice (or any) way
325
+ * to handle reducing or blocking out the L2 LIM while still allowing it
326
+ * be re returned to all enabled after a reset. For the time being, just
327
+ * leave it enabled all the time. This won't break anything, but will be
328
+ * too generous to misbehaving guests.
329
+ */
330
+ memory_region_init_ram(l2lim_mem, NULL, "microchip.pfsoc.l2lim",
331
+ memmap[MICROCHIP_PFSOC_L2LIM].size, &error_fatal);
332
+ memory_region_add_subregion(system_memory,
333
+ memmap[MICROCHIP_PFSOC_L2LIM].base,
334
+ l2lim_mem);
335
+
336
+ /* create PLIC hart topology configuration string */
337
+ plic_hart_config_len = (strlen(MICROCHIP_PFSOC_PLIC_HART_CONFIG) + 1) *
338
+ ms->smp.cpus;
339
+ plic_hart_config = g_malloc0(plic_hart_config_len);
340
+ for (i = 0; i < ms->smp.cpus; i++) {
341
+ if (i != 0) {
342
+ strncat(plic_hart_config, "," MICROCHIP_PFSOC_PLIC_HART_CONFIG,
343
+ plic_hart_config_len);
344
+ } else {
345
+ strncat(plic_hart_config, "M", plic_hart_config_len);
346
+ }
347
+ plic_hart_config_len -= (strlen(MICROCHIP_PFSOC_PLIC_HART_CONFIG) + 1);
348
+ }
349
+
350
+ /* PLIC */
351
+ s->plic = sifive_plic_create(memmap[MICROCHIP_PFSOC_PLIC].base,
352
+ plic_hart_config, 0,
353
+ MICROCHIP_PFSOC_PLIC_NUM_SOURCES,
354
+ MICROCHIP_PFSOC_PLIC_NUM_PRIORITIES,
355
+ MICROCHIP_PFSOC_PLIC_PRIORITY_BASE,
356
+ MICROCHIP_PFSOC_PLIC_PENDING_BASE,
357
+ MICROCHIP_PFSOC_PLIC_ENABLE_BASE,
358
+ MICROCHIP_PFSOC_PLIC_ENABLE_STRIDE,
359
+ MICROCHIP_PFSOC_PLIC_CONTEXT_BASE,
360
+ MICROCHIP_PFSOC_PLIC_CONTEXT_STRIDE,
361
+ memmap[MICROCHIP_PFSOC_PLIC].size);
362
+ g_free(plic_hart_config);
363
+
364
+ /* SYSREG */
365
+ create_unimplemented_device("microchip.pfsoc.sysreg",
366
+ memmap[MICROCHIP_PFSOC_SYSREG].base,
367
+ memmap[MICROCHIP_PFSOC_SYSREG].size);
368
+
369
+ /* MPUCFG */
370
+ create_unimplemented_device("microchip.pfsoc.mpucfg",
371
+ memmap[MICROCHIP_PFSOC_MPUCFG].base,
372
+ memmap[MICROCHIP_PFSOC_MPUCFG].size);
373
+
374
+ /* eNVM */
375
+ memory_region_init_rom(envm_data, OBJECT(dev), "microchip.pfsoc.envm.data",
376
+ memmap[MICROCHIP_PFSOC_ENVM_DATA].size,
377
+ &error_fatal);
378
+ memory_region_add_subregion(system_memory,
379
+ memmap[MICROCHIP_PFSOC_ENVM_DATA].base,
380
+ envm_data);
381
+
382
+ /* IOSCBCFG */
383
+ create_unimplemented_device("microchip.pfsoc.ioscb.cfg",
384
+ memmap[MICROCHIP_PFSOC_IOSCB_CFG].base,
385
+ memmap[MICROCHIP_PFSOC_IOSCB_CFG].size);
386
+}
387
+
388
+static void microchip_pfsoc_soc_class_init(ObjectClass *oc, void *data)
389
+{
391
+{
390
+ DeviceClass *dc = DEVICE_CLASS(oc);
392
+ DeviceClass *dc = DEVICE_CLASS(oc);
391
+
393
+
392
+ dc->realize = microchip_pfsoc_soc_realize;
394
+ dc->reset = sifive_e_aon_reset;
393
+ /* Reason: Uses serial_hds in realize function, thus can't be used twice */
395
+ device_class_set_props(dc, sifive_e_aon_properties);
394
+ dc->user_creatable = false;
396
+}
395
+}
397
+
396
+
398
+static const TypeInfo sifive_e_aon_info = {
397
+static const TypeInfo microchip_pfsoc_soc_type_info = {
399
+ .name = TYPE_SIFIVE_E_AON,
398
+ .name = TYPE_MICROCHIP_PFSOC,
400
+ .parent = TYPE_SYS_BUS_DEVICE,
399
+ .parent = TYPE_DEVICE,
401
+ .instance_size = sizeof(SiFiveEAONState),
400
+ .instance_size = sizeof(MicrochipPFSoCState),
402
+ .instance_init = sifive_e_aon_init,
401
+ .instance_init = microchip_pfsoc_soc_instance_init,
403
+ .class_init = sifive_e_aon_class_init,
402
+ .class_init = microchip_pfsoc_soc_class_init,
403
+};
404
+};
404
+
405
+
405
+static void microchip_pfsoc_soc_register_types(void)
406
+static void sifive_e_aon_register_types(void)
406
+{
407
+{
407
+ type_register_static(&microchip_pfsoc_soc_type_info);
408
+ type_register_static(&sifive_e_aon_info);
408
+}
409
+}
409
+
410
+
410
+type_init(microchip_pfsoc_soc_register_types)
411
+type_init(sifive_e_aon_register_types)
411
+
412
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
412
+static void microchip_icicle_kit_machine_init(MachineState *machine)
413
+{
414
+ MachineClass *mc = MACHINE_GET_CLASS(machine);
415
+ const struct MemmapEntry *memmap = microchip_pfsoc_memmap;
416
+ MicrochipIcicleKitState *s = MICROCHIP_ICICLE_KIT_MACHINE(machine);
417
+ MemoryRegion *system_memory = get_system_memory();
418
+ MemoryRegion *main_mem = g_new(MemoryRegion, 1);
419
+
420
+ /* Sanity check on RAM size */
421
+ if (machine->ram_size < mc->default_ram_size) {
422
+ char *sz = size_to_str(mc->default_ram_size);
423
+ error_report("Invalid RAM size, should be bigger than %s", sz);
424
+ g_free(sz);
425
+ exit(EXIT_FAILURE);
426
+ }
427
+
428
+ /* Initialize SoC */
429
+ object_initialize_child(OBJECT(machine), "soc", &s->soc,
430
+ TYPE_MICROCHIP_PFSOC);
431
+ qdev_realize(DEVICE(&s->soc), NULL, &error_abort);
432
+
433
+ /* Register RAM */
434
+ memory_region_init_ram(main_mem, NULL, "microchip.icicle.kit.ram",
435
+ machine->ram_size, &error_fatal);
436
+ memory_region_add_subregion(system_memory,
437
+ memmap[MICROCHIP_PFSOC_DRAM].base, main_mem);
438
+
439
+ /* Load the firmware */
440
+ riscv_find_and_load_firmware(machine, BIOS_FILENAME, RESET_VECTOR, NULL);
441
+}
442
+
443
+static void microchip_icicle_kit_machine_class_init(ObjectClass *oc, void *data)
444
+{
445
+ MachineClass *mc = MACHINE_CLASS(oc);
446
+
447
+ mc->desc = "Microchip PolarFire SoC Icicle Kit";
448
+ mc->init = microchip_icicle_kit_machine_init;
449
+ mc->max_cpus = MICROCHIP_PFSOC_MANAGEMENT_CPU_COUNT +
450
+ MICROCHIP_PFSOC_COMPUTE_CPU_COUNT;
451
+ mc->min_cpus = MICROCHIP_PFSOC_MANAGEMENT_CPU_COUNT + 1;
452
+ mc->default_cpus = mc->min_cpus;
453
+ mc->default_ram_size = 1 * GiB;
454
+}
455
+
456
+static const TypeInfo microchip_icicle_kit_machine_typeinfo = {
457
+ .name = MACHINE_TYPE_NAME("microchip-icicle-kit"),
458
+ .parent = TYPE_MACHINE,
459
+ .class_init = microchip_icicle_kit_machine_class_init,
460
+ .instance_size = sizeof(MicrochipIcicleKitState),
461
+};
462
+
463
+static void microchip_icicle_kit_machine_init_register_types(void)
464
+{
465
+ type_register_static(&microchip_icicle_kit_machine_typeinfo);
466
+}
467
+
468
+type_init(microchip_icicle_kit_machine_init_register_types)
469
diff --git a/MAINTAINERS b/MAINTAINERS
470
index XXXXXXX..XXXXXXX 100644
413
index XXXXXXX..XXXXXXX 100644
471
--- a/MAINTAINERS
414
--- a/hw/misc/Kconfig
472
+++ b/MAINTAINERS
415
+++ b/hw/misc/Kconfig
473
@@ -XXX,XX +XXX,XX @@ F: include/hw/riscv/opentitan.h
416
@@ -XXX,XX +XXX,XX @@ config SIFIVE_TEST
474
F: include/hw/char/ibex_uart.h
417
config SIFIVE_E_PRCI
475
F: include/hw/intc/ibex_plic.h
418
bool
476
419
477
+Microchip PolarFire SoC Icicle Kit
420
+config SIFIVE_E_AON
478
+M: Bin Meng <bin.meng@windriver.com>
421
+ bool
479
+L: qemu-riscv@nongnu.org
422
+
480
+S: Supported
423
config SIFIVE_U_OTP
481
+F: hw/riscv/microchip_pfsoc.c
424
bool
482
+F: include/hw/riscv/microchip_pfsoc.h
425
483
+
426
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
484
RX Machines
485
-----------
486
rx-gdbsim
487
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
488
index XXXXXXX..XXXXXXX 100644
427
index XXXXXXX..XXXXXXX 100644
489
--- a/hw/riscv/Kconfig
428
--- a/hw/misc/meson.build
490
+++ b/hw/riscv/Kconfig
429
+++ b/hw/misc/meson.build
491
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
430
@@ -XXX,XX +XXX,XX @@ system_ss.add(when: 'CONFIG_MCHP_PFSOC_IOSCB', if_true: files('mchp_pfsoc_ioscb.
492
select PCI_EXPRESS_GENERIC_BRIDGE
431
system_ss.add(when: 'CONFIG_MCHP_PFSOC_SYSREG', if_true: files('mchp_pfsoc_sysreg.c'))
493
select PFLASH_CFI01
432
system_ss.add(when: 'CONFIG_SIFIVE_TEST', if_true: files('sifive_test.c'))
494
select SIFIVE
433
system_ss.add(when: 'CONFIG_SIFIVE_E_PRCI', if_true: files('sifive_e_prci.c'))
495
+
434
+system_ss.add(when: 'CONFIG_SIFIVE_E_AON', if_true: files('sifive_e_aon.c'))
496
+config MICROCHIP_PFSOC
435
system_ss.add(when: 'CONFIG_SIFIVE_U_OTP', if_true: files('sifive_u_otp.c'))
497
+ bool
436
system_ss.add(when: 'CONFIG_SIFIVE_U_PRCI', if_true: files('sifive_u_prci.c'))
498
+ select HART
437
499
+ select SIFIVE
500
+ select UNIMP
501
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
502
index XXXXXXX..XXXXXXX 100644
503
--- a/hw/riscv/meson.build
504
+++ b/hw/riscv/meson.build
505
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_otp.c'))
506
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_prci.c'))
507
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('riscv_htif.c'))
508
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
509
+riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c'))
510
511
hw_arch += {'riscv': riscv_ss}
512
--
438
--
513
2.28.0
439
2.40.1
514
515
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Tommy Wu <tommy.wu@sifive.com>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
Create the AON device when we realize the sifive_e machine.
4
should only contain the RISC-V SoC / machine codes plus generic
4
This patch only implemented the functionality of the watchdog timer,
5
codes. Let's move sifive_uart model to hw/char directory.
5
not all the functionality of the AON device.
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
Signed-off-by: Tommy Wu <tommy.wu@sifive.com>
8
Reviewed-by: Frank Chang <frank.chang@sifive.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-9-git-send-email-bmeng.cn@gmail.com>
10
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
11
Message-Id: <20230627141216.3962299-3-tommy.wu@sifive.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
13
---
12
include/hw/{riscv => char}/sifive_uart.h | 0
14
include/hw/riscv/sifive_e.h | 9 ++++++---
13
hw/{riscv => char}/sifive_uart.c | 2 +-
15
hw/riscv/sifive_e.c | 17 +++++++++++++++--
14
hw/riscv/sifive_e.c | 2 +-
16
hw/riscv/Kconfig | 1 +
15
hw/riscv/sifive_u.c | 2 +-
17
3 files changed, 22 insertions(+), 5 deletions(-)
16
hw/char/Kconfig | 3 +++
17
hw/char/meson.build | 1 +
18
hw/riscv/Kconfig | 2 ++
19
hw/riscv/meson.build | 1 -
20
8 files changed, 9 insertions(+), 4 deletions(-)
21
rename include/hw/{riscv => char}/sifive_uart.h (100%)
22
rename hw/{riscv => char}/sifive_uart.c (99%)
23
18
24
diff --git a/include/hw/riscv/sifive_uart.h b/include/hw/char/sifive_uart.h
19
diff --git a/include/hw/riscv/sifive_e.h b/include/hw/riscv/sifive_e.h
25
similarity index 100%
26
rename from include/hw/riscv/sifive_uart.h
27
rename to include/hw/char/sifive_uart.h
28
diff --git a/hw/riscv/sifive_uart.c b/hw/char/sifive_uart.c
29
similarity index 99%
30
rename from hw/riscv/sifive_uart.c
31
rename to hw/char/sifive_uart.c
32
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
33
--- a/hw/riscv/sifive_uart.c
21
--- a/include/hw/riscv/sifive_e.h
34
+++ b/hw/char/sifive_uart.c
22
+++ b/include/hw/riscv/sifive_e.h
35
@@ -XXX,XX +XXX,XX @@
23
@@ -XXX,XX +XXX,XX @@
36
#include "chardev/char-fe.h"
24
#include "hw/riscv/riscv_hart.h"
37
#include "hw/hw.h"
25
#include "hw/riscv/sifive_cpu.h"
38
#include "hw/irq.h"
26
#include "hw/gpio/sifive_gpio.h"
39
-#include "hw/riscv/sifive_uart.h"
27
+#include "hw/misc/sifive_e_aon.h"
40
+#include "hw/char/sifive_uart.h"
28
#include "hw/boards.h"
41
29
42
/*
30
#define TYPE_RISCV_E_SOC "riscv.sifive.e.soc"
43
* Not yet implemented:
31
@@ -XXX,XX +XXX,XX @@ typedef struct SiFiveESoCState {
32
/*< public >*/
33
RISCVHartArrayState cpus;
34
DeviceState *plic;
35
+ SiFiveEAONState aon;
36
SIFIVEGPIOState gpio;
37
MemoryRegion xip_mem;
38
MemoryRegion mask_rom;
39
@@ -XXX,XX +XXX,XX @@ enum {
40
};
41
42
enum {
43
- SIFIVE_E_UART0_IRQ = 3,
44
- SIFIVE_E_UART1_IRQ = 4,
45
- SIFIVE_E_GPIO0_IRQ0 = 8
46
+ SIFIVE_E_AON_WDT_IRQ = 1,
47
+ SIFIVE_E_UART0_IRQ = 3,
48
+ SIFIVE_E_UART1_IRQ = 4,
49
+ SIFIVE_E_GPIO0_IRQ0 = 8
50
};
51
52
#define SIFIVE_E_PLIC_HART_CONFIG "M"
44
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
53
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
45
index XXXXXXX..XXXXXXX 100644
54
index XXXXXXX..XXXXXXX 100644
46
--- a/hw/riscv/sifive_e.c
55
--- a/hw/riscv/sifive_e.c
47
+++ b/hw/riscv/sifive_e.c
56
+++ b/hw/riscv/sifive_e.c
48
@@ -XXX,XX +XXX,XX @@
57
@@ -XXX,XX +XXX,XX @@
49
#include "hw/misc/unimp.h"
58
#include "hw/intc/riscv_aclint.h"
50
#include "target/riscv/cpu.h"
51
#include "hw/riscv/riscv_hart.h"
52
-#include "hw/riscv/sifive_uart.h"
53
#include "hw/riscv/sifive_e.h"
54
#include "hw/riscv/boot.h"
55
+#include "hw/char/sifive_uart.h"
56
#include "hw/intc/sifive_clint.h"
57
#include "hw/intc/sifive_plic.h"
59
#include "hw/intc/sifive_plic.h"
58
#include "hw/misc/sifive_e_prci.h"
60
#include "hw/misc/sifive_e_prci.h"
59
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
61
+#include "hw/misc/sifive_e_aon.h"
60
index XXXXXXX..XXXXXXX 100644
61
--- a/hw/riscv/sifive_u.c
62
+++ b/hw/riscv/sifive_u.c
63
@@ -XXX,XX +XXX,XX @@
64
#include "hw/misc/unimp.h"
65
#include "target/riscv/cpu.h"
66
#include "hw/riscv/riscv_hart.h"
67
-#include "hw/riscv/sifive_uart.h"
68
#include "hw/riscv/sifive_u.h"
69
#include "hw/riscv/boot.h"
70
+#include "hw/char/sifive_uart.h"
71
#include "hw/intc/sifive_clint.h"
72
#include "hw/intc/sifive_plic.h"
73
#include "chardev/char.h"
62
#include "chardev/char.h"
74
diff --git a/hw/char/Kconfig b/hw/char/Kconfig
63
#include "sysemu/sysemu.h"
75
index XXXXXXX..XXXXXXX 100644
64
76
--- a/hw/char/Kconfig
65
@@ -XXX,XX +XXX,XX @@ static void sifive_e_soc_init(Object *obj)
77
+++ b/hw/char/Kconfig
66
object_property_set_int(OBJECT(&s->cpus), "resetvec", 0x1004, &error_abort);
78
@@ -XXX,XX +XXX,XX @@ config AVR_USART
67
object_initialize_child(obj, "riscv.sifive.e.gpio0", &s->gpio,
79
68
TYPE_SIFIVE_GPIO);
80
config MCHP_PFSOC_MMUART
69
+ object_initialize_child(obj, "riscv.sifive.e.aon", &s->aon,
81
bool
70
+ TYPE_SIFIVE_E_AON);
71
}
72
73
static void sifive_e_soc_realize(DeviceState *dev, Error **errp)
74
@@ -XXX,XX +XXX,XX @@ static void sifive_e_soc_realize(DeviceState *dev, Error **errp)
75
RISCV_ACLINT_DEFAULT_MTIMER_SIZE, 0, ms->smp.cpus,
76
RISCV_ACLINT_DEFAULT_MTIMECMP, RISCV_ACLINT_DEFAULT_MTIME,
77
RISCV_ACLINT_DEFAULT_TIMEBASE_FREQ, false);
78
- create_unimplemented_device("riscv.sifive.e.aon",
79
- memmap[SIFIVE_E_DEV_AON].base, memmap[SIFIVE_E_DEV_AON].size);
80
sifive_e_prci_create(memmap[SIFIVE_E_DEV_PRCI].base);
81
82
+ /* AON */
82
+
83
+
83
+config SIFIVE_UART
84
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->aon), errp)) {
84
+ bool
85
+ return;
85
diff --git a/hw/char/meson.build b/hw/char/meson.build
86
+ }
86
index XXXXXXX..XXXXXXX 100644
87
+
87
--- a/hw/char/meson.build
88
+ /* Map AON registers */
88
+++ b/hw/char/meson.build
89
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->aon), 0, memmap[SIFIVE_E_DEV_AON].base);
89
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_EXYNOS4', if_true: files('exynos4210_uart.c'))
90
+
90
softmmu_ss.add(when: 'CONFIG_OMAP', if_true: files('omap_uart.c'))
91
/* GPIO */
91
softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_aux.c'))
92
92
softmmu_ss.add(when: 'CONFIG_RENESAS_SCI', if_true: files('renesas_sci.c'))
93
if (!sysbus_realize(SYS_BUS_DEVICE(&s->gpio), errp)) {
93
+softmmu_ss.add(when: 'CONFIG_SIFIVE_UART', if_true: files('sifive_uart.c'))
94
@@ -XXX,XX +XXX,XX @@ static void sifive_e_soc_realize(DeviceState *dev, Error **errp)
94
softmmu_ss.add(when: 'CONFIG_SH4', if_true: files('sh_serial.c'))
95
qdev_get_gpio_in(DEVICE(s->plic),
95
softmmu_ss.add(when: 'CONFIG_STM32F2XX_USART', if_true: files('stm32f2xx_usart.c'))
96
SIFIVE_E_GPIO0_IRQ0 + i));
96
softmmu_ss.add(when: 'CONFIG_MCHP_PFSOC_MMUART', if_true: files('mchp_pfsoc_mmuart.c'))
97
}
98
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->aon), 0,
99
+ qdev_get_gpio_in(DEVICE(s->plic),
100
+ SIFIVE_E_AON_WDT_IRQ));
101
102
sifive_uart_create(sys_mem, memmap[SIFIVE_E_DEV_UART0].base,
103
serial_hd(0), qdev_get_gpio_in(DEVICE(s->plic), SIFIVE_E_UART0_IRQ));
97
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
104
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
98
index XXXXXXX..XXXXXXX 100644
105
index XXXXXXX..XXXXXXX 100644
99
--- a/hw/riscv/Kconfig
106
--- a/hw/riscv/Kconfig
100
+++ b/hw/riscv/Kconfig
107
+++ b/hw/riscv/Kconfig
101
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
108
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
102
select SIFIVE_CLINT
103
select SIFIVE_GPIO
104
select SIFIVE_PLIC
109
select SIFIVE_PLIC
105
+ select SIFIVE_UART
110
select SIFIVE_UART
106
select SIFIVE_E_PRCI
111
select SIFIVE_E_PRCI
112
+ select SIFIVE_E_AON
107
select UNIMP
113
select UNIMP
108
114
109
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
115
config SIFIVE_U
110
select SIFIVE_GPIO
111
select SIFIVE_PDMA
112
select SIFIVE_PLIC
113
+ select SIFIVE_UART
114
select SIFIVE_U_OTP
115
select SIFIVE_U_PRCI
116
select UNIMP
117
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
118
index XXXXXXX..XXXXXXX 100644
119
--- a/hw/riscv/meson.build
120
+++ b/hw/riscv/meson.build
121
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
122
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
123
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
124
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
125
-riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
126
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
127
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
128
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
129
--
116
--
130
2.28.0
117
2.40.1
131
118
132
119
diff view generated by jsdifflib
New patch
1
From: Tommy Wu <tommy.wu@sifive.com>
1
2
3
Add some simple tests of the watchdog timer in the always-on domain device
4
of HiFive 1 rev b.
5
6
Signed-off-by: Tommy Wu <tommy.wu@sifive.com>
7
Reviewed-by: Frank Chang <frank.chang@sifive.com>
8
Acked-by: Thomas Huth <thuth@redhat.com>
9
Acked-by: Alistair Francis <alistair.francis@wdc.com>
10
Message-Id: <20230627141216.3962299-4-tommy.wu@sifive.com>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
12
---
13
tests/qtest/sifive-e-aon-watchdog-test.c | 450 +++++++++++++++++++++++
14
tests/qtest/meson.build | 3 +
15
2 files changed, 453 insertions(+)
16
create mode 100644 tests/qtest/sifive-e-aon-watchdog-test.c
17
18
diff --git a/tests/qtest/sifive-e-aon-watchdog-test.c b/tests/qtest/sifive-e-aon-watchdog-test.c
19
new file mode 100644
20
index XXXXXXX..XXXXXXX
21
--- /dev/null
22
+++ b/tests/qtest/sifive-e-aon-watchdog-test.c
23
@@ -XXX,XX +XXX,XX @@
24
+/*
25
+ * QTest testcase for the watchdog timer of HiFive 1 rev b.
26
+ *
27
+ * Copyright (c) 2023 SiFive, Inc.
28
+ *
29
+ * This program is free software; you can redistribute it and/or modify it
30
+ * under the terms and conditions of the GNU General Public License,
31
+ * version 2 or later, as published by the Free Software Foundation.
32
+ *
33
+ * This program is distributed in the hope it will be useful, but WITHOUT
34
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
35
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
36
+ * more details.
37
+ *
38
+ * You should have received a copy of the GNU General Public License along with
39
+ * this program. If not, see <http://www.gnu.org/licenses/>.
40
+ */
41
+
42
+#include "qemu/osdep.h"
43
+#include "qemu/timer.h"
44
+#include "qemu/bitops.h"
45
+#include "libqtest.h"
46
+#include "hw/registerfields.h"
47
+#include "hw/misc/sifive_e_aon.h"
48
+
49
+FIELD(AON_WDT_WDOGCFG, SCALE, 0, 4)
50
+FIELD(AON_WDT_WDOGCFG, RSVD0, 4, 4)
51
+FIELD(AON_WDT_WDOGCFG, RSTEN, 8, 1)
52
+FIELD(AON_WDT_WDOGCFG, ZEROCMP, 9, 1)
53
+FIELD(AON_WDT_WDOGCFG, RSVD1, 10, 2)
54
+FIELD(AON_WDT_WDOGCFG, EN_ALWAYS, 12, 1)
55
+FIELD(AON_WDT_WDOGCFG, EN_CORE_AWAKE, 13, 1)
56
+FIELD(AON_WDT_WDOGCFG, RSVD2, 14, 14)
57
+FIELD(AON_WDT_WDOGCFG, IP0, 28, 1)
58
+FIELD(AON_WDT_WDOGCFG, RSVD3, 29, 3)
59
+
60
+#define WDOG_BASE (0x10000000)
61
+#define WDOGCFG (0x0)
62
+#define WDOGCOUNT (0x8)
63
+#define WDOGS (0x10)
64
+#define WDOGFEED (0x18)
65
+#define WDOGKEY (0x1c)
66
+#define WDOGCMP0 (0x20)
67
+
68
+#define SIFIVE_E_AON_WDOGKEY (0x51F15E)
69
+#define SIFIVE_E_AON_WDOGFEED (0xD09F00D)
70
+#define SIFIVE_E_LFCLK_DEFAULT_FREQ (32768)
71
+
72
+static void test_init(QTestState *qts)
73
+{
74
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
75
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0);
76
+
77
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
78
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, 0);
79
+
80
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
81
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, 0xBEEF);
82
+}
83
+
84
+static void test_wdogcount(void)
85
+{
86
+ uint64_t tmp;
87
+ QTestState *qts = qtest_init("-machine sifive_e");
88
+
89
+ test_init(qts);
90
+
91
+ tmp = qtest_readl(qts, WDOG_BASE + WDOGCOUNT);
92
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0xBEEF);
93
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) == tmp);
94
+
95
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
96
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0xBEEF);
97
+ g_assert(0xBEEF == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
98
+
99
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
100
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0xAAAAAAAA);
101
+ g_assert(0x2AAAAAAA == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
102
+
103
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
104
+ qtest_writel(qts, WDOG_BASE + WDOGFEED, 0xAAAAAAAA);
105
+ g_assert(0x2AAAAAAA == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
106
+
107
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
108
+ qtest_writel(qts, WDOG_BASE + WDOGFEED, SIFIVE_E_AON_WDOGFEED);
109
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
110
+
111
+ qtest_quit(qts);
112
+}
113
+
114
+static void test_wdogcfg(void)
115
+{
116
+ uint32_t tmp_cfg;
117
+ QTestState *qts = qtest_init("-machine sifive_e");
118
+
119
+ test_init(qts);
120
+
121
+ tmp_cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
122
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, 0xFFFFFFFF);
123
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCFG) == tmp_cfg);
124
+
125
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
126
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, 0xFFFFFFFF);
127
+ g_assert(0xFFFFFFFF == qtest_readl(qts, WDOG_BASE + WDOGCFG));
128
+
129
+ tmp_cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
130
+ g_assert(15 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, SCALE));
131
+ g_assert(1 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, RSTEN));
132
+ g_assert(1 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, ZEROCMP));
133
+ g_assert(1 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
134
+ g_assert(1 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
135
+ g_assert(1 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, IP0));
136
+
137
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
138
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, 0);
139
+ tmp_cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
140
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, SCALE));
141
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, RSTEN));
142
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, ZEROCMP));
143
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
144
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
145
+ g_assert(0 == FIELD_EX32(tmp_cfg, AON_WDT_WDOGCFG, IP0));
146
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGCFG));
147
+
148
+ qtest_quit(qts);
149
+}
150
+
151
+static void test_wdogcmp0(void)
152
+{
153
+ uint32_t tmp;
154
+ QTestState *qts = qtest_init("-machine sifive_e");
155
+
156
+ test_init(qts);
157
+
158
+ tmp = qtest_readl(qts, WDOG_BASE + WDOGCMP0);
159
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, 0xBEEF);
160
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCMP0) == tmp);
161
+
162
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
163
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, 0xBEEF);
164
+ g_assert(0xBEEF == qtest_readl(qts, WDOG_BASE + WDOGCMP0));
165
+
166
+ qtest_quit(qts);
167
+}
168
+
169
+static void test_wdogkey(void)
170
+{
171
+ QTestState *qts = qtest_init("-machine sifive_e");
172
+
173
+ test_init(qts);
174
+
175
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGKEY));
176
+
177
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, 0xFFFF);
178
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGKEY));
179
+
180
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
181
+ g_assert(1 == qtest_readl(qts, WDOG_BASE + WDOGKEY));
182
+
183
+ qtest_writel(qts, WDOG_BASE + WDOGFEED, 0xAAAAAAAA);
184
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGKEY));
185
+
186
+ qtest_quit(qts);
187
+}
188
+
189
+static void test_wdogfeed(void)
190
+{
191
+ QTestState *qts = qtest_init("-machine sifive_e");
192
+
193
+ test_init(qts);
194
+
195
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGFEED));
196
+
197
+ qtest_writel(qts, WDOG_BASE + WDOGFEED, 0xFFFF);
198
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGFEED));
199
+
200
+ qtest_quit(qts);
201
+}
202
+
203
+static void test_scaled_wdogs(void)
204
+{
205
+ uint32_t cfg;
206
+ uint32_t fake_count = 0x12345678;
207
+ QTestState *qts = qtest_init("-machine sifive_e");
208
+
209
+ test_init(qts);
210
+
211
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
212
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, fake_count);
213
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) == fake_count);
214
+ g_assert((uint16_t)qtest_readl(qts, WDOG_BASE + WDOGS) ==
215
+ (uint16_t)fake_count);
216
+
217
+ for (int i = 0; i < 16; i++) {
218
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
219
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, SCALE, i);
220
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
221
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
222
+ g_assert((uint16_t)qtest_readl(qts, WDOG_BASE + WDOGS) ==
223
+ (uint16_t)(fake_count >>
224
+ FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE)));
225
+ }
226
+
227
+ qtest_quit(qts);
228
+}
229
+
230
+static void test_watchdog(void)
231
+{
232
+ uint32_t cfg;
233
+ QTestState *qts = qtest_init("-machine sifive_e");
234
+
235
+ test_init(qts);
236
+
237
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
238
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, SIFIVE_E_LFCLK_DEFAULT_FREQ);
239
+
240
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
241
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, SCALE, 0);
242
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 1);
243
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
244
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
245
+
246
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND);
247
+
248
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) ==
249
+ SIFIVE_E_LFCLK_DEFAULT_FREQ);
250
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGS) ==
251
+ SIFIVE_E_LFCLK_DEFAULT_FREQ);
252
+
253
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
254
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
255
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
256
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
257
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
258
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
259
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
260
+
261
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
262
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0);
263
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, IP0, 0);
264
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
265
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
266
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
267
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
268
+
269
+ qtest_quit(qts);
270
+}
271
+
272
+static void test_scaled_watchdog(void)
273
+{
274
+ uint32_t cfg;
275
+ QTestState *qts = qtest_init("-machine sifive_e");
276
+
277
+ test_init(qts);
278
+
279
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
280
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, 10);
281
+
282
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
283
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, SCALE, 15);
284
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 1);
285
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
286
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
287
+
288
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND * 10);
289
+
290
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) ==
291
+ SIFIVE_E_LFCLK_DEFAULT_FREQ * 10);
292
+
293
+ g_assert(10 == qtest_readl(qts, WDOG_BASE + WDOGS));
294
+
295
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
296
+ g_assert(15 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
297
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
298
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
299
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
300
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
301
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
302
+
303
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
304
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0);
305
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, IP0, 0);
306
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
307
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
308
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
309
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
310
+
311
+ qtest_quit(qts);
312
+}
313
+
314
+static void test_periodic_int(void)
315
+{
316
+ uint32_t cfg;
317
+ QTestState *qts = qtest_init("-machine sifive_e");
318
+
319
+ test_init(qts);
320
+
321
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
322
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, SIFIVE_E_LFCLK_DEFAULT_FREQ);
323
+
324
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
325
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, SCALE, 0);
326
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, ZEROCMP, 1);
327
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 1);
328
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
329
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
330
+
331
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND);
332
+
333
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
334
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGS));
335
+
336
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
337
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
338
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
339
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
340
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
341
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
342
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
343
+
344
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, IP0, 0);
345
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
346
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
347
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
348
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
349
+
350
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND);
351
+
352
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGCOUNT));
353
+ g_assert(0 == qtest_readl(qts, WDOG_BASE + WDOGS));
354
+
355
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
356
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
357
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
358
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
359
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
360
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
361
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
362
+
363
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, IP0, 0);
364
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
365
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
366
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
367
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
368
+
369
+ qtest_quit(qts);
370
+}
371
+
372
+static void test_enable_disable(void)
373
+{
374
+ uint32_t cfg;
375
+ QTestState *qts = qtest_init("-machine sifive_e");
376
+
377
+ test_init(qts);
378
+
379
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
380
+ qtest_writel(qts, WDOG_BASE + WDOGCMP0, 10);
381
+
382
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
383
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, SCALE, 15);
384
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 1);
385
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
386
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
387
+
388
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND * 2);
389
+
390
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) ==
391
+ SIFIVE_E_LFCLK_DEFAULT_FREQ * 2);
392
+ g_assert(2 == qtest_readl(qts, WDOG_BASE + WDOGS));
393
+
394
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
395
+ g_assert(15 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
396
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
397
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
398
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
399
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
400
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
401
+
402
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
403
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 0);
404
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
405
+
406
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND * 8);
407
+
408
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) ==
409
+ SIFIVE_E_LFCLK_DEFAULT_FREQ * 2);
410
+ g_assert(2 == qtest_readl(qts, WDOG_BASE + WDOGS));
411
+
412
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
413
+ g_assert(15 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
414
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
415
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
416
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
417
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
418
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
419
+
420
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS, 1);
421
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
422
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
423
+
424
+ qtest_clock_step(qts, NANOSECONDS_PER_SECOND * 8);
425
+
426
+ g_assert(qtest_readl(qts, WDOG_BASE + WDOGCOUNT) ==
427
+ SIFIVE_E_LFCLK_DEFAULT_FREQ * 10);
428
+ g_assert(10 == qtest_readl(qts, WDOG_BASE + WDOGS));
429
+
430
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
431
+ g_assert(15 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, SCALE));
432
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, RSTEN));
433
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, ZEROCMP));
434
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_ALWAYS));
435
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, EN_CORE_AWAKE));
436
+ g_assert(1 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
437
+
438
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
439
+ qtest_writel(qts, WDOG_BASE + WDOGCOUNT, 0);
440
+ cfg = FIELD_DP32(cfg, AON_WDT_WDOGCFG, IP0, 0);
441
+ qtest_writel(qts, WDOG_BASE + WDOGKEY, SIFIVE_E_AON_WDOGKEY);
442
+ qtest_writel(qts, WDOG_BASE + WDOGCFG, cfg);
443
+ cfg = qtest_readl(qts, WDOG_BASE + WDOGCFG);
444
+ g_assert(0 == FIELD_EX32(cfg, AON_WDT_WDOGCFG, IP0));
445
+
446
+ qtest_quit(qts);
447
+}
448
+
449
+int main(int argc, char *argv[])
450
+{
451
+ g_test_init(&argc, &argv, NULL);
452
+ qtest_add_func("/sifive-e-aon-watchdog-test/wdogcount",
453
+ test_wdogcount);
454
+ qtest_add_func("/sifive-e-aon-watchdog-test/wdogcfg",
455
+ test_wdogcfg);
456
+ qtest_add_func("/sifive-e-aon-watchdog-test/wdogcmp0",
457
+ test_wdogcmp0);
458
+ qtest_add_func("/sifive-e-aon-watchdog-test/wdogkey",
459
+ test_wdogkey);
460
+ qtest_add_func("/sifive-e-aon-watchdog-test/wdogfeed",
461
+ test_wdogfeed);
462
+ qtest_add_func("/sifive-e-aon-watchdog-test/scaled_wdogs",
463
+ test_scaled_wdogs);
464
+ qtest_add_func("/sifive-e-aon-watchdog-test/watchdog",
465
+ test_watchdog);
466
+ qtest_add_func("/sifive-e-aon-watchdog-test/scaled_watchdog",
467
+ test_scaled_watchdog);
468
+ qtest_add_func("/sifive-e-aon-watchdog-test/periodic_int",
469
+ test_periodic_int);
470
+ qtest_add_func("/sifive-e-aon-watchdog-test/enable_disable",
471
+ test_enable_disable);
472
+ return g_test_run();
473
+}
474
diff --git a/tests/qtest/meson.build b/tests/qtest/meson.build
475
index XXXXXXX..XXXXXXX 100644
476
--- a/tests/qtest/meson.build
477
+++ b/tests/qtest/meson.build
478
@@ -XXX,XX +XXX,XX @@ qtests_s390x = \
479
'cpu-plug-test',
480
'migration-test']
481
482
+qtests_riscv32 = \
483
+ (config_all_devices.has_key('CONFIG_SIFIVE_E_AON') ? ['sifive-e-aon-watchdog-test'] : [])
484
+
485
qos_test_ss = ss.source_set()
486
qos_test_ss.add(
487
'ac97-test.c',
488
--
489
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Philippe Mathieu-Daudé <philmd@linaro.org>
2
2
3
Every RISC-V machine needs riscv_hart hence there is no need to
3
We want to keep the ability to distinct between 32/64-bit host.
4
have a dedicated Kconfig option for it. Drop the Kconfig option
5
and always build riscv_hart.c.
6
4
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
5
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-11-git-send-email-bmeng.cn@gmail.com>
8
Message-Id: <20230627143235.29947-2-philmd@linaro.org>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
10
---
12
hw/riscv/Kconfig | 9 ---------
11
meson.build | 11 ++++-------
13
hw/riscv/meson.build | 2 +-
12
1 file changed, 4 insertions(+), 7 deletions(-)
14
2 files changed, 1 insertion(+), 10 deletions(-)
15
13
16
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
14
diff --git a/meson.build b/meson.build
17
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/riscv/Kconfig
16
--- a/meson.build
19
+++ b/hw/riscv/Kconfig
17
+++ b/meson.build
20
@@ -XXX,XX +XXX,XX @@
18
@@ -XXX,XX +XXX,XX @@ qapi_trace_events = []
21
-config HART
19
22
- bool
20
bsd_oses = ['gnu/kfreebsd', 'freebsd', 'netbsd', 'openbsd', 'dragonfly', 'darwin']
21
supported_oses = ['windows', 'freebsd', 'netbsd', 'openbsd', 'darwin', 'sunos', 'linux']
22
-supported_cpus = ['ppc', 'ppc64', 's390x', 'riscv', 'x86', 'x86_64',
23
+supported_cpus = ['ppc', 'ppc64', 's390x', 'riscv32', 'riscv64', 'x86', 'x86_64',
24
'arm', 'aarch64', 'loongarch64', 'mips', 'mips64', 'sparc64']
25
26
cpu = host_machine.cpu_family()
27
28
-# Unify riscv* to a single family.
29
-if cpu in ['riscv32', 'riscv64']
30
- cpu = 'riscv'
31
-endif
23
-
32
-
24
config IBEX
33
target_dirs = config_host['TARGET_DIRS'].split()
25
bool
34
have_linux_user = false
26
35
have_bsd_user = false
27
@@ -XXX,XX +XXX,XX @@ config SIFIVE
36
@@ -XXX,XX +XXX,XX @@ elif cpu == 'x86'
28
37
host_arch = 'i386'
29
config SIFIVE_E
38
elif cpu == 'mips64'
30
bool
39
host_arch = 'mips'
31
- select HART
40
+elif cpu in ['riscv32', 'riscv64']
32
select SIFIVE
41
+ host_arch = 'riscv'
33
select SIFIVE_CLINT
42
else
34
select SIFIVE_GPIO
43
host_arch = cpu
35
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
44
endif
36
config SIFIVE_U
45
@@ -XXX,XX +XXX,XX @@ elif cpu in ['ppc', 'ppc64']
37
bool
46
kvm_targets = ['ppc-softmmu', 'ppc64-softmmu']
38
select CADENCE
47
elif cpu in ['mips', 'mips64']
39
- select HART
48
kvm_targets = ['mips-softmmu', 'mipsel-softmmu', 'mips64-softmmu', 'mips64el-softmmu']
40
select SIFIVE
49
-elif cpu in ['riscv']
41
select SIFIVE_CLINT
50
+elif cpu in ['riscv32', 'riscv64']
42
select SIFIVE_GPIO
51
kvm_targets = ['riscv32-softmmu', 'riscv64-softmmu']
43
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
52
else
44
53
kvm_targets = []
45
config SPIKE
46
bool
47
- select HART
48
select HTIF
49
select SIFIVE
50
select SIFIVE_CLINT
51
@@ -XXX,XX +XXX,XX @@ config SPIKE
52
config OPENTITAN
53
bool
54
select IBEX
55
- select HART
56
select UNIMP
57
58
config RISCV_VIRT
59
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
60
imply PCI_DEVICES
61
imply TEST_DEVICES
62
select PCI
63
- select HART
64
select SERIAL
65
select GOLDFISH_RTC
66
select VIRTIO_MMIO
67
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
68
69
config MICROCHIP_PFSOC
70
bool
71
- select HART
72
select SIFIVE
73
select SIFIVE_CLINT
74
select UNIMP
75
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
76
index XXXXXXX..XXXXXXX 100644
77
--- a/hw/riscv/meson.build
78
+++ b/hw/riscv/meson.build
79
@@ -XXX,XX +XXX,XX @@
80
riscv_ss = ss.source_set()
81
riscv_ss.add(files('boot.c'), fdt)
82
riscv_ss.add(files('numa.c'))
83
-riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
84
+riscv_ss.add(files('riscv_hart.c'))
85
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
86
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
87
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
88
--
54
--
89
2.28.0
55
2.40.1
90
56
91
57
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Philippe Mathieu-Daudé <philmd@linaro.org>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
Per Anup Patel in [*]:
4
should only contain the RISC-V SoC / machine codes plus generic
5
codes. Let's move sifive_gpio model to hw/gpio directory.
6
4
7
Note this also removes the trace-events in the hw/riscv directory,
5
> Currently, we only support running rv64 guest on rv64 host
8
since gpio is the only supported trace target in that directory.
6
> and rv32 guest on rv32 host.
7
>
8
> In the future, we might support running rv32 guest on rv64
9
> host but as of now we don't see a strong push for it.
9
10
10
Signed-off-by: Bin Meng <bin.meng@windriver.com>
11
Therefore, when only using the KVM accelerator it is pointless
12
to build qemu-system-riscv32 on a rv64 host (or qemu-system-riscv64
13
on a rv32 host). Restrict meson to only build the correct binary,
14
avoiding to waste ressources building unusable code.
15
16
[*] https://lore.kernel.org/qemu-devel/CAAhSdy2JeRHeeoEc1XKQhPO3aDz4YKeyQsPT4S8yKJcYTA+AiQ@mail.gmail.com/
17
18
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
19
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
11
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
20
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
12
Message-Id: <1599129623-68957-5-git-send-email-bmeng.cn@gmail.com>
21
Message-Id: <20230627143235.29947-3-philmd@linaro.org>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
22
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
14
---
23
---
15
hw/riscv/trace.h | 1 -
24
meson.build | 6 ++++--
16
include/hw/{riscv => gpio}/sifive_gpio.h | 0
25
1 file changed, 4 insertions(+), 2 deletions(-)
17
include/hw/riscv/sifive_e.h | 2 +-
18
include/hw/riscv/sifive_u.h | 2 +-
19
hw/{riscv => gpio}/sifive_gpio.c | 2 +-
20
hw/gpio/Kconfig | 3 +++
21
hw/gpio/meson.build | 1 +
22
hw/gpio/trace-events | 6 ++++++
23
hw/riscv/Kconfig | 2 ++
24
hw/riscv/meson.build | 1 -
25
hw/riscv/trace-events | 7 -------
26
meson.build | 1 -
27
12 files changed, 15 insertions(+), 13 deletions(-)
28
delete mode 100644 hw/riscv/trace.h
29
rename include/hw/{riscv => gpio}/sifive_gpio.h (100%)
30
rename hw/{riscv => gpio}/sifive_gpio.c (99%)
31
delete mode 100644 hw/riscv/trace-events
32
26
33
diff --git a/hw/riscv/trace.h b/hw/riscv/trace.h
34
deleted file mode 100644
35
index XXXXXXX..XXXXXXX
36
--- a/hw/riscv/trace.h
37
+++ /dev/null
38
@@ -1 +0,0 @@
39
-#include "trace/trace-hw_riscv.h"
40
diff --git a/include/hw/riscv/sifive_gpio.h b/include/hw/gpio/sifive_gpio.h
41
similarity index 100%
42
rename from include/hw/riscv/sifive_gpio.h
43
rename to include/hw/gpio/sifive_gpio.h
44
diff --git a/include/hw/riscv/sifive_e.h b/include/hw/riscv/sifive_e.h
45
index XXXXXXX..XXXXXXX 100644
46
--- a/include/hw/riscv/sifive_e.h
47
+++ b/include/hw/riscv/sifive_e.h
48
@@ -XXX,XX +XXX,XX @@
49
50
#include "hw/riscv/riscv_hart.h"
51
#include "hw/riscv/sifive_cpu.h"
52
-#include "hw/riscv/sifive_gpio.h"
53
+#include "hw/gpio/sifive_gpio.h"
54
55
#define TYPE_RISCV_E_SOC "riscv.sifive.e.soc"
56
#define RISCV_E_SOC(obj) \
57
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
58
index XXXXXXX..XXXXXXX 100644
59
--- a/include/hw/riscv/sifive_u.h
60
+++ b/include/hw/riscv/sifive_u.h
61
@@ -XXX,XX +XXX,XX @@
62
#include "hw/net/cadence_gem.h"
63
#include "hw/riscv/riscv_hart.h"
64
#include "hw/riscv/sifive_cpu.h"
65
-#include "hw/riscv/sifive_gpio.h"
66
+#include "hw/gpio/sifive_gpio.h"
67
#include "hw/misc/sifive_u_otp.h"
68
#include "hw/misc/sifive_u_prci.h"
69
70
diff --git a/hw/riscv/sifive_gpio.c b/hw/gpio/sifive_gpio.c
71
similarity index 99%
72
rename from hw/riscv/sifive_gpio.c
73
rename to hw/gpio/sifive_gpio.c
74
index XXXXXXX..XXXXXXX 100644
75
--- a/hw/riscv/sifive_gpio.c
76
+++ b/hw/gpio/sifive_gpio.c
77
@@ -XXX,XX +XXX,XX @@
78
#include "qemu/log.h"
79
#include "hw/irq.h"
80
#include "hw/qdev-properties.h"
81
-#include "hw/riscv/sifive_gpio.h"
82
+#include "hw/gpio/sifive_gpio.h"
83
#include "migration/vmstate.h"
84
#include "trace.h"
85
86
diff --git a/hw/gpio/Kconfig b/hw/gpio/Kconfig
87
index XXXXXXX..XXXXXXX 100644
88
--- a/hw/gpio/Kconfig
89
+++ b/hw/gpio/Kconfig
90
@@ -XXX,XX +XXX,XX @@ config PL061
91
92
config GPIO_KEY
93
bool
94
+
95
+config SIFIVE_GPIO
96
+ bool
97
diff --git a/hw/gpio/meson.build b/hw/gpio/meson.build
98
index XXXXXXX..XXXXXXX 100644
99
--- a/hw/gpio/meson.build
100
+++ b/hw/gpio/meson.build
101
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_NRF51_SOC', if_true: files('nrf51_gpio.c'))
102
softmmu_ss.add(when: 'CONFIG_OMAP', if_true: files('omap_gpio.c'))
103
softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_gpio.c'))
104
softmmu_ss.add(when: 'CONFIG_ASPEED_SOC', if_true: files('aspeed_gpio.c'))
105
+softmmu_ss.add(when: 'CONFIG_SIFIVE_GPIO', if_true: files('sifive_gpio.c'))
106
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
107
index XXXXXXX..XXXXXXX 100644
108
--- a/hw/gpio/trace-events
109
+++ b/hw/gpio/trace-events
110
@@ -XXX,XX +XXX,XX @@ nrf51_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PR
111
nrf51_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x%" PRIx64
112
nrf51_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
113
nrf51_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
114
+
115
+# sifive_gpio.c
116
+sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
117
+sifive_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x%" PRIx64
118
+sifive_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
119
+sifive_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
120
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
121
index XXXXXXX..XXXXXXX 100644
122
--- a/hw/riscv/Kconfig
123
+++ b/hw/riscv/Kconfig
124
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
125
bool
126
select HART
127
select SIFIVE
128
+ select SIFIVE_GPIO
129
select SIFIVE_E_PRCI
130
select UNIMP
131
132
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
133
select CADENCE
134
select HART
135
select SIFIVE
136
+ select SIFIVE_GPIO
137
select SIFIVE_PDMA
138
select SIFIVE_U_OTP
139
select SIFIVE_U_PRCI
140
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
141
index XXXXXXX..XXXXXXX 100644
142
--- a/hw/riscv/meson.build
143
+++ b/hw/riscv/meson.build
144
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
145
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
146
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
147
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_clint.c'))
148
-riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_gpio.c'))
149
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_plic.c'))
150
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
151
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
152
diff --git a/hw/riscv/trace-events b/hw/riscv/trace-events
153
deleted file mode 100644
154
index XXXXXXX..XXXXXXX
155
--- a/hw/riscv/trace-events
156
+++ /dev/null
157
@@ -XXX,XX +XXX,XX @@
158
-# See docs/devel/tracing.txt for syntax documentation.
159
-
160
-# hw/gpio/sifive_gpio.c
161
-sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
162
-sifive_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x%" PRIx64
163
-sifive_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
164
-sifive_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
165
diff --git a/meson.build b/meson.build
27
diff --git a/meson.build b/meson.build
166
index XXXXXXX..XXXXXXX 100644
28
index XXXXXXX..XXXXXXX 100644
167
--- a/meson.build
29
--- a/meson.build
168
+++ b/meson.build
30
+++ b/meson.build
169
@@ -XXX,XX +XXX,XX @@ if have_system
31
@@ -XXX,XX +XXX,XX @@ elif cpu in ['ppc', 'ppc64']
170
'hw/watchdog',
32
kvm_targets = ['ppc-softmmu', 'ppc64-softmmu']
171
'hw/xen',
33
elif cpu in ['mips', 'mips64']
172
'hw/gpio',
34
kvm_targets = ['mips-softmmu', 'mipsel-softmmu', 'mips64-softmmu', 'mips64el-softmmu']
173
- 'hw/riscv',
35
-elif cpu in ['riscv32', 'riscv64']
174
'migration',
36
- kvm_targets = ['riscv32-softmmu', 'riscv64-softmmu']
175
'net',
37
+elif cpu in ['riscv32']
176
'ui',
38
+ kvm_targets = ['riscv32-softmmu']
39
+elif cpu in ['riscv64']
40
+ kvm_targets = ['riscv64-softmmu']
41
else
42
kvm_targets = []
43
endif
177
--
44
--
178
2.28.0
45
2.40.1
179
46
180
47
diff view generated by jsdifflib
New patch
1
From: Ivan Klokov <ivan.klokov@syntacore.com>
1
2
3
Print RvV extension register to log if VPU option is enabled.
4
5
Signed-off-by: Ivan Klokov <ivan.klokov@syntacore.com>
6
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
Message-Id: <20230629083730.386604-1-ivan.klokov@syntacore.com>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
---
11
target/riscv/cpu.c | 57 +++++++++++++++++++++++++++++++++++++++++++++-
12
1 file changed, 56 insertions(+), 1 deletion(-)
13
14
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/target/riscv/cpu.c
17
+++ b/target/riscv/cpu.c
18
@@ -XXX,XX +XXX,XX @@ struct isa_ext_data {
19
#define ISA_EXT_DATA_ENTRY(_name, _min_ver, _prop) \
20
{#_name, _min_ver, offsetof(struct RISCVCPUConfig, _prop)}
21
22
+/*
23
+ * From vector_helper.c
24
+ * Note that vector data is stored in host-endian 64-bit chunks,
25
+ * so addressing bytes needs a host-endian fixup.
26
+ */
27
+#if HOST_BIG_ENDIAN
28
+#define BYTE(x) ((x) ^ 7)
29
+#else
30
+#define BYTE(x) (x)
31
+#endif
32
+
33
/*
34
* Here are the ordering rules of extension naming defined by RISC-V
35
* specification :
36
@@ -XXX,XX +XXX,XX @@ const char * const riscv_fpr_regnames[] = {
37
"f30/ft10", "f31/ft11"
38
};
39
40
+const char * const riscv_rvv_regnames[] = {
41
+ "v0", "v1", "v2", "v3", "v4", "v5", "v6",
42
+ "v7", "v8", "v9", "v10", "v11", "v12", "v13",
43
+ "v14", "v15", "v16", "v17", "v18", "v19", "v20",
44
+ "v21", "v22", "v23", "v24", "v25", "v26", "v27",
45
+ "v28", "v29", "v30", "v31"
46
+};
47
+
48
static const char * const riscv_excp_names[] = {
49
"misaligned_fetch",
50
"fault_fetch",
51
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
52
{
53
RISCVCPU *cpu = RISCV_CPU(cs);
54
CPURISCVState *env = &cpu->env;
55
- int i;
56
+ int i, j;
57
+ uint8_t *p;
58
59
#if !defined(CONFIG_USER_ONLY)
60
if (riscv_has_ext(env, RVH)) {
61
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
62
}
63
}
64
}
65
+ if (riscv_has_ext(env, RVV) && (flags & CPU_DUMP_VPU)) {
66
+ static const int dump_rvv_csrs[] = {
67
+ CSR_VSTART,
68
+ CSR_VXSAT,
69
+ CSR_VXRM,
70
+ CSR_VCSR,
71
+ CSR_VL,
72
+ CSR_VTYPE,
73
+ CSR_VLENB,
74
+ };
75
+ for (int i = 0; i < ARRAY_SIZE(dump_rvv_csrs); ++i) {
76
+ int csrno = dump_rvv_csrs[i];
77
+ target_ulong val = 0;
78
+ RISCVException res = riscv_csrrw_debug(env, csrno, &val, 0, 0);
79
+
80
+ /*
81
+ * Rely on the smode, hmode, etc, predicates within csr.c
82
+ * to do the filtering of the registers that are present.
83
+ */
84
+ if (res == RISCV_EXCP_NONE) {
85
+ qemu_fprintf(f, " %-8s " TARGET_FMT_lx "\n",
86
+ csr_ops[csrno].name, val);
87
+ }
88
+ }
89
+ uint16_t vlenb = cpu->cfg.vlen >> 3;
90
+
91
+ for (i = 0; i < 32; i++) {
92
+ qemu_fprintf(f, " %-8s ", riscv_rvv_regnames[i]);
93
+ p = (uint8_t *)env->vreg;
94
+ for (j = vlenb - 1 ; j >= 0; j--) {
95
+ qemu_fprintf(f, "%02x", *(p + i * vlenb + BYTE(j)));
96
+ }
97
+ qemu_fprintf(f, "\n");
98
+ }
99
+ }
100
}
101
102
static void riscv_cpu_set_pc(CPUState *cs, vaddr value)
103
--
104
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Philippe Mathieu-Daudé <philmd@linaro.org>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
The Advanced Core Local Interruptor (ACLINT) device can
4
should only contain the RISC-V SoC / machine codes plus generic
4
only be used with TCG. Check for TCG enabled instead of
5
codes. Let's move sifive_test model to hw/misc directory.
5
KVM being not. Only add the property when TCG is used.
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-10-git-send-email-bmeng.cn@gmail.com>
10
Message-Id: <20230629121103.87733-3-philmd@linaro.org>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
12
---
12
include/hw/{riscv => misc}/sifive_test.h | 0
13
docs/system/riscv/virt.rst | 1 +
13
hw/{riscv => misc}/sifive_test.c | 2 +-
14
hw/riscv/virt.c | 18 ++++++++++--------
14
hw/riscv/virt.c | 2 +-
15
2 files changed, 11 insertions(+), 8 deletions(-)
15
hw/misc/Kconfig | 3 +++
16
hw/misc/meson.build | 1 +
17
hw/riscv/Kconfig | 1 +
18
hw/riscv/meson.build | 1 -
19
7 files changed, 7 insertions(+), 3 deletions(-)
20
rename include/hw/{riscv => misc}/sifive_test.h (100%)
21
rename hw/{riscv => misc}/sifive_test.c (98%)
22
16
23
diff --git a/include/hw/riscv/sifive_test.h b/include/hw/misc/sifive_test.h
17
diff --git a/docs/system/riscv/virt.rst b/docs/system/riscv/virt.rst
24
similarity index 100%
25
rename from include/hw/riscv/sifive_test.h
26
rename to include/hw/misc/sifive_test.h
27
diff --git a/hw/riscv/sifive_test.c b/hw/misc/sifive_test.c
28
similarity index 98%
29
rename from hw/riscv/sifive_test.c
30
rename to hw/misc/sifive_test.c
31
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
32
--- a/hw/riscv/sifive_test.c
19
--- a/docs/system/riscv/virt.rst
33
+++ b/hw/misc/sifive_test.c
20
+++ b/docs/system/riscv/virt.rst
34
@@ -XXX,XX +XXX,XX @@
21
@@ -XXX,XX +XXX,XX @@ The following machine-specific options are supported:
35
#include "qemu/module.h"
22
36
#include "sysemu/runstate.h"
23
When this option is "on", ACLINT devices will be emulated instead of
37
#include "hw/hw.h"
24
SiFive CLINT. When not specified, this option is assumed to be "off".
38
-#include "hw/riscv/sifive_test.h"
25
+ This option is restricted to the TCG accelerator.
39
+#include "hw/misc/sifive_test.h"
26
40
27
- aia=[none|aplic|aplic-imsic]
41
static uint64_t sifive_test_read(void *opaque, hwaddr addr, unsigned int size)
28
42
{
43
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
29
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
44
index XXXXXXX..XXXXXXX 100644
30
index XXXXXXX..XXXXXXX 100644
45
--- a/hw/riscv/virt.c
31
--- a/hw/riscv/virt.c
46
+++ b/hw/riscv/virt.c
32
+++ b/hw/riscv/virt.c
47
@@ -XXX,XX +XXX,XX @@
33
@@ -XXX,XX +XXX,XX @@
48
#include "hw/char/serial.h"
49
#include "target/riscv/cpu.h"
50
#include "hw/riscv/riscv_hart.h"
51
-#include "hw/riscv/sifive_test.h"
52
#include "hw/riscv/virt.h"
53
#include "hw/riscv/boot.h"
54
#include "hw/riscv/numa.h"
55
#include "hw/intc/sifive_clint.h"
56
#include "hw/intc/sifive_plic.h"
57
+#include "hw/misc/sifive_test.h"
58
#include "chardev/char.h"
34
#include "chardev/char.h"
59
#include "sysemu/arch_init.h"
60
#include "sysemu/device_tree.h"
35
#include "sysemu/device_tree.h"
61
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
36
#include "sysemu/sysemu.h"
62
index XXXXXXX..XXXXXXX 100644
37
+#include "sysemu/tcg.h"
63
--- a/hw/misc/Kconfig
38
#include "sysemu/kvm.h"
64
+++ b/hw/misc/Kconfig
39
#include "sysemu/tpm.h"
65
@@ -XXX,XX +XXX,XX @@ config MAC_VIA
40
#include "hw/pci/pci.h"
66
config AVR_POWER
41
@@ -XXX,XX +XXX,XX @@ static void create_fdt_sockets(RISCVVirtState *s, const MemMapEntry *memmap,
67
bool
42
68
43
g_free(clust_name);
69
+config SIFIVE_TEST
44
70
+ bool
45
- if (!kvm_enabled()) {
71
+
46
+ if (tcg_enabled()) {
72
config SIFIVE_E_PRCI
47
if (s->have_aclint) {
73
bool
48
create_fdt_socket_aclint(s, memmap, socket,
74
49
&intc_phandles[phandle_pos]);
75
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
50
@@ -XXX,XX +XXX,XX @@ static void virt_machine_init(MachineState *machine)
76
index XXXXXXX..XXXXXXX 100644
51
hart_count, &error_abort);
77
--- a/hw/misc/meson.build
52
sysbus_realize(SYS_BUS_DEVICE(&s->soc[i]), &error_fatal);
78
+++ b/hw/misc/meson.build
53
79
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_ARM11SCU', if_true: files('arm11scu.c'))
54
- if (!kvm_enabled()) {
80
softmmu_ss.add(when: 'CONFIG_MOS6522', if_true: files('mos6522.c'))
55
+ if (tcg_enabled()) {
81
56
if (s->have_aclint) {
82
# RISC-V devices
57
if (s->aia_type == VIRT_AIA_TYPE_APLIC_IMSIC) {
83
+softmmu_ss.add(when: 'CONFIG_SIFIVE_TEST', if_true: files('sifive_test.c'))
58
/* Per-socket ACLINT MTIMER */
84
softmmu_ss.add(when: 'CONFIG_SIFIVE_E_PRCI', if_true: files('sifive_e_prci.c'))
59
@@ -XXX,XX +XXX,XX @@ static void virt_machine_class_init(ObjectClass *oc, void *data)
85
softmmu_ss.add(when: 'CONFIG_SIFIVE_U_OTP', if_true: files('sifive_u_otp.c'))
60
machine_class_allow_dynamic_sysbus_dev(mc, TYPE_TPM_TIS_SYSBUS);
86
softmmu_ss.add(when: 'CONFIG_SIFIVE_U_PRCI', if_true: files('sifive_u_prci.c'))
61
#endif
87
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
62
88
index XXXXXXX..XXXXXXX 100644
63
- object_class_property_add_bool(oc, "aclint", virt_get_aclint,
89
--- a/hw/riscv/Kconfig
64
- virt_set_aclint);
90
+++ b/hw/riscv/Kconfig
65
- object_class_property_set_description(oc, "aclint",
91
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
66
- "Set on/off to enable/disable "
92
select SIFIVE
67
- "emulating ACLINT devices");
93
select SIFIVE_CLINT
68
-
94
select SIFIVE_PLIC
69
+ if (tcg_enabled()) {
95
+ select SIFIVE_TEST
70
+ object_class_property_add_bool(oc, "aclint", virt_get_aclint,
96
71
+ virt_set_aclint);
97
config MICROCHIP_PFSOC
72
+ object_class_property_set_description(oc, "aclint",
98
bool
73
+ "Set on/off to enable/disable "
99
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
74
+ "emulating ACLINT devices");
100
index XXXXXXX..XXXXXXX 100644
75
+ }
101
--- a/hw/riscv/meson.build
76
object_class_property_add_str(oc, "aia", virt_get_aia,
102
+++ b/hw/riscv/meson.build
77
virt_set_aia);
103
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(files('numa.c'))
78
object_class_property_set_description(oc, "aia",
104
riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
105
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
106
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
107
-riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
108
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
109
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
110
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
111
--
79
--
112
2.28.0
80
2.40.1
113
81
114
82
diff view generated by jsdifflib
New patch
1
From: Robbin Ehn <rehn@rivosinc.com>
1
2
3
This patch adds the new syscall for the
4
"RISC-V Hardware Probing Interface"
5
(https://docs.kernel.org/riscv/hwprobe.html).
6
7
Reviewed-by: Palmer Dabbelt <palmer@rivosinc.com>
8
Signed-off-by: Robbin Ehn <rehn@rivosinc.com>
9
Message-Id: <06a4543df2aa6101ca9a48f21a3198064b4f1f87.camel@rivosinc.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
12
linux-user/riscv/syscall32_nr.h | 1 +
13
linux-user/riscv/syscall64_nr.h | 1 +
14
linux-user/syscall.c | 146 ++++++++++++++++++++++++++++++++
15
3 files changed, 148 insertions(+)
16
17
diff --git a/linux-user/riscv/syscall32_nr.h b/linux-user/riscv/syscall32_nr.h
18
index XXXXXXX..XXXXXXX 100644
19
--- a/linux-user/riscv/syscall32_nr.h
20
+++ b/linux-user/riscv/syscall32_nr.h
21
@@ -XXX,XX +XXX,XX @@
22
#define TARGET_NR_accept4 242
23
#define TARGET_NR_arch_specific_syscall 244
24
#define TARGET_NR_riscv_flush_icache (TARGET_NR_arch_specific_syscall + 15)
25
+#define TARGET_NR_riscv_hwprobe (TARGET_NR_arch_specific_syscall + 14)
26
#define TARGET_NR_prlimit64 261
27
#define TARGET_NR_fanotify_init 262
28
#define TARGET_NR_fanotify_mark 263
29
diff --git a/linux-user/riscv/syscall64_nr.h b/linux-user/riscv/syscall64_nr.h
30
index XXXXXXX..XXXXXXX 100644
31
--- a/linux-user/riscv/syscall64_nr.h
32
+++ b/linux-user/riscv/syscall64_nr.h
33
@@ -XXX,XX +XXX,XX @@
34
#define TARGET_NR_recvmmsg 243
35
#define TARGET_NR_arch_specific_syscall 244
36
#define TARGET_NR_riscv_flush_icache (TARGET_NR_arch_specific_syscall + 15)
37
+#define TARGET_NR_riscv_hwprobe (TARGET_NR_arch_specific_syscall + 14)
38
#define TARGET_NR_wait4 260
39
#define TARGET_NR_prlimit64 261
40
#define TARGET_NR_fanotify_init 262
41
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
42
index XXXXXXX..XXXXXXX 100644
43
--- a/linux-user/syscall.c
44
+++ b/linux-user/syscall.c
45
@@ -XXX,XX +XXX,XX @@ static int do_getdents64(abi_long dirfd, abi_long arg2, abi_long count)
46
}
47
#endif /* TARGET_NR_getdents64 */
48
49
+#if defined(TARGET_NR_riscv_hwprobe)
50
+
51
+#define RISCV_HWPROBE_KEY_MVENDORID 0
52
+#define RISCV_HWPROBE_KEY_MARCHID 1
53
+#define RISCV_HWPROBE_KEY_MIMPID 2
54
+
55
+#define RISCV_HWPROBE_KEY_BASE_BEHAVIOR 3
56
+#define RISCV_HWPROBE_BASE_BEHAVIOR_IMA (1 << 0)
57
+
58
+#define RISCV_HWPROBE_KEY_IMA_EXT_0 4
59
+#define RISCV_HWPROBE_IMA_FD (1 << 0)
60
+#define RISCV_HWPROBE_IMA_C (1 << 1)
61
+
62
+#define RISCV_HWPROBE_KEY_CPUPERF_0 5
63
+#define RISCV_HWPROBE_MISALIGNED_UNKNOWN (0 << 0)
64
+#define RISCV_HWPROBE_MISALIGNED_EMULATED (1 << 0)
65
+#define RISCV_HWPROBE_MISALIGNED_SLOW (2 << 0)
66
+#define RISCV_HWPROBE_MISALIGNED_FAST (3 << 0)
67
+#define RISCV_HWPROBE_MISALIGNED_UNSUPPORTED (4 << 0)
68
+#define RISCV_HWPROBE_MISALIGNED_MASK (7 << 0)
69
+
70
+struct riscv_hwprobe {
71
+ abi_llong key;
72
+ abi_ullong value;
73
+};
74
+
75
+static void risc_hwprobe_fill_pairs(CPURISCVState *env,
76
+ struct riscv_hwprobe *pair,
77
+ size_t pair_count)
78
+{
79
+ const RISCVCPUConfig *cfg = riscv_cpu_cfg(env);
80
+
81
+ for (; pair_count > 0; pair_count--, pair++) {
82
+ abi_llong key;
83
+ abi_ullong value;
84
+ __put_user(0, &pair->value);
85
+ __get_user(key, &pair->key);
86
+ switch (key) {
87
+ case RISCV_HWPROBE_KEY_MVENDORID:
88
+ __put_user(cfg->mvendorid, &pair->value);
89
+ break;
90
+ case RISCV_HWPROBE_KEY_MARCHID:
91
+ __put_user(cfg->marchid, &pair->value);
92
+ break;
93
+ case RISCV_HWPROBE_KEY_MIMPID:
94
+ __put_user(cfg->mimpid, &pair->value);
95
+ break;
96
+ case RISCV_HWPROBE_KEY_BASE_BEHAVIOR:
97
+ value = riscv_has_ext(env, RVI) &&
98
+ riscv_has_ext(env, RVM) &&
99
+ riscv_has_ext(env, RVA) ?
100
+ RISCV_HWPROBE_BASE_BEHAVIOR_IMA : 0;
101
+ __put_user(value, &pair->value);
102
+ break;
103
+ case RISCV_HWPROBE_KEY_IMA_EXT_0:
104
+ value = riscv_has_ext(env, RVF) &&
105
+ riscv_has_ext(env, RVD) ?
106
+ RISCV_HWPROBE_IMA_FD : 0;
107
+ value |= riscv_has_ext(env, RVC) ?
108
+ RISCV_HWPROBE_IMA_C : pair->value;
109
+ __put_user(value, &pair->value);
110
+ break;
111
+ case RISCV_HWPROBE_KEY_CPUPERF_0:
112
+ __put_user(RISCV_HWPROBE_MISALIGNED_FAST, &pair->value);
113
+ break;
114
+ default:
115
+ __put_user(-1, &pair->key);
116
+ break;
117
+ }
118
+ }
119
+}
120
+
121
+static int cpu_set_valid(abi_long arg3, abi_long arg4)
122
+{
123
+ int ret, i, tmp;
124
+ size_t host_mask_size, target_mask_size;
125
+ unsigned long *host_mask;
126
+
127
+ /*
128
+ * cpu_set_t represent CPU masks as bit masks of type unsigned long *.
129
+ * arg3 contains the cpu count.
130
+ */
131
+ tmp = (8 * sizeof(abi_ulong));
132
+ target_mask_size = ((arg3 + tmp - 1) / tmp) * sizeof(abi_ulong);
133
+ host_mask_size = (target_mask_size + (sizeof(*host_mask) - 1)) &
134
+ ~(sizeof(*host_mask) - 1);
135
+
136
+ host_mask = alloca(host_mask_size);
137
+
138
+ ret = target_to_host_cpu_mask(host_mask, host_mask_size,
139
+ arg4, target_mask_size);
140
+ if (ret != 0) {
141
+ return ret;
142
+ }
143
+
144
+ for (i = 0 ; i < host_mask_size / sizeof(*host_mask); i++) {
145
+ if (host_mask[i] != 0) {
146
+ return 0;
147
+ }
148
+ }
149
+ return -TARGET_EINVAL;
150
+}
151
+
152
+static abi_long do_riscv_hwprobe(CPUArchState *cpu_env, abi_long arg1,
153
+ abi_long arg2, abi_long arg3,
154
+ abi_long arg4, abi_long arg5)
155
+{
156
+ int ret;
157
+ struct riscv_hwprobe *host_pairs;
158
+
159
+ /* flags must be 0 */
160
+ if (arg5 != 0) {
161
+ return -TARGET_EINVAL;
162
+ }
163
+
164
+ /* check cpu_set */
165
+ if (arg3 != 0) {
166
+ ret = cpu_set_valid(arg3, arg4);
167
+ if (ret != 0) {
168
+ return ret;
169
+ }
170
+ } else if (arg4 != 0) {
171
+ return -TARGET_EINVAL;
172
+ }
173
+
174
+ /* no pairs */
175
+ if (arg2 == 0) {
176
+ return 0;
177
+ }
178
+
179
+ host_pairs = lock_user(VERIFY_WRITE, arg1,
180
+ sizeof(*host_pairs) * (size_t)arg2, 0);
181
+ if (host_pairs == NULL) {
182
+ return -TARGET_EFAULT;
183
+ }
184
+ risc_hwprobe_fill_pairs(cpu_env, host_pairs, arg2);
185
+ unlock_user(host_pairs, arg1, sizeof(*host_pairs) * (size_t)arg2);
186
+ return 0;
187
+}
188
+#endif /* TARGET_NR_riscv_hwprobe */
189
+
190
#if defined(TARGET_NR_pivot_root) && defined(__NR_pivot_root)
191
_syscall2(int, pivot_root, const char *, new_root, const char *, put_old)
192
#endif
193
@@ -XXX,XX +XXX,XX @@ static abi_long do_syscall1(CPUArchState *cpu_env, int num, abi_long arg1,
194
return ret;
195
#endif
196
197
+#if defined(TARGET_NR_riscv_hwprobe)
198
+ case TARGET_NR_riscv_hwprobe:
199
+ return do_riscv_hwprobe(cpu_env, arg1, arg2, arg3, arg4, arg5);
200
+#endif
201
+
202
default:
203
qemu_log_mask(LOG_UNIMP, "Unsupported syscall: %d\n", num);
204
return -TARGET_ENOSYS;
205
--
206
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Add ext_zfbfmin/zvfbfmin/zvfbfwma properties.
4
Add require check for BF16 extensions.
5
6
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
7
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Message-Id: <20230615063302.102409-2-liweiwei@iscas.ac.cn>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
12
target/riscv/cpu_cfg.h | 3 +++
13
target/riscv/cpu.c | 20 ++++++++++++++++++++
14
2 files changed, 23 insertions(+)
15
16
diff --git a/target/riscv/cpu_cfg.h b/target/riscv/cpu_cfg.h
17
index XXXXXXX..XXXXXXX 100644
18
--- a/target/riscv/cpu_cfg.h
19
+++ b/target/riscv/cpu_cfg.h
20
@@ -XXX,XX +XXX,XX @@ struct RISCVCPUConfig {
21
bool ext_svpbmt;
22
bool ext_zdinx;
23
bool ext_zawrs;
24
+ bool ext_zfbfmin;
25
bool ext_zfh;
26
bool ext_zfhmin;
27
bool ext_zfinx;
28
@@ -XXX,XX +XXX,XX @@ struct RISCVCPUConfig {
29
bool ext_zve64f;
30
bool ext_zve64d;
31
bool ext_zmmul;
32
+ bool ext_zvfbfmin;
33
+ bool ext_zvfbfwma;
34
bool ext_zvfh;
35
bool ext_zvfhmin;
36
bool ext_smaia;
37
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
38
index XXXXXXX..XXXXXXX 100644
39
--- a/target/riscv/cpu.c
40
+++ b/target/riscv/cpu.c
41
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_validate_set_extensions(RISCVCPU *cpu, Error **errp)
42
return;
43
}
44
45
+ if (cpu->cfg.ext_zfbfmin && !riscv_has_ext(env, RVF)) {
46
+ error_setg(errp, "Zfbfmin extension depends on F extension");
47
+ return;
48
+ }
49
+
50
if (riscv_has_ext(env, RVD) && !riscv_has_ext(env, RVF)) {
51
error_setg(errp, "D extension requires F extension");
52
return;
53
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_validate_set_extensions(RISCVCPU *cpu, Error **errp)
54
return;
55
}
56
57
+ if (cpu->cfg.ext_zvfbfmin && !cpu->cfg.ext_zfbfmin) {
58
+ error_setg(errp, "Zvfbfmin extension depends on Zfbfmin extension");
59
+ return;
60
+ }
61
+
62
+ if (cpu->cfg.ext_zvfbfmin && !cpu->cfg.ext_zve32f) {
63
+ error_setg(errp, "Zvfbfmin extension depends on Zve32f extension");
64
+ return;
65
+ }
66
+
67
+ if (cpu->cfg.ext_zvfbfwma && !cpu->cfg.ext_zvfbfmin) {
68
+ error_setg(errp, "Zvfbfwma extension depends on Zvfbfmin extension");
69
+ return;
70
+ }
71
+
72
/* Set the ISA extensions, checks should have happened above */
73
if (cpu->cfg.ext_zhinx) {
74
cpu->cfg.ext_zhinxmin = true;
75
--
76
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Add trans_* and helper function for Zfbfmin instructions.
4
5
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
6
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-Id: <20230615063302.102409-3-liweiwei@iscas.ac.cn>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
---
11
target/riscv/helper.h | 4 ++
12
target/riscv/insn32.decode | 4 ++
13
target/riscv/fpu_helper.c | 12 +++++
14
target/riscv/translate.c | 1 +
15
target/riscv/insn_trans/trans_rvbf16.c.inc | 53 ++++++++++++++++++++++
16
target/riscv/insn_trans/trans_rvzfh.c.inc | 12 ++---
17
6 files changed, 80 insertions(+), 6 deletions(-)
18
create mode 100644 target/riscv/insn_trans/trans_rvbf16.c.inc
19
20
diff --git a/target/riscv/helper.h b/target/riscv/helper.h
21
index XXXXXXX..XXXXXXX 100644
22
--- a/target/riscv/helper.h
23
+++ b/target/riscv/helper.h
24
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_3(sm4ks, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
25
26
/* Zce helper */
27
DEF_HELPER_FLAGS_2(cm_jalt, TCG_CALL_NO_WG, tl, env, i32)
28
+
29
+/* BF16 functions */
30
+DEF_HELPER_FLAGS_2(fcvt_bf16_s, TCG_CALL_NO_RWG, i64, env, i64)
31
+DEF_HELPER_FLAGS_2(fcvt_s_bf16, TCG_CALL_NO_RWG, i64, env, i64)
32
diff --git a/target/riscv/insn32.decode b/target/riscv/insn32.decode
33
index XXXXXXX..XXXXXXX 100644
34
--- a/target/riscv/insn32.decode
35
+++ b/target/riscv/insn32.decode
36
@@ -XXX,XX +XXX,XX @@ sm4ks .. 11010 ..... ..... 000 ..... 0110011 @k_aes
37
# *** RV32 Zicond Standard Extension ***
38
czero_eqz 0000111 ..... ..... 101 ..... 0110011 @r
39
czero_nez 0000111 ..... ..... 111 ..... 0110011 @r
40
+
41
+# *** Zfbfmin Standard Extension ***
42
+fcvt_bf16_s 0100010 01000 ..... ... ..... 1010011 @r2_rm
43
+fcvt_s_bf16 0100000 00110 ..... ... ..... 1010011 @r2_rm
44
diff --git a/target/riscv/fpu_helper.c b/target/riscv/fpu_helper.c
45
index XXXXXXX..XXXXXXX 100644
46
--- a/target/riscv/fpu_helper.c
47
+++ b/target/riscv/fpu_helper.c
48
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fcvt_d_h(CPURISCVState *env, uint64_t rs1)
49
float16 frs1 = check_nanbox_h(env, rs1);
50
return float16_to_float64(frs1, true, &env->fp_status);
51
}
52
+
53
+uint64_t helper_fcvt_bf16_s(CPURISCVState *env, uint64_t rs1)
54
+{
55
+ float32 frs1 = check_nanbox_s(env, rs1);
56
+ return nanbox_h(env, float32_to_bfloat16(frs1, &env->fp_status));
57
+}
58
+
59
+uint64_t helper_fcvt_s_bf16(CPURISCVState *env, uint64_t rs1)
60
+{
61
+ float16 frs1 = check_nanbox_h(env, rs1);
62
+ return nanbox_s(env, bfloat16_to_float32(frs1, &env->fp_status));
63
+}
64
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
65
index XXXXXXX..XXXXXXX 100644
66
--- a/target/riscv/translate.c
67
+++ b/target/riscv/translate.c
68
@@ -XXX,XX +XXX,XX @@ static uint32_t opcode_at(DisasContextBase *dcbase, target_ulong pc)
69
#include "insn_trans/trans_rvk.c.inc"
70
#include "insn_trans/trans_privileged.c.inc"
71
#include "insn_trans/trans_svinval.c.inc"
72
+#include "insn_trans/trans_rvbf16.c.inc"
73
#include "decode-xthead.c.inc"
74
#include "insn_trans/trans_xthead.c.inc"
75
#include "insn_trans/trans_xventanacondops.c.inc"
76
diff --git a/target/riscv/insn_trans/trans_rvbf16.c.inc b/target/riscv/insn_trans/trans_rvbf16.c.inc
77
new file mode 100644
78
index XXXXXXX..XXXXXXX
79
--- /dev/null
80
+++ b/target/riscv/insn_trans/trans_rvbf16.c.inc
81
@@ -XXX,XX +XXX,XX @@
82
+/*
83
+ * RISC-V translation routines for the BF16 Standard Extensions.
84
+ *
85
+ * Copyright (c) 2020-2023 PLCT Lab
86
+ *
87
+ * This program is free software; you can redistribute it and/or modify it
88
+ * under the terms and conditions of the GNU General Public License,
89
+ * version 2 or later, as published by the Free Software Foundation.
90
+ *
91
+ * This program is distributed in the hope it will be useful, but WITHOUT
92
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
93
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
94
+ * more details.
95
+ *
96
+ * You should have received a copy of the GNU General Public License along with
97
+ * this program. If not, see <http://www.gnu.org/licenses/>.
98
+ */
99
+
100
+#define REQUIRE_ZFBFMIN(ctx) do { \
101
+ if (!ctx->cfg_ptr->ext_zfbfmin) { \
102
+ return false; \
103
+ } \
104
+} while (0)
105
+
106
+static bool trans_fcvt_bf16_s(DisasContext *ctx, arg_fcvt_bf16_s *a)
107
+{
108
+ REQUIRE_FPU;
109
+ REQUIRE_ZFBFMIN(ctx);
110
+
111
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
112
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
113
+
114
+ gen_set_rm(ctx, a->rm);
115
+ gen_helper_fcvt_bf16_s(dest, cpu_env, src1);
116
+ gen_set_fpr_hs(ctx, a->rd, dest);
117
+ mark_fs_dirty(ctx);
118
+ return true;
119
+}
120
+
121
+static bool trans_fcvt_s_bf16(DisasContext *ctx, arg_fcvt_s_bf16 *a)
122
+{
123
+ REQUIRE_FPU;
124
+ REQUIRE_ZFBFMIN(ctx);
125
+
126
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
127
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
128
+
129
+ gen_set_rm(ctx, a->rm);
130
+ gen_helper_fcvt_s_bf16(dest, cpu_env, src1);
131
+ gen_set_fpr_hs(ctx, a->rd, dest);
132
+ mark_fs_dirty(ctx);
133
+ return true;
134
+}
135
diff --git a/target/riscv/insn_trans/trans_rvzfh.c.inc b/target/riscv/insn_trans/trans_rvzfh.c.inc
136
index XXXXXXX..XXXXXXX 100644
137
--- a/target/riscv/insn_trans/trans_rvzfh.c.inc
138
+++ b/target/riscv/insn_trans/trans_rvzfh.c.inc
139
@@ -XXX,XX +XXX,XX @@
140
} \
141
} while (0)
142
143
-#define REQUIRE_ZFHMIN(ctx) do { \
144
- if (!ctx->cfg_ptr->ext_zfhmin) { \
145
+#define REQUIRE_ZFHMIN_OR_ZFBFMIN(ctx) do { \
146
+ if (!ctx->cfg_ptr->ext_zfhmin && !ctx->cfg_ptr->ext_zfbfmin) { \
147
return false; \
148
} \
149
} while (0)
150
@@ -XXX,XX +XXX,XX @@ static bool trans_flh(DisasContext *ctx, arg_flh *a)
151
TCGv t0;
152
153
REQUIRE_FPU;
154
- REQUIRE_ZFHMIN(ctx);
155
+ REQUIRE_ZFHMIN_OR_ZFBFMIN(ctx);
156
157
decode_save_opc(ctx);
158
t0 = get_gpr(ctx, a->rs1, EXT_NONE);
159
@@ -XXX,XX +XXX,XX @@ static bool trans_fsh(DisasContext *ctx, arg_fsh *a)
160
TCGv t0;
161
162
REQUIRE_FPU;
163
- REQUIRE_ZFHMIN(ctx);
164
+ REQUIRE_ZFHMIN_OR_ZFBFMIN(ctx);
165
166
decode_save_opc(ctx);
167
t0 = get_gpr(ctx, a->rs1, EXT_NONE);
168
@@ -XXX,XX +XXX,XX @@ static bool trans_fcvt_h_wu(DisasContext *ctx, arg_fcvt_h_wu *a)
169
static bool trans_fmv_x_h(DisasContext *ctx, arg_fmv_x_h *a)
170
{
171
REQUIRE_FPU;
172
- REQUIRE_ZFHMIN(ctx);
173
+ REQUIRE_ZFHMIN_OR_ZFBFMIN(ctx);
174
175
TCGv dest = dest_gpr(ctx, a->rd);
176
177
@@ -XXX,XX +XXX,XX @@ static bool trans_fmv_x_h(DisasContext *ctx, arg_fmv_x_h *a)
178
static bool trans_fmv_h_x(DisasContext *ctx, arg_fmv_h_x *a)
179
{
180
REQUIRE_FPU;
181
- REQUIRE_ZFHMIN(ctx);
182
+ REQUIRE_ZFHMIN_OR_ZFBFMIN(ctx);
183
184
TCGv t0 = get_gpr(ctx, a->rs1, EXT_ZERO);
185
186
--
187
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Add trans_* and helper function for Zvfbfmin instructions.
4
5
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
6
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-Id: <20230615063302.102409-4-liweiwei@iscas.ac.cn>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
---
11
target/riscv/helper.h | 3 +
12
target/riscv/insn32.decode | 4 ++
13
target/riscv/vector_helper.c | 6 ++
14
target/riscv/insn_trans/trans_rvbf16.c.inc | 64 ++++++++++++++++++++++
15
4 files changed, 77 insertions(+)
16
17
diff --git a/target/riscv/helper.h b/target/riscv/helper.h
18
index XXXXXXX..XXXXXXX 100644
19
--- a/target/riscv/helper.h
20
+++ b/target/riscv/helper.h
21
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_2(cm_jalt, TCG_CALL_NO_WG, tl, env, i32)
22
/* BF16 functions */
23
DEF_HELPER_FLAGS_2(fcvt_bf16_s, TCG_CALL_NO_RWG, i64, env, i64)
24
DEF_HELPER_FLAGS_2(fcvt_s_bf16, TCG_CALL_NO_RWG, i64, env, i64)
25
+
26
+DEF_HELPER_5(vfncvtbf16_f_f_w, void, ptr, ptr, ptr, env, i32)
27
+DEF_HELPER_5(vfwcvtbf16_f_f_v, void, ptr, ptr, ptr, env, i32)
28
diff --git a/target/riscv/insn32.decode b/target/riscv/insn32.decode
29
index XXXXXXX..XXXXXXX 100644
30
--- a/target/riscv/insn32.decode
31
+++ b/target/riscv/insn32.decode
32
@@ -XXX,XX +XXX,XX @@ czero_nez 0000111 ..... ..... 111 ..... 0110011 @r
33
# *** Zfbfmin Standard Extension ***
34
fcvt_bf16_s 0100010 01000 ..... ... ..... 1010011 @r2_rm
35
fcvt_s_bf16 0100000 00110 ..... ... ..... 1010011 @r2_rm
36
+
37
+# *** Zvfbfmin Standard Extension ***
38
+vfncvtbf16_f_f_w 010010 . ..... 11101 001 ..... 1010111 @r2_vm
39
+vfwcvtbf16_f_f_v 010010 . ..... 01101 001 ..... 1010111 @r2_vm
40
diff --git a/target/riscv/vector_helper.c b/target/riscv/vector_helper.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/target/riscv/vector_helper.c
43
+++ b/target/riscv/vector_helper.c
44
@@ -XXX,XX +XXX,XX @@ RVVCALL(OPFVV1, vfwcvt_f_f_v_w, WOP_UU_W, H8, H4, float32_to_float64)
45
GEN_VEXT_V_ENV(vfwcvt_f_f_v_h, 4)
46
GEN_VEXT_V_ENV(vfwcvt_f_f_v_w, 8)
47
48
+RVVCALL(OPFVV1, vfwcvtbf16_f_f_v, WOP_UU_H, H4, H2, bfloat16_to_float32)
49
+GEN_VEXT_V_ENV(vfwcvtbf16_f_f_v, 4)
50
+
51
/* Narrowing Floating-Point/Integer Type-Convert Instructions */
52
/* (TD, T2, TX2) */
53
#define NOP_UU_B uint8_t, uint16_t, uint32_t
54
@@ -XXX,XX +XXX,XX @@ RVVCALL(OPFVV1, vfncvt_f_f_w_w, NOP_UU_W, H4, H8, float64_to_float32)
55
GEN_VEXT_V_ENV(vfncvt_f_f_w_h, 2)
56
GEN_VEXT_V_ENV(vfncvt_f_f_w_w, 4)
57
58
+RVVCALL(OPFVV1, vfncvtbf16_f_f_w, NOP_UU_H, H2, H4, float32_to_bfloat16)
59
+GEN_VEXT_V_ENV(vfncvtbf16_f_f_w, 2)
60
+
61
/*
62
* Vector Reduction Operations
63
*/
64
diff --git a/target/riscv/insn_trans/trans_rvbf16.c.inc b/target/riscv/insn_trans/trans_rvbf16.c.inc
65
index XXXXXXX..XXXXXXX 100644
66
--- a/target/riscv/insn_trans/trans_rvbf16.c.inc
67
+++ b/target/riscv/insn_trans/trans_rvbf16.c.inc
68
@@ -XXX,XX +XXX,XX @@
69
} \
70
} while (0)
71
72
+#define REQUIRE_ZVFBFMIN(ctx) do { \
73
+ if (!ctx->cfg_ptr->ext_zvfbfmin) { \
74
+ return false; \
75
+ } \
76
+} while (0)
77
+
78
static bool trans_fcvt_bf16_s(DisasContext *ctx, arg_fcvt_bf16_s *a)
79
{
80
REQUIRE_FPU;
81
@@ -XXX,XX +XXX,XX @@ static bool trans_fcvt_s_bf16(DisasContext *ctx, arg_fcvt_s_bf16 *a)
82
mark_fs_dirty(ctx);
83
return true;
84
}
85
+
86
+static bool trans_vfncvtbf16_f_f_w(DisasContext *ctx, arg_vfncvtbf16_f_f_w *a)
87
+{
88
+ REQUIRE_FPU;
89
+ REQUIRE_ZVFBFMIN(ctx);
90
+
91
+ if (opfv_narrow_check(ctx, a) && (ctx->sew == MO_16)) {
92
+ uint32_t data = 0;
93
+ TCGLabel *over = gen_new_label();
94
+
95
+ gen_set_rm_chkfrm(ctx, RISCV_FRM_DYN);
96
+ tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
97
+ tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
98
+
99
+ data = FIELD_DP32(data, VDATA, VM, a->vm);
100
+ data = FIELD_DP32(data, VDATA, LMUL, ctx->lmul);
101
+ data = FIELD_DP32(data, VDATA, VTA, ctx->vta);
102
+ data = FIELD_DP32(data, VDATA, VMA, ctx->vma);
103
+ tcg_gen_gvec_3_ptr(vreg_ofs(ctx, a->rd), vreg_ofs(ctx, 0),
104
+ vreg_ofs(ctx, a->rs2), cpu_env,
105
+ ctx->cfg_ptr->vlen / 8,
106
+ ctx->cfg_ptr->vlen / 8, data,
107
+ gen_helper_vfncvtbf16_f_f_w);
108
+ mark_vs_dirty(ctx);
109
+ gen_set_label(over);
110
+ return true;
111
+ }
112
+ return false;
113
+}
114
+
115
+static bool trans_vfwcvtbf16_f_f_v(DisasContext *ctx, arg_vfwcvtbf16_f_f_v *a)
116
+{
117
+ REQUIRE_FPU;
118
+ REQUIRE_ZVFBFMIN(ctx);
119
+
120
+ if (opfv_widen_check(ctx, a) && (ctx->sew == MO_16)) {
121
+ uint32_t data = 0;
122
+ TCGLabel *over = gen_new_label();
123
+
124
+ gen_set_rm_chkfrm(ctx, RISCV_FRM_DYN);
125
+ tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
126
+ tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
127
+
128
+ data = FIELD_DP32(data, VDATA, VM, a->vm);
129
+ data = FIELD_DP32(data, VDATA, LMUL, ctx->lmul);
130
+ data = FIELD_DP32(data, VDATA, VTA, ctx->vta);
131
+ data = FIELD_DP32(data, VDATA, VMA, ctx->vma);
132
+ tcg_gen_gvec_3_ptr(vreg_ofs(ctx, a->rd), vreg_ofs(ctx, 0),
133
+ vreg_ofs(ctx, a->rs2), cpu_env,
134
+ ctx->cfg_ptr->vlen / 8,
135
+ ctx->cfg_ptr->vlen / 8, data,
136
+ gen_helper_vfwcvtbf16_f_f_v);
137
+ mark_vs_dirty(ctx);
138
+ gen_set_label(over);
139
+ return true;
140
+ }
141
+ return false;
142
+}
143
--
144
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Add trans_* and helper function for Zvfbfwma instructions.
4
5
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
6
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-Id: <20230615063302.102409-5-liweiwei@iscas.ac.cn>
9
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
---
11
target/riscv/helper.h | 3 ++
12
target/riscv/insn32.decode | 4 ++
13
target/riscv/vector_helper.c | 11 ++++
14
target/riscv/insn_trans/trans_rvbf16.c.inc | 58 ++++++++++++++++++++++
15
4 files changed, 76 insertions(+)
16
17
diff --git a/target/riscv/helper.h b/target/riscv/helper.h
18
index XXXXXXX..XXXXXXX 100644
19
--- a/target/riscv/helper.h
20
+++ b/target/riscv/helper.h
21
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_2(fcvt_s_bf16, TCG_CALL_NO_RWG, i64, env, i64)
22
23
DEF_HELPER_5(vfncvtbf16_f_f_w, void, ptr, ptr, ptr, env, i32)
24
DEF_HELPER_5(vfwcvtbf16_f_f_v, void, ptr, ptr, ptr, env, i32)
25
+
26
+DEF_HELPER_6(vfwmaccbf16_vv, void, ptr, ptr, ptr, ptr, env, i32)
27
+DEF_HELPER_6(vfwmaccbf16_vf, void, ptr, ptr, i64, ptr, env, i32)
28
diff --git a/target/riscv/insn32.decode b/target/riscv/insn32.decode
29
index XXXXXXX..XXXXXXX 100644
30
--- a/target/riscv/insn32.decode
31
+++ b/target/riscv/insn32.decode
32
@@ -XXX,XX +XXX,XX @@ fcvt_s_bf16 0100000 00110 ..... ... ..... 1010011 @r2_rm
33
# *** Zvfbfmin Standard Extension ***
34
vfncvtbf16_f_f_w 010010 . ..... 11101 001 ..... 1010111 @r2_vm
35
vfwcvtbf16_f_f_v 010010 . ..... 01101 001 ..... 1010111 @r2_vm
36
+
37
+# *** Zvfbfwma Standard Extension ***
38
+vfwmaccbf16_vv 111011 . ..... ..... 001 ..... 1010111 @r_vm
39
+vfwmaccbf16_vf 111011 . ..... ..... 101 ..... 1010111 @r_vm
40
diff --git a/target/riscv/vector_helper.c b/target/riscv/vector_helper.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/target/riscv/vector_helper.c
43
+++ b/target/riscv/vector_helper.c
44
@@ -XXX,XX +XXX,XX @@ RVVCALL(OPFVF3, vfwmacc_vf_w, WOP_UUU_W, H8, H4, fwmacc32)
45
GEN_VEXT_VF(vfwmacc_vf_h, 4)
46
GEN_VEXT_VF(vfwmacc_vf_w, 8)
47
48
+static uint32_t fwmaccbf16(uint16_t a, uint16_t b, uint32_t d, float_status *s)
49
+{
50
+ return float32_muladd(bfloat16_to_float32(a, s),
51
+ bfloat16_to_float32(b, s), d, 0, s);
52
+}
53
+
54
+RVVCALL(OPFVV3, vfwmaccbf16_vv, WOP_UUU_H, H4, H2, H2, fwmaccbf16)
55
+GEN_VEXT_VV_ENV(vfwmaccbf16_vv, 4)
56
+RVVCALL(OPFVF3, vfwmaccbf16_vf, WOP_UUU_H, H4, H2, fwmacc16)
57
+GEN_VEXT_VF(vfwmaccbf16_vf, 4)
58
+
59
static uint32_t fwnmacc16(uint16_t a, uint16_t b, uint32_t d, float_status *s)
60
{
61
return float32_muladd(float16_to_float32(a, true, s),
62
diff --git a/target/riscv/insn_trans/trans_rvbf16.c.inc b/target/riscv/insn_trans/trans_rvbf16.c.inc
63
index XXXXXXX..XXXXXXX 100644
64
--- a/target/riscv/insn_trans/trans_rvbf16.c.inc
65
+++ b/target/riscv/insn_trans/trans_rvbf16.c.inc
66
@@ -XXX,XX +XXX,XX @@
67
} \
68
} while (0)
69
70
+#define REQUIRE_ZVFBFWMA(ctx) do { \
71
+ if (!ctx->cfg_ptr->ext_zvfbfwma) { \
72
+ return false; \
73
+ } \
74
+} while (0)
75
+
76
static bool trans_fcvt_bf16_s(DisasContext *ctx, arg_fcvt_bf16_s *a)
77
{
78
REQUIRE_FPU;
79
@@ -XXX,XX +XXX,XX @@ static bool trans_vfwcvtbf16_f_f_v(DisasContext *ctx, arg_vfwcvtbf16_f_f_v *a)
80
}
81
return false;
82
}
83
+
84
+static bool trans_vfwmaccbf16_vv(DisasContext *ctx, arg_vfwmaccbf16_vv *a)
85
+{
86
+ REQUIRE_FPU;
87
+ REQUIRE_ZVFBFWMA(ctx);
88
+
89
+ if (require_rvv(ctx) && vext_check_isa_ill(ctx) && (ctx->sew == MO_16) &&
90
+ vext_check_dss(ctx, a->rd, a->rs1, a->rs2, a->vm)) {
91
+ uint32_t data = 0;
92
+ TCGLabel *over = gen_new_label();
93
+
94
+ gen_set_rm_chkfrm(ctx, RISCV_FRM_DYN);
95
+ tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
96
+ tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
97
+
98
+ data = FIELD_DP32(data, VDATA, VM, a->vm);
99
+ data = FIELD_DP32(data, VDATA, LMUL, ctx->lmul);
100
+ data = FIELD_DP32(data, VDATA, VTA, ctx->vta);
101
+ data = FIELD_DP32(data, VDATA, VMA, ctx->vma);
102
+ tcg_gen_gvec_4_ptr(vreg_ofs(ctx, a->rd), vreg_ofs(ctx, 0),
103
+ vreg_ofs(ctx, a->rs1),
104
+ vreg_ofs(ctx, a->rs2), cpu_env,
105
+ ctx->cfg_ptr->vlen / 8,
106
+ ctx->cfg_ptr->vlen / 8, data,
107
+ gen_helper_vfwmaccbf16_vv);
108
+ mark_vs_dirty(ctx);
109
+ gen_set_label(over);
110
+ return true;
111
+ }
112
+ return false;
113
+}
114
+
115
+static bool trans_vfwmaccbf16_vf(DisasContext *ctx, arg_vfwmaccbf16_vf *a)
116
+{
117
+ REQUIRE_FPU;
118
+ REQUIRE_ZVFBFWMA(ctx);
119
+
120
+ if (require_rvv(ctx) && (ctx->sew == MO_16) && vext_check_isa_ill(ctx) &&
121
+ vext_check_ds(ctx, a->rd, a->rs2, a->vm)) {
122
+ uint32_t data = 0;
123
+
124
+ gen_set_rm(ctx, RISCV_FRM_DYN);
125
+ data = FIELD_DP32(data, VDATA, VM, a->vm);
126
+ data = FIELD_DP32(data, VDATA, LMUL, ctx->lmul);
127
+ data = FIELD_DP32(data, VDATA, VTA, ctx->vta);
128
+ data = FIELD_DP32(data, VDATA, VMA, ctx->vma);
129
+ return opfvf_trans(a->rd, a->rs1, a->rs2, data,
130
+ gen_helper_vfwmaccbf16_vf, ctx);
131
+ }
132
+
133
+ return false;
134
+}
135
--
136
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
2
2
3
RISC-V machines do not instantiate RISC-V CPUs directly, instead
3
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
4
they do that via the hart array. Add a new property for the reset
4
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
5
vector address to allow the value to be passed to the CPU, before
5
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
6
CPU is realized.
6
Message-Id: <20230615063302.102409-6-liweiwei@iscas.ac.cn>
7
8
Signed-off-by: Bin Meng <bin.meng@windriver.com>
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
11
Message-Id: <1598924352-89526-3-git-send-email-bmeng.cn@gmail.com>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
7
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
13
---
8
---
14
include/hw/riscv/riscv_hart.h | 1 +
9
target/riscv/cpu.c | 7 +++++++
15
hw/riscv/riscv_hart.c | 3 +++
10
1 file changed, 7 insertions(+)
16
2 files changed, 4 insertions(+)
17
11
18
diff --git a/include/hw/riscv/riscv_hart.h b/include/hw/riscv/riscv_hart.h
12
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
19
index XXXXXXX..XXXXXXX 100644
13
index XXXXXXX..XXXXXXX 100644
20
--- a/include/hw/riscv/riscv_hart.h
14
--- a/target/riscv/cpu.c
21
+++ b/include/hw/riscv/riscv_hart.h
15
+++ b/target/riscv/cpu.c
22
@@ -XXX,XX +XXX,XX @@ typedef struct RISCVHartArrayState {
16
@@ -XXX,XX +XXX,XX @@ static const struct isa_ext_data isa_edata_arr[] = {
23
uint32_t num_harts;
17
ISA_EXT_DATA_ENTRY(zifencei, PRIV_VERSION_1_10_0, ext_ifencei),
24
uint32_t hartid_base;
18
ISA_EXT_DATA_ENTRY(zihintpause, PRIV_VERSION_1_10_0, ext_zihintpause),
25
char *cpu_type;
19
ISA_EXT_DATA_ENTRY(zawrs, PRIV_VERSION_1_12_0, ext_zawrs),
26
+ uint64_t resetvec;
20
+ ISA_EXT_DATA_ENTRY(zfbfmin, PRIV_VERSION_1_12_0, ext_zfbfmin),
27
RISCVCPU *harts;
21
ISA_EXT_DATA_ENTRY(zfh, PRIV_VERSION_1_11_0, ext_zfh),
28
} RISCVHartArrayState;
22
ISA_EXT_DATA_ENTRY(zfhmin, PRIV_VERSION_1_11_0, ext_zfhmin),
29
23
ISA_EXT_DATA_ENTRY(zfinx, PRIV_VERSION_1_12_0, ext_zfinx),
30
diff --git a/hw/riscv/riscv_hart.c b/hw/riscv/riscv_hart.c
24
@@ -XXX,XX +XXX,XX @@ static const struct isa_ext_data isa_edata_arr[] = {
31
index XXXXXXX..XXXXXXX 100644
25
ISA_EXT_DATA_ENTRY(zve32f, PRIV_VERSION_1_10_0, ext_zve32f),
32
--- a/hw/riscv/riscv_hart.c
26
ISA_EXT_DATA_ENTRY(zve64f, PRIV_VERSION_1_10_0, ext_zve64f),
33
+++ b/hw/riscv/riscv_hart.c
27
ISA_EXT_DATA_ENTRY(zve64d, PRIV_VERSION_1_10_0, ext_zve64d),
34
@@ -XXX,XX +XXX,XX @@ static Property riscv_harts_props[] = {
28
+ ISA_EXT_DATA_ENTRY(zvfbfmin, PRIV_VERSION_1_12_0, ext_zvfbfmin),
35
DEFINE_PROP_UINT32("num-harts", RISCVHartArrayState, num_harts, 1),
29
+ ISA_EXT_DATA_ENTRY(zvfbfwma, PRIV_VERSION_1_12_0, ext_zvfbfwma),
36
DEFINE_PROP_UINT32("hartid-base", RISCVHartArrayState, hartid_base, 0),
30
ISA_EXT_DATA_ENTRY(zvfh, PRIV_VERSION_1_12_0, ext_zvfh),
37
DEFINE_PROP_STRING("cpu-type", RISCVHartArrayState, cpu_type),
31
ISA_EXT_DATA_ENTRY(zvfhmin, PRIV_VERSION_1_12_0, ext_zvfhmin),
38
+ DEFINE_PROP_UINT64("resetvec", RISCVHartArrayState, resetvec,
32
ISA_EXT_DATA_ENTRY(zhinx, PRIV_VERSION_1_12_0, ext_zhinx),
39
+ DEFAULT_RSTVEC),
33
@@ -XXX,XX +XXX,XX @@ static Property riscv_cpu_extensions[] = {
34
DEFINE_PROP_BOOL("x-zvfh", RISCVCPU, cfg.ext_zvfh, false),
35
DEFINE_PROP_BOOL("x-zvfhmin", RISCVCPU, cfg.ext_zvfhmin, false),
36
37
+ DEFINE_PROP_BOOL("x-zfbfmin", RISCVCPU, cfg.ext_zfbfmin, false),
38
+ DEFINE_PROP_BOOL("x-zvfbfmin", RISCVCPU, cfg.ext_zvfbfmin, false),
39
+ DEFINE_PROP_BOOL("x-zvfbfwma", RISCVCPU, cfg.ext_zvfbfwma, false),
40
+
40
DEFINE_PROP_END_OF_LIST(),
41
DEFINE_PROP_END_OF_LIST(),
41
};
42
};
42
43
43
@@ -XXX,XX +XXX,XX @@ static bool riscv_hart_realize(RISCVHartArrayState *s, int idx,
44
char *cpu_type, Error **errp)
45
{
46
object_initialize_child(OBJECT(s), "harts[*]", &s->harts[idx], cpu_type);
47
+ qdev_prop_set_uint64(DEVICE(&s->harts[idx]), "resetvec", s->resetvec);
48
s->harts[idx].env.mhartid = s->hartid_base + idx;
49
qemu_register_reset(riscv_harts_cpu_reset, &s->harts[idx]);
50
return qdev_realize(DEVICE(&s->harts[idx]), NULL, errp);
51
--
44
--
52
2.28.0
45
2.40.1
53
54
diff view generated by jsdifflib
New patch
1
From: Jason Chien <jason.chien@sifive.com>
1
2
3
The privileged spec states:
4
For a memory access made to support VS-stage address translation (such as
5
to read/write a VS-level page table), permissions are checked as though
6
for a load or store, not for the original access type. However, any
7
exception is always reported for the original access type (instruction,
8
load, or store/AMO).
9
10
The current implementation converts the access type to LOAD if implicit
11
G-stage translation fails which results in only reporting "Load guest-page
12
fault". This commit removes the convertion of access type, so the reported
13
exception conforms to the spec.
14
15
Signed-off-by: Jason Chien <jason.chien@sifive.com>
16
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
17
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
18
Message-Id: <20230627074915.7686-1-jason.chien@sifive.com>
19
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
20
---
21
target/riscv/cpu_helper.c | 1 -
22
1 file changed, 1 deletion(-)
23
24
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
25
index XXXXXXX..XXXXXXX 100644
26
--- a/target/riscv/cpu_helper.c
27
+++ b/target/riscv/cpu_helper.c
28
@@ -XXX,XX +XXX,XX @@ bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
29
if (ret == TRANSLATE_G_STAGE_FAIL) {
30
first_stage_error = false;
31
two_stage_indirect_error = true;
32
- access_type = MMU_DATA_LOAD;
33
}
34
35
qemu_log_mask(CPU_LOG_MMU,
36
--
37
2.40.1
diff view generated by jsdifflib
New patch
1
From: Weiwei Li <liweiwei@iscas.ac.cn>
1
2
3
Signed-off-by: Weiwei Li <liweiwei@iscas.ac.cn>
4
Signed-off-by: Junqiang Wang <wangjunqiang@iscas.ac.cn>
5
Acked-by: Alistair Francis <alistair.francis@wdc.com>
6
Message-Id: <20230703071759.86775-2-liweiwei@iscas.ac.cn>
7
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
8
---
9
disas/riscv.c | 44 ++++++++++++++++++++++++++++++++++++++++++++
10
1 file changed, 44 insertions(+)
11
12
diff --git a/disas/riscv.c b/disas/riscv.c
13
index XXXXXXX..XXXXXXX 100644
14
--- a/disas/riscv.c
15
+++ b/disas/riscv.c
16
@@ -XXX,XX +XXX,XX @@ typedef enum {
17
rv_op_cm_jalt = 788,
18
rv_op_czero_eqz = 789,
19
rv_op_czero_nez = 790,
20
+ rv_op_fcvt_bf16_s = 791,
21
+ rv_op_fcvt_s_bf16 = 792,
22
+ rv_op_vfncvtbf16_f_f_w = 793,
23
+ rv_op_vfwcvtbf16_f_f_v = 794,
24
+ rv_op_vfwmaccbf16_vv = 795,
25
+ rv_op_vfwmaccbf16_vf = 796,
26
+ rv_op_flh = 797,
27
+ rv_op_fsh = 798,
28
+ rv_op_fmv_h_x = 799,
29
+ rv_op_fmv_x_h = 800,
30
} rv_op;
31
32
/* register names */
33
@@ -XXX,XX +XXX,XX @@ const rv_opcode_data rvi_opcode_data[] = {
34
{ "cm.jalt", rv_codec_zcmt_jt, rv_fmt_zcmt_index, NULL, 0 },
35
{ "czero.eqz", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
36
{ "czero.nez", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
37
+ { "fcvt.bf16.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
38
+ { "fcvt.s.bf16", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
39
+ { "vfncvtbf16.f.f.w", rv_codec_v_r, rv_fmt_vd_vs2_vm, NULL, 0, 0, 0 },
40
+ { "vfwcvtbf16.f.f.v", rv_codec_v_r, rv_fmt_vd_vs2_vm, NULL, 0, 0, 0 },
41
+ { "vfwmaccbf16.vv", rv_codec_v_r, rv_fmt_vd_vs1_vs2_vm, NULL, 0, 0, 0 },
42
+ { "vfwmaccbf16.vf", rv_codec_v_r, rv_fmt_vd_fs1_vs2_vm, NULL, 0, 0, 0 },
43
+ { "flh", rv_codec_i, rv_fmt_frd_offset_rs1, NULL, 0, 0, 0 },
44
+ { "fsh", rv_codec_s, rv_fmt_frs2_offset_rs1, NULL, 0, 0, 0 },
45
+ { "fmv.h.x", rv_codec_r, rv_fmt_frd_rs1, NULL, 0, 0, 0 },
46
+ { "fmv.x.h", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
47
};
48
49
/* CSR names */
50
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
51
case 3: op = rv_op_vloxei8_v; break;
52
}
53
break;
54
+ case 1: op = rv_op_flh; break;
55
case 2: op = rv_op_flw; break;
56
case 3: op = rv_op_fld; break;
57
case 4: op = rv_op_flq; break;
58
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
59
case 3: op = rv_op_vsoxei8_v; break;
60
}
61
break;
62
+ case 1: op = rv_op_fsh; break;
63
case 2: op = rv_op_fsw; break;
64
case 3: op = rv_op_fsd; break;
65
case 4: op = rv_op_fsq; break;
66
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
67
switch ((inst >> 20) & 0b11111) {
68
case 1: op = rv_op_fcvt_s_d; break;
69
case 3: op = rv_op_fcvt_s_q; break;
70
+ case 6: op = rv_op_fcvt_s_bf16; break;
71
}
72
break;
73
case 33:
74
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
75
case 3: op = rv_op_fcvt_d_q; break;
76
}
77
break;
78
+ case 34:
79
+ switch (((inst >> 20) & 0b11111)) {
80
+ case 8: op = rv_op_fcvt_bf16_s; break;
81
+ }
82
+ break;
83
case 35:
84
switch ((inst >> 20) & 0b11111) {
85
case 0: op = rv_op_fcvt_q_s; break;
86
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
87
case 1: op = rv_op_fclass_d; break;
88
}
89
break;
90
+ case 114:
91
+ switch (((inst >> 17) & 0b11111000) |
92
+ ((inst >> 12) & 0b00000111)) {
93
+ case 0: op = rv_op_fmv_x_h; break;
94
+ }
95
+ break;
96
case 115:
97
switch (((inst >> 17) & 0b11111000) |
98
((inst >> 12) & 0b00000111)) {
99
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
100
case 0: op = rv_op_fmv_d_x; break;
101
}
102
break;
103
+ case 122:
104
+ switch (((inst >> 17) & 0b11111000) |
105
+ ((inst >> 12) & 0b00000111)) {
106
+ case 0: op = rv_op_fmv_h_x; break;
107
+ }
108
+ break;
109
case 123:
110
switch (((inst >> 17) & 0b11111000) |
111
((inst >> 12) & 0b00000111)) {
112
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
113
case 10: op = rv_op_vfwcvt_f_xu_v; break;
114
case 11: op = rv_op_vfwcvt_f_x_v; break;
115
case 12: op = rv_op_vfwcvt_f_f_v; break;
116
+ case 13: op = rv_op_vfwcvtbf16_f_f_v; break;
117
case 14: op = rv_op_vfwcvt_rtz_xu_f_v; break;
118
case 15: op = rv_op_vfwcvt_rtz_x_f_v; break;
119
case 16: op = rv_op_vfncvt_xu_f_w; break;
120
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
121
case 21: op = rv_op_vfncvt_rod_f_f_w; break;
122
case 22: op = rv_op_vfncvt_rtz_xu_f_w; break;
123
case 23: op = rv_op_vfncvt_rtz_x_f_w; break;
124
+ case 29: op = rv_op_vfncvtbf16_f_f_w; break;
125
}
126
break;
127
case 19:
128
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
129
case 52: op = rv_op_vfwadd_wv; break;
130
case 54: op = rv_op_vfwsub_wv; break;
131
case 56: op = rv_op_vfwmul_vv; break;
132
+ case 59: op = rv_op_vfwmaccbf16_vv; break;
133
case 60: op = rv_op_vfwmacc_vv; break;
134
case 61: op = rv_op_vfwnmacc_vv; break;
135
case 62: op = rv_op_vfwmsac_vv; break;
136
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
137
case 52: op = rv_op_vfwadd_wf; break;
138
case 54: op = rv_op_vfwsub_wf; break;
139
case 56: op = rv_op_vfwmul_vf; break;
140
+ case 59: op = rv_op_vfwmaccbf16_vf; break;
141
case 60: op = rv_op_vfwmacc_vf; break;
142
case 61: op = rv_op_vfwnmacc_vf; break;
143
case 62: op = rv_op_vfwmsac_vf; break;
144
--
145
2.40.1
diff view generated by jsdifflib
1
From: Nathan Chancellor <natechancellor@gmail.com>
1
From: "yang.zhang" <yang.zhang@hexintek.com>
2
2
3
When shutting down the machine running a mainline Linux kernel, the
3
Should set/get riscv all reg timer,i.e, time/compare/frequency/state.
4
following error happens:
5
4
6
$ build/riscv64-softmmu/qemu-system-riscv64 -bios default -M virt \
5
Signed-off-by: Yang Zhang <yang.zhang@hexintek.com>
7
-display none -initrd rootfs.cpio -kernel Image -m 512m \
6
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/1688
8
-nodefaults -serial mon:stdio
9
...
10
Requesting system poweroff
11
[ 4.999630] reboot: Power down
12
sbi_trap_error: hart0: trap handler failed (error -2)
13
sbi_trap_error: hart0: mcause=0x0000000000000007 mtval=0x0000000000100000
14
sbi_trap_error: hart0: mepc=0x000000008000d4cc mstatus=0x0000000000001822
15
sbi_trap_error: hart0: ra=0x000000008000999e sp=0x0000000080015c78
16
sbi_trap_error: hart0: gp=0xffffffe000e76610 tp=0xffffffe0081b89c0
17
sbi_trap_error: hart0: s0=0x0000000080015c88 s1=0x0000000000000040
18
sbi_trap_error: hart0: a0=0x0000000000000000 a1=0x0000000080004024
19
sbi_trap_error: hart0: a2=0x0000000080004024 a3=0x0000000080004024
20
sbi_trap_error: hart0: a4=0x0000000000100000 a5=0x0000000000005555
21
sbi_trap_error: hart0: a6=0x0000000000004024 a7=0x0000000080011158
22
sbi_trap_error: hart0: s2=0x0000000000000000 s3=0x0000000080016000
23
sbi_trap_error: hart0: s4=0x0000000000000000 s5=0x0000000000000000
24
sbi_trap_error: hart0: s6=0x0000000000000001 s7=0x0000000000000000
25
sbi_trap_error: hart0: s8=0x0000000000000000 s9=0x0000000000000000
26
sbi_trap_error: hart0: s10=0x0000000000000000 s11=0x0000000000000008
27
sbi_trap_error: hart0: t0=0x0000000000000000 t1=0x0000000000000000
28
sbi_trap_error: hart0: t2=0x0000000000000000 t3=0x0000000000000000
29
sbi_trap_error: hart0: t4=0x0000000000000000 t5=0x0000000000000000
30
sbi_trap_error: hart0: t6=0x0000000000000000
31
32
The kernel does a 16-bit write when powering off the machine, which
33
was allowed before commit 5d971f9e67 ("memory: Revert "memory: accept
34
mismatching sizes in memory_region_access_valid""). Make min_access_size
35
match reality so that the machine can shut down properly now.
36
37
Cc: qemu-stable@nongnu.org
38
Fixes: 88a07990fa ("SiFive RISC-V Test Finisher")
39
Fixes: 5d971f9e67 ("memory: Revert "memory: accept mismatching sizes in memory_region_access_valid"")
40
Signed-off-by: Nathan Chancellor <natechancellor@gmail.com>
41
Acked-by: Michael S. Tsirkin <mst@redhat.com>
42
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
43
Message-Id: <20200901055822.2721209-1-natechancellor@gmail.com>
8
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
9
Message-Id: <20230707032306.4606-1-gaoshanliukou@163.com>
44
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
45
---
11
---
46
hw/riscv/sifive_test.c | 2 +-
12
target/riscv/kvm.c | 2 +-
47
1 file changed, 1 insertion(+), 1 deletion(-)
13
1 file changed, 1 insertion(+), 1 deletion(-)
48
14
49
diff --git a/hw/riscv/sifive_test.c b/hw/riscv/sifive_test.c
15
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
50
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
51
--- a/hw/riscv/sifive_test.c
17
--- a/target/riscv/kvm.c
52
+++ b/hw/riscv/sifive_test.c
18
+++ b/target/riscv/kvm.c
53
@@ -XXX,XX +XXX,XX @@ static const MemoryRegionOps sifive_test_ops = {
19
@@ -XXX,XX +XXX,XX @@ static uint64_t kvm_riscv_reg_id(CPURISCVState *env, uint64_t type,
54
.write = sifive_test_write,
20
55
.endianness = DEVICE_NATIVE_ENDIAN,
21
#define KVM_RISCV_SET_TIMER(cs, env, name, reg) \
56
.valid = {
22
do { \
57
- .min_access_size = 4,
23
- int ret = kvm_set_one_reg(cs, RISCV_TIMER_REG(env, time), &reg); \
58
+ .min_access_size = 2,
24
+ int ret = kvm_set_one_reg(cs, RISCV_TIMER_REG(env, name), &reg); \
59
.max_access_size = 4
25
if (ret) { \
60
}
26
abort(); \
61
};
27
} \
62
--
28
--
63
2.28.0
29
2.40.1
64
65
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Lakshmi Bai Raja Subramanian <lakshmi.bai.rajasubramanian@bodhicomputing.com>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
fdt_load_addr was previously declared as uint32_t which doe not match
4
should only contain the RISC-V SoC / machine codes plus generic
4
with the return type of riscv_compute_fdt_addr().
5
codes. Let's move sifive_plic model to hw/intc directory.
6
5
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
6
This patch modifies the fdt_load_addr type from a uint32_t to a uint64_t
7
to match the riscv_compute_fdt_addr() return type.
8
9
This fixes calculating the fdt address when DRAM is mapped to higher
10
64-bit address.
11
12
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
13
Signed-off-by: Lakshmi Bai Raja Subramanian <lakshmi.bai.rajasubramanian@bodhicomputing.com>
14
[ Change by AF:
15
- Cleanup commit title and message
16
]
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
17
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-7-git-send-email-bmeng.cn@gmail.com>
18
Message-Id: <168872495192.6334.3845988291412774261-1@git.sr.ht>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
19
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
20
---
12
{include/hw/riscv => hw/intc}/sifive_plic.h | 0
21
hw/riscv/virt.c | 2 +-
13
hw/{riscv => intc}/sifive_plic.c | 2 +-
22
1 file changed, 1 insertion(+), 1 deletion(-)
14
hw/riscv/microchip_pfsoc.c | 2 +-
15
hw/riscv/sifive_e.c | 2 +-
16
hw/riscv/sifive_u.c | 2 +-
17
hw/riscv/virt.c | 2 +-
18
hw/intc/Kconfig | 3 +++
19
hw/intc/meson.build | 1 +
20
hw/riscv/Kconfig | 5 +++++
21
hw/riscv/meson.build | 1 -
22
10 files changed, 14 insertions(+), 6 deletions(-)
23
rename {include/hw/riscv => hw/intc}/sifive_plic.h (100%)
24
rename hw/{riscv => intc}/sifive_plic.c (99%)
25
23
26
diff --git a/include/hw/riscv/sifive_plic.h b/hw/intc/sifive_plic.h
27
similarity index 100%
28
rename from include/hw/riscv/sifive_plic.h
29
rename to hw/intc/sifive_plic.h
30
diff --git a/hw/riscv/sifive_plic.c b/hw/intc/sifive_plic.c
31
similarity index 99%
32
rename from hw/riscv/sifive_plic.c
33
rename to hw/intc/sifive_plic.c
34
index XXXXXXX..XXXXXXX 100644
35
--- a/hw/riscv/sifive_plic.c
36
+++ b/hw/intc/sifive_plic.c
37
@@ -XXX,XX +XXX,XX @@
38
#include "hw/pci/msi.h"
39
#include "hw/boards.h"
40
#include "hw/qdev-properties.h"
41
+#include "hw/intc/sifive_plic.h"
42
#include "target/riscv/cpu.h"
43
#include "sysemu/sysemu.h"
44
-#include "hw/riscv/sifive_plic.h"
45
46
#define RISCV_DEBUG_PLIC 0
47
48
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
49
index XXXXXXX..XXXXXXX 100644
50
--- a/hw/riscv/microchip_pfsoc.c
51
+++ b/hw/riscv/microchip_pfsoc.c
52
@@ -XXX,XX +XXX,XX @@
53
#include "hw/misc/unimp.h"
54
#include "hw/riscv/boot.h"
55
#include "hw/riscv/riscv_hart.h"
56
-#include "hw/riscv/sifive_plic.h"
57
#include "hw/riscv/microchip_pfsoc.h"
58
#include "hw/intc/sifive_clint.h"
59
+#include "hw/intc/sifive_plic.h"
60
#include "sysemu/sysemu.h"
61
62
/*
63
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
64
index XXXXXXX..XXXXXXX 100644
65
--- a/hw/riscv/sifive_e.c
66
+++ b/hw/riscv/sifive_e.c
67
@@ -XXX,XX +XXX,XX @@
68
#include "hw/misc/unimp.h"
69
#include "target/riscv/cpu.h"
70
#include "hw/riscv/riscv_hart.h"
71
-#include "hw/riscv/sifive_plic.h"
72
#include "hw/riscv/sifive_uart.h"
73
#include "hw/riscv/sifive_e.h"
74
#include "hw/riscv/boot.h"
75
#include "hw/intc/sifive_clint.h"
76
+#include "hw/intc/sifive_plic.h"
77
#include "hw/misc/sifive_e_prci.h"
78
#include "chardev/char.h"
79
#include "sysemu/arch_init.h"
80
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
81
index XXXXXXX..XXXXXXX 100644
82
--- a/hw/riscv/sifive_u.c
83
+++ b/hw/riscv/sifive_u.c
84
@@ -XXX,XX +XXX,XX @@
85
#include "hw/misc/unimp.h"
86
#include "target/riscv/cpu.h"
87
#include "hw/riscv/riscv_hart.h"
88
-#include "hw/riscv/sifive_plic.h"
89
#include "hw/riscv/sifive_uart.h"
90
#include "hw/riscv/sifive_u.h"
91
#include "hw/riscv/boot.h"
92
#include "hw/intc/sifive_clint.h"
93
+#include "hw/intc/sifive_plic.h"
94
#include "chardev/char.h"
95
#include "net/eth.h"
96
#include "sysemu/arch_init.h"
97
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
24
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
98
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX 100644
99
--- a/hw/riscv/virt.c
26
--- a/hw/riscv/virt.c
100
+++ b/hw/riscv/virt.c
27
+++ b/hw/riscv/virt.c
101
@@ -XXX,XX +XXX,XX @@
28
@@ -XXX,XX +XXX,XX @@ static void virt_machine_done(Notifier *notifier, void *data)
102
#include "hw/char/serial.h"
29
target_ulong start_addr = memmap[VIRT_DRAM].base;
103
#include "target/riscv/cpu.h"
30
target_ulong firmware_end_addr, kernel_start_addr;
104
#include "hw/riscv/riscv_hart.h"
31
const char *firmware_name = riscv_default_firmware_name(&s->soc[0]);
105
-#include "hw/riscv/sifive_plic.h"
32
- uint32_t fdt_load_addr;
106
#include "hw/riscv/sifive_test.h"
33
+ uint64_t fdt_load_addr;
107
#include "hw/riscv/virt.h"
34
uint64_t kernel_entry = 0;
108
#include "hw/riscv/boot.h"
35
BlockBackend *pflash_blk0;
109
#include "hw/riscv/numa.h"
36
110
#include "hw/intc/sifive_clint.h"
111
+#include "hw/intc/sifive_plic.h"
112
#include "chardev/char.h"
113
#include "sysemu/arch_init.h"
114
#include "sysemu/device_tree.h"
115
diff --git a/hw/intc/Kconfig b/hw/intc/Kconfig
116
index XXXXXXX..XXXXXXX 100644
117
--- a/hw/intc/Kconfig
118
+++ b/hw/intc/Kconfig
119
@@ -XXX,XX +XXX,XX @@ config LOONGSON_LIOINTC
120
121
config SIFIVE_CLINT
122
bool
123
+
124
+config SIFIVE_PLIC
125
+ bool
126
diff --git a/hw/intc/meson.build b/hw/intc/meson.build
127
index XXXXXXX..XXXXXXX 100644
128
--- a/hw/intc/meson.build
129
+++ b/hw/intc/meson.build
130
@@ -XXX,XX +XXX,XX @@ specific_ss.add(when: 'CONFIG_S390_FLIC', if_true: files('s390_flic.c'))
131
specific_ss.add(when: 'CONFIG_S390_FLIC_KVM', if_true: files('s390_flic_kvm.c'))
132
specific_ss.add(when: 'CONFIG_SH4', if_true: files('sh_intc.c'))
133
specific_ss.add(when: 'CONFIG_SIFIVE_CLINT', if_true: files('sifive_clint.c'))
134
+specific_ss.add(when: 'CONFIG_SIFIVE_PLIC', if_true: files('sifive_plic.c'))
135
specific_ss.add(when: 'CONFIG_XICS', if_true: files('xics.c'))
136
specific_ss.add(when: 'CONFIG_XICS_KVM', if_true: files('xics_kvm.c'))
137
specific_ss.add(when: 'CONFIG_XICS_SPAPR', if_true: files('xics_spapr.c'))
138
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
139
index XXXXXXX..XXXXXXX 100644
140
--- a/hw/riscv/Kconfig
141
+++ b/hw/riscv/Kconfig
142
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
143
select SIFIVE
144
select SIFIVE_CLINT
145
select SIFIVE_GPIO
146
+ select SIFIVE_PLIC
147
select SIFIVE_E_PRCI
148
select UNIMP
149
150
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
151
select SIFIVE_CLINT
152
select SIFIVE_GPIO
153
select SIFIVE_PDMA
154
+ select SIFIVE_PLIC
155
select SIFIVE_U_OTP
156
select SIFIVE_U_PRCI
157
select UNIMP
158
@@ -XXX,XX +XXX,XX @@ config SPIKE
159
select HTIF
160
select SIFIVE
161
select SIFIVE_CLINT
162
+ select SIFIVE_PLIC
163
164
config OPENTITAN
165
bool
166
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
167
select PFLASH_CFI01
168
select SIFIVE
169
select SIFIVE_CLINT
170
+ select SIFIVE_PLIC
171
172
config MICROCHIP_PFSOC
173
bool
174
@@ -XXX,XX +XXX,XX @@ config MICROCHIP_PFSOC
175
select UNIMP
176
select MCHP_PFSOC_MMUART
177
select SIFIVE_PDMA
178
+ select SIFIVE_PLIC
179
select CADENCE_SDHCI
180
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
181
index XXXXXXX..XXXXXXX 100644
182
--- a/hw/riscv/meson.build
183
+++ b/hw/riscv/meson.build
184
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(files('numa.c'))
185
riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
186
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
187
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
188
-riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_plic.c'))
189
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
190
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
191
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
192
--
37
--
193
2.28.0
38
2.40.1
194
195
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
As it is today it's not possible to use '-cpu host' if the RISC-V host
4
has RVH enabled. This is the resulting error:
5
6
$ ./qemu/build/qemu-system-riscv64 \
7
-machine virt,accel=kvm -m 2G -smp 1 \
8
-nographic -snapshot -kernel ./guest_imgs/Image \
9
-initrd ./guest_imgs/rootfs_kvm_riscv64.img \
10
-append "earlycon=sbi root=/dev/ram rw" \
11
-cpu host
12
qemu-system-riscv64: H extension requires priv spec 1.12.0
13
14
This happens because we're checking for priv spec for all CPUs, and
15
since we're not setting env->priv_ver for the 'host' CPU, it's being
16
default to zero (i.e. PRIV_SPEC_1_10_0).
17
18
In reality env->priv_ver does not make sense when running with the KVM
19
'host' CPU. It's used to gate certain CSRs/extensions during translation
20
to make them unavailable if the hart declares an older spec version. It
21
doesn't have any other use. E.g. OpenSBI version 1.2 retrieves the spec
22
checking if the CSR_MCOUNTEREN, CSR_MCOUNTINHIBIT and CSR_MENVCFG CSRs
23
are available [1].
24
25
'priv_ver' is just one example. We're doing a lot of feature validation
26
and setup during riscv_cpu_realize() that it doesn't apply to KVM CPUs.
27
Validating the feature set for those CPUs is a KVM problem that should
28
be handled in KVM specific code.
29
30
The new riscv_cpu_realize_tcg() helper contains all validation logic that
31
are applicable to TCG CPUs only. riscv_cpu_realize() verifies if we're
32
running TCG and, if it's the case, proceed with the usual TCG realize()
33
logic.
34
35
[1] lib/sbi/sbi_hart.c, hart_detect_features()
36
37
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
38
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
39
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
40
Message-Id: <20230706101738.460804-2-dbarboza@ventanamicro.com>
41
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
42
---
43
target/riscv/cpu.c | 35 +++++++++++++++++++++++++----------
44
1 file changed, 25 insertions(+), 10 deletions(-)
45
46
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
47
index XXXXXXX..XXXXXXX 100644
48
--- a/target/riscv/cpu.c
49
+++ b/target/riscv/cpu.c
50
@@ -XXX,XX +XXX,XX @@
51
#include "migration/vmstate.h"
52
#include "fpu/softfloat-helpers.h"
53
#include "sysemu/kvm.h"
54
+#include "sysemu/tcg.h"
55
#include "kvm_riscv.h"
56
#include "tcg/tcg.h"
57
58
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_validate_misa_priv(CPURISCVState *env, Error **errp)
59
}
60
}
61
62
-static void riscv_cpu_realize(DeviceState *dev, Error **errp)
63
+static void riscv_cpu_realize_tcg(DeviceState *dev, Error **errp)
64
{
65
- CPUState *cs = CPU(dev);
66
RISCVCPU *cpu = RISCV_CPU(dev);
67
CPURISCVState *env = &cpu->env;
68
- RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(dev);
69
Error *local_err = NULL;
70
71
- cpu_exec_realizefn(cs, &local_err);
72
- if (local_err != NULL) {
73
- error_propagate(errp, local_err);
74
- return;
75
- }
76
-
77
riscv_cpu_validate_misa_mxl(cpu, &local_err);
78
if (local_err != NULL) {
79
error_propagate(errp, local_err);
80
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_realize(DeviceState *dev, Error **errp)
81
}
82
83
#ifndef CONFIG_USER_ONLY
84
- cs->tcg_cflags |= CF_PCREL;
85
+ CPU(dev)->tcg_cflags |= CF_PCREL;
86
87
if (cpu->cfg.ext_sstc) {
88
riscv_timer_init(cpu);
89
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_realize(DeviceState *dev, Error **errp)
90
}
91
}
92
#endif
93
+}
94
+
95
+static void riscv_cpu_realize(DeviceState *dev, Error **errp)
96
+{
97
+ CPUState *cs = CPU(dev);
98
+ RISCVCPU *cpu = RISCV_CPU(dev);
99
+ RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(dev);
100
+ Error *local_err = NULL;
101
+
102
+ cpu_exec_realizefn(cs, &local_err);
103
+ if (local_err != NULL) {
104
+ error_propagate(errp, local_err);
105
+ return;
106
+ }
107
+
108
+ if (tcg_enabled()) {
109
+ riscv_cpu_realize_tcg(dev, &local_err);
110
+ if (local_err != NULL) {
111
+ error_propagate(errp, local_err);
112
+ return;
113
+ }
114
+ }
115
116
riscv_cpu_finalize_features(cpu, &local_err);
117
if (local_err != NULL) {
118
--
119
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
The absence of a satp mode in riscv_host_cpu_init() is causing the
4
should only contain the RISC-V SoC / machine codes plus generic
4
following error:
5
codes. Let's move sifive_clint model to hw/intc directory.
6
5
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
6
$ ./qemu/build/qemu-system-riscv64 -machine virt,accel=kvm \
7
-m 2G -smp 1 -nographic -snapshot \
8
-kernel ./guest_imgs/Image \
9
-initrd ./guest_imgs/rootfs_kvm_riscv64.img \
10
-append "earlycon=sbi root=/dev/ram rw" \
11
-cpu host
12
**
13
ERROR:../target/riscv/cpu.c:320:satp_mode_str: code should not be
14
reached
15
Bail out! ERROR:../target/riscv/cpu.c:320:satp_mode_str: code should
16
not be reached
17
Aborted
18
19
The error is triggered from create_fdt_socket_cpus() in hw/riscv/virt.c.
20
It's trying to get satp_mode_str for a NULL cpu->cfg.satp_mode.map.
21
22
For this KVM cpu we would need to inherit the satp supported modes
23
from the RISC-V host. At this moment this is not possible because the
24
KVM driver does not support it. And even when it does we can't just let
25
this broken for every other older kernel.
26
27
Since mmu-type is not a required node, according to [1], skip the
28
'mmu-type' FDT node if there's no satp_mode set. We'll revisit this
29
logic when we can get satp information from KVM.
30
31
[1] https://github.com/torvalds/linux/blob/master/Documentation/devicetree/bindings/riscv/cpus.yaml
32
33
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
34
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
35
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-6-git-send-email-bmeng.cn@gmail.com>
36
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
37
Message-Id: <20230706101738.460804-3-dbarboza@ventanamicro.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
38
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
39
---
12
include/hw/{riscv => intc}/sifive_clint.h | 0
40
hw/riscv/virt.c | 14 +++++++-------
13
hw/{riscv => intc}/sifive_clint.c | 2 +-
41
1 file changed, 7 insertions(+), 7 deletions(-)
14
hw/riscv/microchip_pfsoc.c | 2 +-
15
hw/riscv/sifive_e.c | 2 +-
16
hw/riscv/sifive_u.c | 2 +-
17
hw/riscv/spike.c | 2 +-
18
hw/riscv/virt.c | 2 +-
19
hw/intc/Kconfig | 3 +++
20
hw/intc/meson.build | 1 +
21
hw/riscv/Kconfig | 5 +++++
22
hw/riscv/meson.build | 1 -
23
11 files changed, 15 insertions(+), 7 deletions(-)
24
rename include/hw/{riscv => intc}/sifive_clint.h (100%)
25
rename hw/{riscv => intc}/sifive_clint.c (99%)
26
42
27
diff --git a/include/hw/riscv/sifive_clint.h b/include/hw/intc/sifive_clint.h
28
similarity index 100%
29
rename from include/hw/riscv/sifive_clint.h
30
rename to include/hw/intc/sifive_clint.h
31
diff --git a/hw/riscv/sifive_clint.c b/hw/intc/sifive_clint.c
32
similarity index 99%
33
rename from hw/riscv/sifive_clint.c
34
rename to hw/intc/sifive_clint.c
35
index XXXXXXX..XXXXXXX 100644
36
--- a/hw/riscv/sifive_clint.c
37
+++ b/hw/intc/sifive_clint.c
38
@@ -XXX,XX +XXX,XX @@
39
#include "hw/sysbus.h"
40
#include "target/riscv/cpu.h"
41
#include "hw/qdev-properties.h"
42
-#include "hw/riscv/sifive_clint.h"
43
+#include "hw/intc/sifive_clint.h"
44
#include "qemu/timer.h"
45
46
static uint64_t cpu_riscv_read_rtc(uint32_t timebase_freq)
47
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
48
index XXXXXXX..XXXXXXX 100644
49
--- a/hw/riscv/microchip_pfsoc.c
50
+++ b/hw/riscv/microchip_pfsoc.c
51
@@ -XXX,XX +XXX,XX @@
52
#include "hw/misc/unimp.h"
53
#include "hw/riscv/boot.h"
54
#include "hw/riscv/riscv_hart.h"
55
-#include "hw/riscv/sifive_clint.h"
56
#include "hw/riscv/sifive_plic.h"
57
#include "hw/riscv/microchip_pfsoc.h"
58
+#include "hw/intc/sifive_clint.h"
59
#include "sysemu/sysemu.h"
60
61
/*
62
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
63
index XXXXXXX..XXXXXXX 100644
64
--- a/hw/riscv/sifive_e.c
65
+++ b/hw/riscv/sifive_e.c
66
@@ -XXX,XX +XXX,XX @@
67
#include "target/riscv/cpu.h"
68
#include "hw/riscv/riscv_hart.h"
69
#include "hw/riscv/sifive_plic.h"
70
-#include "hw/riscv/sifive_clint.h"
71
#include "hw/riscv/sifive_uart.h"
72
#include "hw/riscv/sifive_e.h"
73
#include "hw/riscv/boot.h"
74
+#include "hw/intc/sifive_clint.h"
75
#include "hw/misc/sifive_e_prci.h"
76
#include "chardev/char.h"
77
#include "sysemu/arch_init.h"
78
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
79
index XXXXXXX..XXXXXXX 100644
80
--- a/hw/riscv/sifive_u.c
81
+++ b/hw/riscv/sifive_u.c
82
@@ -XXX,XX +XXX,XX @@
83
#include "target/riscv/cpu.h"
84
#include "hw/riscv/riscv_hart.h"
85
#include "hw/riscv/sifive_plic.h"
86
-#include "hw/riscv/sifive_clint.h"
87
#include "hw/riscv/sifive_uart.h"
88
#include "hw/riscv/sifive_u.h"
89
#include "hw/riscv/boot.h"
90
+#include "hw/intc/sifive_clint.h"
91
#include "chardev/char.h"
92
#include "net/eth.h"
93
#include "sysemu/arch_init.h"
94
diff --git a/hw/riscv/spike.c b/hw/riscv/spike.c
95
index XXXXXXX..XXXXXXX 100644
96
--- a/hw/riscv/spike.c
97
+++ b/hw/riscv/spike.c
98
@@ -XXX,XX +XXX,XX @@
99
#include "target/riscv/cpu.h"
100
#include "hw/riscv/riscv_htif.h"
101
#include "hw/riscv/riscv_hart.h"
102
-#include "hw/riscv/sifive_clint.h"
103
#include "hw/riscv/spike.h"
104
#include "hw/riscv/boot.h"
105
#include "hw/riscv/numa.h"
106
+#include "hw/intc/sifive_clint.h"
107
#include "chardev/char.h"
108
#include "sysemu/arch_init.h"
109
#include "sysemu/device_tree.h"
110
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
43
diff --git a/hw/riscv/virt.c b/hw/riscv/virt.c
111
index XXXXXXX..XXXXXXX 100644
44
index XXXXXXX..XXXXXXX 100644
112
--- a/hw/riscv/virt.c
45
--- a/hw/riscv/virt.c
113
+++ b/hw/riscv/virt.c
46
+++ b/hw/riscv/virt.c
114
@@ -XXX,XX +XXX,XX @@
47
@@ -XXX,XX +XXX,XX @@ static void create_fdt_socket_cpus(RISCVVirtState *s, int socket,
115
#include "target/riscv/cpu.h"
48
s->soc[socket].hartid_base + cpu);
116
#include "hw/riscv/riscv_hart.h"
49
qemu_fdt_add_subnode(ms->fdt, cpu_name);
117
#include "hw/riscv/sifive_plic.h"
50
118
-#include "hw/riscv/sifive_clint.h"
51
- satp_mode_max = satp_mode_max_from_map(
119
#include "hw/riscv/sifive_test.h"
52
- s->soc[socket].harts[cpu].cfg.satp_mode.map);
120
#include "hw/riscv/virt.h"
53
- sv_name = g_strdup_printf("riscv,%s",
121
#include "hw/riscv/boot.h"
54
- satp_mode_str(satp_mode_max, is_32_bit));
122
#include "hw/riscv/numa.h"
55
- qemu_fdt_setprop_string(ms->fdt, cpu_name, "mmu-type", sv_name);
123
+#include "hw/intc/sifive_clint.h"
56
- g_free(sv_name);
124
#include "chardev/char.h"
57
-
125
#include "sysemu/arch_init.h"
58
+ if (cpu_ptr->cfg.satp_mode.supported != 0) {
126
#include "sysemu/device_tree.h"
59
+ satp_mode_max = satp_mode_max_from_map(cpu_ptr->cfg.satp_mode.map);
127
diff --git a/hw/intc/Kconfig b/hw/intc/Kconfig
60
+ sv_name = g_strdup_printf("riscv,%s",
128
index XXXXXXX..XXXXXXX 100644
61
+ satp_mode_str(satp_mode_max, is_32_bit));
129
--- a/hw/intc/Kconfig
62
+ qemu_fdt_setprop_string(ms->fdt, cpu_name, "mmu-type", sv_name);
130
+++ b/hw/intc/Kconfig
63
+ g_free(sv_name);
131
@@ -XXX,XX +XXX,XX @@ config RX_ICU
64
+ }
132
65
133
config LOONGSON_LIOINTC
66
name = riscv_isa_string(cpu_ptr);
134
bool
67
qemu_fdt_setprop_string(ms->fdt, cpu_name, "riscv,isa", name);
135
+
136
+config SIFIVE_CLINT
137
+ bool
138
diff --git a/hw/intc/meson.build b/hw/intc/meson.build
139
index XXXXXXX..XXXXXXX 100644
140
--- a/hw/intc/meson.build
141
+++ b/hw/intc/meson.build
142
@@ -XXX,XX +XXX,XX @@ specific_ss.add(when: 'CONFIG_RX_ICU', if_true: files('rx_icu.c'))
143
specific_ss.add(when: 'CONFIG_S390_FLIC', if_true: files('s390_flic.c'))
144
specific_ss.add(when: 'CONFIG_S390_FLIC_KVM', if_true: files('s390_flic_kvm.c'))
145
specific_ss.add(when: 'CONFIG_SH4', if_true: files('sh_intc.c'))
146
+specific_ss.add(when: 'CONFIG_SIFIVE_CLINT', if_true: files('sifive_clint.c'))
147
specific_ss.add(when: 'CONFIG_XICS', if_true: files('xics.c'))
148
specific_ss.add(when: 'CONFIG_XICS_KVM', if_true: files('xics_kvm.c'))
149
specific_ss.add(when: 'CONFIG_XICS_SPAPR', if_true: files('xics_spapr.c'))
150
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
151
index XXXXXXX..XXXXXXX 100644
152
--- a/hw/riscv/Kconfig
153
+++ b/hw/riscv/Kconfig
154
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
155
bool
156
select HART
157
select SIFIVE
158
+ select SIFIVE_CLINT
159
select SIFIVE_GPIO
160
select SIFIVE_E_PRCI
161
select UNIMP
162
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
163
select CADENCE
164
select HART
165
select SIFIVE
166
+ select SIFIVE_CLINT
167
select SIFIVE_GPIO
168
select SIFIVE_PDMA
169
select SIFIVE_U_OTP
170
@@ -XXX,XX +XXX,XX @@ config SPIKE
171
select HART
172
select HTIF
173
select SIFIVE
174
+ select SIFIVE_CLINT
175
176
config OPENTITAN
177
bool
178
@@ -XXX,XX +XXX,XX @@ config RISCV_VIRT
179
select PCI_EXPRESS_GENERIC_BRIDGE
180
select PFLASH_CFI01
181
select SIFIVE
182
+ select SIFIVE_CLINT
183
184
config MICROCHIP_PFSOC
185
bool
186
select HART
187
select SIFIVE
188
+ select SIFIVE_CLINT
189
select UNIMP
190
select MCHP_PFSOC_MMUART
191
select SIFIVE_PDMA
192
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
193
index XXXXXXX..XXXXXXX 100644
194
--- a/hw/riscv/meson.build
195
+++ b/hw/riscv/meson.build
196
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(files('numa.c'))
197
riscv_ss.add(when: 'CONFIG_HART', if_true: files('riscv_hart.c'))
198
riscv_ss.add(when: 'CONFIG_OPENTITAN', if_true: files('opentitan.c'))
199
riscv_ss.add(when: 'CONFIG_RISCV_VIRT', if_true: files('virt.c'))
200
-riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_clint.c'))
201
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_plic.c'))
202
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
203
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
204
--
68
--
205
2.28.0
69
2.40.1
206
70
207
71
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
SiFive FU540 SoC integrates a platform DMA controller with 4 DMA
3
We're going to change the handling of mvendorid/marchid/mimpid by the
4
channels. This connects the exsiting SiFive PDMA model to the SoC,
4
KVM driver. Since these are always present in all CPUs let's put the
5
and adds its device tree data as well.
5
same validation for everyone.
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
It doesn't make sense to allow 'mvendorid' to be different than it
8
is already set in named (vendor) CPUs. Generic (dynamic) CPUs can have
9
any 'mvendorid' they want.
10
11
Change 'mvendorid' to be a class property created via
12
'object_class_property_add', instead of using the DEFINE_PROP_UINT32()
13
macro. This allow us to define a custom setter for it that will verify,
14
for named CPUs, if mvendorid is different than it is already set by the
15
CPU. This is the error thrown for the 'veyron-v1' CPU if 'mvendorid' is
16
set to an invalid value:
17
18
$ qemu-system-riscv64 -M virt -nographic -cpu veyron-v1,mvendorid=2
19
qemu-system-riscv64: can't apply global veyron-v1-riscv-cpu.mvendorid=2:
20
Unable to change veyron-v1-riscv-cpu mvendorid (0x61f)
21
22
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
23
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
24
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1598924352-89526-17-git-send-email-bmeng.cn@gmail.com>
25
Message-Id: <20230706101738.460804-4-dbarboza@ventanamicro.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
26
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
27
---
12
include/hw/riscv/sifive_u.h | 11 +++++++++++
28
target/riscv/cpu.c | 38 +++++++++++++++++++++++++++++++++++++-
13
hw/riscv/sifive_u.c | 30 ++++++++++++++++++++++++++++++
29
1 file changed, 37 insertions(+), 1 deletion(-)
14
hw/riscv/Kconfig | 1 +
15
3 files changed, 42 insertions(+)
16
30
17
diff --git a/include/hw/riscv/sifive_u.h b/include/hw/riscv/sifive_u.h
31
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
18
index XXXXXXX..XXXXXXX 100644
32
index XXXXXXX..XXXXXXX 100644
19
--- a/include/hw/riscv/sifive_u.h
33
--- a/target/riscv/cpu.c
20
+++ b/include/hw/riscv/sifive_u.h
34
+++ b/target/riscv/cpu.c
21
@@ -XXX,XX +XXX,XX @@
35
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
22
#ifndef HW_SIFIVE_U_H
36
static Property riscv_cpu_properties[] = {
23
#define HW_SIFIVE_U_H
37
DEFINE_PROP_BOOL("debug", RISCVCPU, cfg.debug, true),
24
38
25
+#include "hw/dma/sifive_pdma.h"
39
- DEFINE_PROP_UINT32("mvendorid", RISCVCPU, cfg.mvendorid, 0),
26
#include "hw/net/cadence_gem.h"
40
DEFINE_PROP_UINT64("marchid", RISCVCPU, cfg.marchid, RISCV_CPU_MARCHID),
27
#include "hw/riscv/riscv_hart.h"
41
DEFINE_PROP_UINT64("mimpid", RISCVCPU, cfg.mimpid, RISCV_CPU_MIMPID),
28
#include "hw/riscv/sifive_cpu.h"
42
29
@@ -XXX,XX +XXX,XX @@ typedef struct SiFiveUSoCState {
43
@@ -XXX,XX +XXX,XX @@ static const struct TCGCPUOps riscv_tcg_ops = {
30
SiFiveUPRCIState prci;
44
#endif /* !CONFIG_USER_ONLY */
31
SIFIVEGPIOState gpio;
32
SiFiveUOTPState otp;
33
+ SiFivePDMAState dma;
34
CadenceGEMState gem;
35
36
uint32_t serial;
37
@@ -XXX,XX +XXX,XX @@ enum {
38
SIFIVE_U_MROM,
39
SIFIVE_U_CLINT,
40
SIFIVE_U_L2CC,
41
+ SIFIVE_U_PDMA,
42
SIFIVE_U_L2LIM,
43
SIFIVE_U_PLIC,
44
SIFIVE_U_PRCI,
45
@@ -XXX,XX +XXX,XX @@ enum {
46
SIFIVE_U_GPIO_IRQ13 = 20,
47
SIFIVE_U_GPIO_IRQ14 = 21,
48
SIFIVE_U_GPIO_IRQ15 = 22,
49
+ SIFIVE_U_PDMA_IRQ0 = 23,
50
+ SIFIVE_U_PDMA_IRQ1 = 24,
51
+ SIFIVE_U_PDMA_IRQ2 = 25,
52
+ SIFIVE_U_PDMA_IRQ3 = 26,
53
+ SIFIVE_U_PDMA_IRQ4 = 27,
54
+ SIFIVE_U_PDMA_IRQ5 = 28,
55
+ SIFIVE_U_PDMA_IRQ6 = 29,
56
+ SIFIVE_U_PDMA_IRQ7 = 30,
57
SIFIVE_U_GEM_IRQ = 0x35
58
};
45
};
59
46
60
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
47
+static bool riscv_cpu_is_dynamic(Object *cpu_obj)
61
index XXXXXXX..XXXXXXX 100644
48
+{
62
--- a/hw/riscv/sifive_u.c
49
+ return object_dynamic_cast(cpu_obj, TYPE_RISCV_DYNAMIC_CPU) != NULL;
63
+++ b/hw/riscv/sifive_u.c
50
+}
64
@@ -XXX,XX +XXX,XX @@
65
* 4) GPIO (General Purpose Input/Output Controller)
66
* 5) OTP (One-Time Programmable) memory with stored serial number
67
* 6) GEM (Gigabit Ethernet Controller) and management block
68
+ * 7) DMA (Direct Memory Access Controller)
69
*
70
* This board currently generates devicetree dynamically that indicates at least
71
* two harts and up to five harts.
72
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
73
[SIFIVE_U_MROM] = { 0x1000, 0xf000 },
74
[SIFIVE_U_CLINT] = { 0x2000000, 0x10000 },
75
[SIFIVE_U_L2CC] = { 0x2010000, 0x1000 },
76
+ [SIFIVE_U_PDMA] = { 0x3000000, 0x100000 },
77
[SIFIVE_U_L2LIM] = { 0x8000000, 0x2000000 },
78
[SIFIVE_U_PLIC] = { 0xc000000, 0x4000000 },
79
[SIFIVE_U_PRCI] = { 0x10000000, 0x1000 },
80
@@ -XXX,XX +XXX,XX @@ static void create_fdt(SiFiveUState *s, const struct MemmapEntry *memmap,
81
qemu_fdt_setprop_string(fdt, nodename, "compatible", "gpio-restart");
82
g_free(nodename);
83
84
+ nodename = g_strdup_printf("/soc/dma@%lx",
85
+ (long)memmap[SIFIVE_U_PDMA].base);
86
+ qemu_fdt_add_subnode(fdt, nodename);
87
+ qemu_fdt_setprop_cell(fdt, nodename, "#dma-cells", 1);
88
+ qemu_fdt_setprop_cells(fdt, nodename, "interrupts",
89
+ SIFIVE_U_PDMA_IRQ0, SIFIVE_U_PDMA_IRQ1, SIFIVE_U_PDMA_IRQ2,
90
+ SIFIVE_U_PDMA_IRQ3, SIFIVE_U_PDMA_IRQ4, SIFIVE_U_PDMA_IRQ5,
91
+ SIFIVE_U_PDMA_IRQ6, SIFIVE_U_PDMA_IRQ7);
92
+ qemu_fdt_setprop_cell(fdt, nodename, "interrupt-parent", plic_phandle);
93
+ qemu_fdt_setprop_cells(fdt, nodename, "reg",
94
+ 0x0, memmap[SIFIVE_U_PDMA].base,
95
+ 0x0, memmap[SIFIVE_U_PDMA].size);
96
+ qemu_fdt_setprop_string(fdt, nodename, "compatible",
97
+ "sifive,fu540-c000-pdma");
98
+ g_free(nodename);
99
+
51
+
100
nodename = g_strdup_printf("/soc/cache-controller@%lx",
52
+static void cpu_set_mvendorid(Object *obj, Visitor *v, const char *name,
101
(long)memmap[SIFIVE_U_L2CC].base);
53
+ void *opaque, Error **errp)
102
qemu_fdt_add_subnode(fdt, nodename);
54
+{
103
@@ -XXX,XX +XXX,XX @@ static void sifive_u_soc_instance_init(Object *obj)
55
+ bool dynamic_cpu = riscv_cpu_is_dynamic(obj);
104
object_initialize_child(obj, "otp", &s->otp, TYPE_SIFIVE_U_OTP);
56
+ RISCVCPU *cpu = RISCV_CPU(obj);
105
object_initialize_child(obj, "gem", &s->gem, TYPE_CADENCE_GEM);
57
+ uint32_t prev_val = cpu->cfg.mvendorid;
106
object_initialize_child(obj, "gpio", &s->gpio, TYPE_SIFIVE_GPIO);
58
+ uint32_t value;
107
+ object_initialize_child(obj, "pdma", &s->dma, TYPE_SIFIVE_PDMA);
108
}
109
110
static void sifive_u_soc_realize(DeviceState *dev, Error **errp)
111
@@ -XXX,XX +XXX,XX @@ static void sifive_u_soc_realize(DeviceState *dev, Error **errp)
112
SIFIVE_U_GPIO_IRQ0 + i));
113
}
114
115
+ /* PDMA */
116
+ sysbus_realize(SYS_BUS_DEVICE(&s->dma), errp);
117
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->dma), 0, memmap[SIFIVE_U_PDMA].base);
118
+
59
+
119
+ /* Connect PDMA interrupts to the PLIC */
60
+ if (!visit_type_uint32(v, name, &value, errp)) {
120
+ for (i = 0; i < SIFIVE_PDMA_IRQS; i++) {
61
+ return;
121
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->dma), i,
122
+ qdev_get_gpio_in(DEVICE(s->plic),
123
+ SIFIVE_U_PDMA_IRQ0 + i));
124
+ }
62
+ }
125
+
63
+
126
qdev_prop_set_uint32(DEVICE(&s->otp), "serial", s->serial);
64
+ if (!dynamic_cpu && prev_val != value) {
127
if (!sysbus_realize(SYS_BUS_DEVICE(&s->otp), errp)) {
65
+ error_setg(errp, "Unable to change %s mvendorid (0x%x)",
128
return;
66
+ object_get_typename(obj), prev_val);
129
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
67
+ return;
130
index XXXXXXX..XXXXXXX 100644
68
+ }
131
--- a/hw/riscv/Kconfig
69
+
132
+++ b/hw/riscv/Kconfig
70
+ cpu->cfg.mvendorid = value;
133
@@ -XXX,XX +XXX,XX @@ config SIFIVE_U
71
+}
134
select CADENCE
72
+
135
select HART
73
+static void cpu_get_mvendorid(Object *obj, Visitor *v, const char *name,
136
select SIFIVE
74
+ void *opaque, Error **errp)
137
+ select SIFIVE_PDMA
75
+{
138
select UNIMP
76
+ bool value = RISCV_CPU(obj)->cfg.mvendorid;
139
77
+
140
config SPIKE
78
+ visit_type_bool(v, name, &value, errp);
79
+}
80
+
81
static void riscv_cpu_class_init(ObjectClass *c, void *data)
82
{
83
RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
84
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_class_init(ObjectClass *c, void *data)
85
cc->gdb_get_dynamic_xml = riscv_gdb_get_dynamic_xml;
86
cc->tcg_ops = &riscv_tcg_ops;
87
88
+ object_class_property_add(c, "mvendorid", "uint32", cpu_get_mvendorid,
89
+ cpu_set_mvendorid, NULL, NULL);
90
+
91
device_class_set_props(dc, riscv_cpu_properties);
92
}
93
141
--
94
--
142
2.28.0
95
2.40.1
143
144
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
Following the same logic used with 'mvendorid' let's also restrict
4
'mimpid' for named CPUs. Generic CPUs keep setting the value freely.
5
6
Note that we're getting rid of the default RISCV_CPU_MARCHID value. The
7
reason is that this is not a good default since it's dynamic, changing
8
with with every QEMU version, regardless of whether the actual
9
implementation of the CPU changed from one QEMU version to the other.
10
Named CPU should set it to a meaningful value instead and generic CPUs
11
can set whatever they want.
12
13
This is the error thrown for an invalid 'mimpid' value for the veyron-v1
14
CPU:
15
16
$ ./qemu-system-riscv64 -M virt -nographic -cpu veyron-v1,mimpid=2
17
qemu-system-riscv64: can't apply global veyron-v1-riscv-cpu.mimpid=2:
18
Unable to change veyron-v1-riscv-cpu mimpid (0x111)
19
20
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
21
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
22
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
23
Message-Id: <20230706101738.460804-5-dbarboza@ventanamicro.com>
24
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
25
---
26
target/riscv/cpu.c | 34 ++++++++++++++++++++++++++++++++--
27
1 file changed, 32 insertions(+), 2 deletions(-)
28
29
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
30
index XXXXXXX..XXXXXXX 100644
31
--- a/target/riscv/cpu.c
32
+++ b/target/riscv/cpu.c
33
@@ -XXX,XX +XXX,XX @@
34
#define RISCV_CPU_MARCHID ((QEMU_VERSION_MAJOR << 16) | \
35
(QEMU_VERSION_MINOR << 8) | \
36
(QEMU_VERSION_MICRO))
37
-#define RISCV_CPU_MIMPID RISCV_CPU_MARCHID
38
39
static const char riscv_single_letter_exts[] = "IEMAFDQCPVH";
40
41
@@ -XXX,XX +XXX,XX @@ static Property riscv_cpu_properties[] = {
42
DEFINE_PROP_BOOL("debug", RISCVCPU, cfg.debug, true),
43
44
DEFINE_PROP_UINT64("marchid", RISCVCPU, cfg.marchid, RISCV_CPU_MARCHID),
45
- DEFINE_PROP_UINT64("mimpid", RISCVCPU, cfg.mimpid, RISCV_CPU_MIMPID),
46
47
#ifndef CONFIG_USER_ONLY
48
DEFINE_PROP_UINT64("resetvec", RISCVCPU, env.resetvec, DEFAULT_RSTVEC),
49
@@ -XXX,XX +XXX,XX @@ static void cpu_get_mvendorid(Object *obj, Visitor *v, const char *name,
50
visit_type_bool(v, name, &value, errp);
51
}
52
53
+static void cpu_set_mimpid(Object *obj, Visitor *v, const char *name,
54
+ void *opaque, Error **errp)
55
+{
56
+ bool dynamic_cpu = riscv_cpu_is_dynamic(obj);
57
+ RISCVCPU *cpu = RISCV_CPU(obj);
58
+ uint64_t prev_val = cpu->cfg.mimpid;
59
+ uint64_t value;
60
+
61
+ if (!visit_type_uint64(v, name, &value, errp)) {
62
+ return;
63
+ }
64
+
65
+ if (!dynamic_cpu && prev_val != value) {
66
+ error_setg(errp, "Unable to change %s mimpid (0x%" PRIu64 ")",
67
+ object_get_typename(obj), prev_val);
68
+ return;
69
+ }
70
+
71
+ cpu->cfg.mimpid = value;
72
+}
73
+
74
+static void cpu_get_mimpid(Object *obj, Visitor *v, const char *name,
75
+ void *opaque, Error **errp)
76
+{
77
+ bool value = RISCV_CPU(obj)->cfg.mimpid;
78
+
79
+ visit_type_bool(v, name, &value, errp);
80
+}
81
+
82
static void riscv_cpu_class_init(ObjectClass *c, void *data)
83
{
84
RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
85
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_class_init(ObjectClass *c, void *data)
86
object_class_property_add(c, "mvendorid", "uint32", cpu_get_mvendorid,
87
cpu_set_mvendorid, NULL, NULL);
88
89
+ object_class_property_add(c, "mimpid", "uint64", cpu_get_mimpid,
90
+ cpu_set_mimpid, NULL, NULL);
91
+
92
device_class_set_props(dc, riscv_cpu_properties);
93
}
94
95
--
96
2.40.1
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
'marchid' shouldn't be set to a different value as previously set for
4
named CPUs.
5
6
For all other CPUs it shouldn't be freely set either - the spec requires
7
that 'marchid' can't have the MSB (most significant bit) set and every
8
other bit set to zero, i.e. 0x80000000 is an invalid 'marchid' value for
9
32 bit CPUs.
10
11
As with 'mimpid', setting a default value based on the current QEMU
12
version is not a good idea because it implies that the CPU
13
implementation changes from one QEMU version to the other. Named CPUs
14
should set 'marchid' to a meaningful value instead, and generic CPUs can
15
set to any valid value.
16
17
For the 'veyron-v1' CPU this is the error thrown if 'marchid' is set to
18
a different val:
19
20
$ ./build/qemu-system-riscv64 -M virt -nographic -cpu veyron-v1,marchid=0x80000000
21
qemu-system-riscv64: can't apply global veyron-v1-riscv-cpu.marchid=0x80000000:
22
Unable to change veyron-v1-riscv-cpu marchid (0x8000000000010000)
23
24
And, for generics CPUs, this is the error when trying to set to an
25
invalid val:
26
27
$ ./build/qemu-system-riscv64 -M virt -nographic -cpu rv64,marchid=0x8000000000000000
28
qemu-system-riscv64: can't apply global rv64-riscv-cpu.marchid=0x8000000000000000:
29
Unable to set marchid with MSB (64) bit set and the remaining bits zero
30
31
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
32
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
33
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
34
Message-Id: <20230706101738.460804-6-dbarboza@ventanamicro.com>
35
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
36
---
37
target/riscv/cpu.c | 60 ++++++++++++++++++++++++++++++++++++++++------
38
1 file changed, 53 insertions(+), 7 deletions(-)
39
40
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/target/riscv/cpu.c
43
+++ b/target/riscv/cpu.c
44
@@ -XXX,XX +XXX,XX @@
45
#include "tcg/tcg.h"
46
47
/* RISC-V CPU definitions */
48
-
49
-#define RISCV_CPU_MARCHID ((QEMU_VERSION_MAJOR << 16) | \
50
- (QEMU_VERSION_MINOR << 8) | \
51
- (QEMU_VERSION_MICRO))
52
-
53
static const char riscv_single_letter_exts[] = "IEMAFDQCPVH";
54
55
struct isa_ext_data {
56
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
57
static Property riscv_cpu_properties[] = {
58
DEFINE_PROP_BOOL("debug", RISCVCPU, cfg.debug, true),
59
60
- DEFINE_PROP_UINT64("marchid", RISCVCPU, cfg.marchid, RISCV_CPU_MARCHID),
61
-
62
#ifndef CONFIG_USER_ONLY
63
DEFINE_PROP_UINT64("resetvec", RISCVCPU, env.resetvec, DEFAULT_RSTVEC),
64
#endif
65
@@ -XXX,XX +XXX,XX @@ static void cpu_get_mimpid(Object *obj, Visitor *v, const char *name,
66
visit_type_bool(v, name, &value, errp);
67
}
68
69
+static void cpu_set_marchid(Object *obj, Visitor *v, const char *name,
70
+ void *opaque, Error **errp)
71
+{
72
+ bool dynamic_cpu = riscv_cpu_is_dynamic(obj);
73
+ RISCVCPU *cpu = RISCV_CPU(obj);
74
+ uint64_t prev_val = cpu->cfg.marchid;
75
+ uint64_t value, invalid_val;
76
+ uint32_t mxlen = 0;
77
+
78
+ if (!visit_type_uint64(v, name, &value, errp)) {
79
+ return;
80
+ }
81
+
82
+ if (!dynamic_cpu && prev_val != value) {
83
+ error_setg(errp, "Unable to change %s marchid (0x%" PRIu64 ")",
84
+ object_get_typename(obj), prev_val);
85
+ return;
86
+ }
87
+
88
+ switch (riscv_cpu_mxl(&cpu->env)) {
89
+ case MXL_RV32:
90
+ mxlen = 32;
91
+ break;
92
+ case MXL_RV64:
93
+ case MXL_RV128:
94
+ mxlen = 64;
95
+ break;
96
+ default:
97
+ g_assert_not_reached();
98
+ }
99
+
100
+ invalid_val = 1LL << (mxlen - 1);
101
+
102
+ if (value == invalid_val) {
103
+ error_setg(errp, "Unable to set marchid with MSB (%u) bit set "
104
+ "and the remaining bits zero", mxlen);
105
+ return;
106
+ }
107
+
108
+ cpu->cfg.marchid = value;
109
+}
110
+
111
+static void cpu_get_marchid(Object *obj, Visitor *v, const char *name,
112
+ void *opaque, Error **errp)
113
+{
114
+ bool value = RISCV_CPU(obj)->cfg.marchid;
115
+
116
+ visit_type_bool(v, name, &value, errp);
117
+}
118
+
119
static void riscv_cpu_class_init(ObjectClass *c, void *data)
120
{
121
RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
122
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_class_init(ObjectClass *c, void *data)
123
object_class_property_add(c, "mimpid", "uint64", cpu_get_mimpid,
124
cpu_set_mimpid, NULL, NULL);
125
126
+ object_class_property_add(c, "marchid", "uint64", cpu_get_marchid,
127
+ cpu_set_marchid, NULL, NULL);
128
+
129
device_class_set_props(dc, riscv_cpu_properties);
130
}
131
132
--
133
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
Microchip PolarFire SoC integrates a DMA engine that supports:
3
Certain validations, such as the validations done for the machine IDs
4
* Independent concurrent DMA transfers using 4 DMA channels
4
(mvendorid/marchid/mimpid), are done before starting the CPU.
5
* Generation of interrupts on various conditions during execution
5
Non-dynamic (named) CPUs tries to match user input with a preset
6
which is actually an IP reused from the SiFive FU540 chip.
6
default. As it is today we can't prefetch a KVM default for these cases
7
because we're only able to read/write KVM regs after the vcpu is
8
spinning.
7
9
8
This creates a model to support both polling and interrupt modes.
10
Our target/arm friends use a concept called "scratch CPU", which
11
consists of creating a vcpu for doing queries and validations and so on,
12
which is discarded shortly after use [1]. This is a suitable solution
13
for what we need so let's implement it in target/riscv as well.
9
14
10
Signed-off-by: Bin Meng <bin.meng@windriver.com>
15
kvm_riscv_init_machine_ids() will be used to do any pre-launch setup for
16
KVM CPUs, via riscv_cpu_add_user_properties(). The function will create
17
a KVM scratch CPU, fetch KVM regs that work as default values for user
18
properties, and then discard the scratch CPU afterwards.
19
20
We're starting by initializing 'mvendorid'. This concept will be used to
21
init other KVM specific properties in the next patches as well.
22
23
[1] target/arm/kvm.c, kvm_arm_create_scratch_host_vcpu()
24
25
Suggested-by: Andrew Jones <ajones@ventanamicro.com>
26
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
27
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
11
Acked-by: Alistair Francis <alistair.francis@wdc.com>
28
Acked-by: Alistair Francis <alistair.francis@wdc.com>
12
Message-Id: <1598924352-89526-10-git-send-email-bmeng.cn@gmail.com>
29
Message-Id: <20230706101738.460804-7-dbarboza@ventanamicro.com>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
30
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
14
---
31
---
15
include/hw/dma/sifive_pdma.h | 57 +++++++
32
target/riscv/kvm_riscv.h | 1 +
16
hw/dma/sifive_pdma.c | 313 +++++++++++++++++++++++++++++++++++
33
target/riscv/cpu.c | 6 +++
17
hw/dma/Kconfig | 3 +
34
target/riscv/kvm.c | 85 ++++++++++++++++++++++++++++++++++++++++
18
hw/dma/meson.build | 1 +
35
3 files changed, 92 insertions(+)
19
4 files changed, 374 insertions(+)
20
create mode 100644 include/hw/dma/sifive_pdma.h
21
create mode 100644 hw/dma/sifive_pdma.c
22
36
23
diff --git a/include/hw/dma/sifive_pdma.h b/include/hw/dma/sifive_pdma.h
37
diff --git a/target/riscv/kvm_riscv.h b/target/riscv/kvm_riscv.h
24
new file mode 100644
38
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX
39
--- a/target/riscv/kvm_riscv.h
26
--- /dev/null
40
+++ b/target/riscv/kvm_riscv.h
27
+++ b/include/hw/dma/sifive_pdma.h
28
@@ -XXX,XX +XXX,XX @@
41
@@ -XXX,XX +XXX,XX @@
42
#ifndef QEMU_KVM_RISCV_H
43
#define QEMU_KVM_RISCV_H
44
45
+void kvm_riscv_init_user_properties(Object *cpu_obj);
46
void kvm_riscv_reset_vcpu(RISCVCPU *cpu);
47
void kvm_riscv_set_irq(RISCVCPU *cpu, int irq, int level);
48
49
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
50
index XXXXXXX..XXXXXXX 100644
51
--- a/target/riscv/cpu.c
52
+++ b/target/riscv/cpu.c
53
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
54
Property *prop;
55
DeviceState *dev = DEVICE(obj);
56
57
+#ifndef CONFIG_USER_ONLY
58
+ if (kvm_enabled()) {
59
+ kvm_riscv_init_user_properties(obj);
60
+ }
61
+#endif
62
+
63
riscv_cpu_add_misa_properties(obj);
64
65
for (prop = riscv_cpu_extensions; prop && prop->name; prop++) {
66
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
67
index XXXXXXX..XXXXXXX 100644
68
--- a/target/riscv/kvm.c
69
+++ b/target/riscv/kvm.c
70
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_put_regs_timer(CPUState *cs)
71
env->kvm_timer_dirty = false;
72
}
73
74
+typedef struct KVMScratchCPU {
75
+ int kvmfd;
76
+ int vmfd;
77
+ int cpufd;
78
+} KVMScratchCPU;
79
+
29
+/*
80
+/*
30
+ * SiFive Platform DMA emulation
81
+ * Heavily inspired by kvm_arm_create_scratch_host_vcpu()
31
+ *
82
+ * from target/arm/kvm.c.
32
+ * Copyright (c) 2020 Wind River Systems, Inc.
33
+ *
34
+ * Author:
35
+ * Bin Meng <bin.meng@windriver.com>
36
+ *
37
+ * This program is free software; you can redistribute it and/or
38
+ * modify it under the terms of the GNU General Public License as
39
+ * published by the Free Software Foundation; either version 2 or
40
+ * (at your option) version 3 of the License.
41
+ *
42
+ * This program is distributed in the hope that it will be useful,
43
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
44
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
45
+ * GNU General Public License for more details.
46
+ *
47
+ * You should have received a copy of the GNU General Public License along
48
+ * with this program; if not, see <http://www.gnu.org/licenses/>.
49
+ */
83
+ */
84
+static bool kvm_riscv_create_scratch_vcpu(KVMScratchCPU *scratch)
85
+{
86
+ int kvmfd = -1, vmfd = -1, cpufd = -1;
50
+
87
+
51
+#ifndef SIFIVE_PDMA_H
88
+ kvmfd = qemu_open_old("/dev/kvm", O_RDWR);
52
+#define SIFIVE_PDMA_H
89
+ if (kvmfd < 0) {
53
+
90
+ goto err;
54
+struct sifive_pdma_chan {
91
+ }
55
+ uint32_t control;
92
+ do {
56
+ uint32_t next_config;
93
+ vmfd = ioctl(kvmfd, KVM_CREATE_VM, 0);
57
+ uint64_t next_bytes;
94
+ } while (vmfd == -1 && errno == EINTR);
58
+ uint64_t next_dst;
95
+ if (vmfd < 0) {
59
+ uint64_t next_src;
96
+ goto err;
60
+ uint32_t exec_config;
97
+ }
61
+ uint64_t exec_bytes;
98
+ cpufd = ioctl(vmfd, KVM_CREATE_VCPU, 0);
62
+ uint64_t exec_dst;
99
+ if (cpufd < 0) {
63
+ uint64_t exec_src;
100
+ goto err;
64
+ int state;
65
+};
66
+
67
+#define SIFIVE_PDMA_CHANS 4
68
+#define SIFIVE_PDMA_IRQS (SIFIVE_PDMA_CHANS * 2)
69
+#define SIFIVE_PDMA_REG_SIZE 0x100000
70
+#define SIFIVE_PDMA_CHAN_NO(reg) ((reg & (SIFIVE_PDMA_REG_SIZE - 1)) >> 12)
71
+
72
+typedef struct SiFivePDMAState {
73
+ SysBusDevice parent;
74
+ MemoryRegion iomem;
75
+ qemu_irq irq[SIFIVE_PDMA_IRQS];
76
+
77
+ struct sifive_pdma_chan chan[SIFIVE_PDMA_CHANS];
78
+} SiFivePDMAState;
79
+
80
+#define TYPE_SIFIVE_PDMA "sifive.pdma"
81
+
82
+#define SIFIVE_PDMA(obj) \
83
+ OBJECT_CHECK(SiFivePDMAState, (obj), TYPE_SIFIVE_PDMA)
84
+
85
+#endif /* SIFIVE_PDMA_H */
86
diff --git a/hw/dma/sifive_pdma.c b/hw/dma/sifive_pdma.c
87
new file mode 100644
88
index XXXXXXX..XXXXXXX
89
--- /dev/null
90
+++ b/hw/dma/sifive_pdma.c
91
@@ -XXX,XX +XXX,XX @@
92
+/*
93
+ * SiFive Platform DMA emulation
94
+ *
95
+ * Copyright (c) 2020 Wind River Systems, Inc.
96
+ *
97
+ * Author:
98
+ * Bin Meng <bin.meng@windriver.com>
99
+ *
100
+ * This program is free software; you can redistribute it and/or
101
+ * modify it under the terms of the GNU General Public License as
102
+ * published by the Free Software Foundation; either version 2 or
103
+ * (at your option) version 3 of the License.
104
+ *
105
+ * This program is distributed in the hope that it will be useful,
106
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
107
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
108
+ * GNU General Public License for more details.
109
+ *
110
+ * You should have received a copy of the GNU General Public License along
111
+ * with this program; if not, see <http://www.gnu.org/licenses/>.
112
+ */
113
+
114
+#include "qemu/osdep.h"
115
+#include "qemu/bitops.h"
116
+#include "qemu/log.h"
117
+#include "qapi/error.h"
118
+#include "hw/hw.h"
119
+#include "hw/irq.h"
120
+#include "hw/qdev-properties.h"
121
+#include "hw/sysbus.h"
122
+#include "migration/vmstate.h"
123
+#include "sysemu/dma.h"
124
+#include "hw/dma/sifive_pdma.h"
125
+
126
+#define DMA_CONTROL 0x000
127
+#define CONTROL_CLAIM BIT(0)
128
+#define CONTROL_RUN BIT(1)
129
+#define CONTROL_DONE_IE BIT(14)
130
+#define CONTROL_ERR_IE BIT(15)
131
+#define CONTROL_DONE BIT(30)
132
+#define CONTROL_ERR BIT(31)
133
+
134
+#define DMA_NEXT_CONFIG 0x004
135
+#define CONFIG_REPEAT BIT(2)
136
+#define CONFIG_ORDER BIT(3)
137
+#define CONFIG_WRSZ_SHIFT 24
138
+#define CONFIG_RDSZ_SHIFT 28
139
+#define CONFIG_SZ_MASK 0xf
140
+
141
+#define DMA_NEXT_BYTES 0x008
142
+#define DMA_NEXT_DST 0x010
143
+#define DMA_NEXT_SRC 0x018
144
+#define DMA_EXEC_CONFIG 0x104
145
+#define DMA_EXEC_BYTES 0x108
146
+#define DMA_EXEC_DST 0x110
147
+#define DMA_EXEC_SRC 0x118
148
+
149
+enum dma_chan_state {
150
+ DMA_CHAN_STATE_IDLE,
151
+ DMA_CHAN_STATE_STARTED,
152
+ DMA_CHAN_STATE_ERROR,
153
+ DMA_CHAN_STATE_DONE
154
+};
155
+
156
+static void sifive_pdma_run(SiFivePDMAState *s, int ch)
157
+{
158
+ uint64_t bytes = s->chan[ch].next_bytes;
159
+ uint64_t dst = s->chan[ch].next_dst;
160
+ uint64_t src = s->chan[ch].next_src;
161
+ uint32_t config = s->chan[ch].next_config;
162
+ int wsize, rsize, size;
163
+ uint8_t buf[64];
164
+ int n;
165
+
166
+ /* do nothing if bytes to transfer is zero */
167
+ if (!bytes) {
168
+ goto error;
169
+ }
101
+ }
170
+
102
+
171
+ /*
103
+ scratch->kvmfd = kvmfd;
172
+ * The manual does not describe how the hardware behaviors when
104
+ scratch->vmfd = vmfd;
173
+ * config.wsize and config.rsize are given different values.
105
+ scratch->cpufd = cpufd;
174
+ * A common case is memory to memory DMA, and in this case they
106
+
175
+ * are normally the same. Abort if this expectation fails.
107
+ return true;
176
+ */
108
+
177
+ wsize = (config >> CONFIG_WRSZ_SHIFT) & CONFIG_SZ_MASK;
109
+ err:
178
+ rsize = (config >> CONFIG_RDSZ_SHIFT) & CONFIG_SZ_MASK;
110
+ if (cpufd >= 0) {
179
+ if (wsize != rsize) {
111
+ close(cpufd);
180
+ goto error;
112
+ }
113
+ if (vmfd >= 0) {
114
+ close(vmfd);
115
+ }
116
+ if (kvmfd >= 0) {
117
+ close(kvmfd);
181
+ }
118
+ }
182
+
119
+
183
+ /*
120
+ return false;
184
+ * Calculate the transaction size
185
+ *
186
+ * size field is base 2 logarithm of DMA transaction size,
187
+ * but there is an upper limit of 64 bytes per transaction.
188
+ */
189
+ size = wsize;
190
+ if (size > 6) {
191
+ size = 6;
192
+ }
193
+ size = 1 << size;
194
+
195
+ /* the bytes to transfer should be multiple of transaction size */
196
+ if (bytes % size) {
197
+ goto error;
198
+ }
199
+
200
+ /* indicate a DMA transfer is started */
201
+ s->chan[ch].state = DMA_CHAN_STATE_STARTED;
202
+ s->chan[ch].control &= ~CONTROL_DONE;
203
+ s->chan[ch].control &= ~CONTROL_ERR;
204
+
205
+ /* load the next_ registers into their exec_ counterparts */
206
+ s->chan[ch].exec_config = config;
207
+ s->chan[ch].exec_bytes = bytes;
208
+ s->chan[ch].exec_dst = dst;
209
+ s->chan[ch].exec_src = src;
210
+
211
+ for (n = 0; n < bytes / size; n++) {
212
+ cpu_physical_memory_read(s->chan[ch].exec_src, buf, size);
213
+ cpu_physical_memory_write(s->chan[ch].exec_dst, buf, size);
214
+ s->chan[ch].exec_src += size;
215
+ s->chan[ch].exec_dst += size;
216
+ s->chan[ch].exec_bytes -= size;
217
+ }
218
+
219
+ /* indicate a DMA transfer is done */
220
+ s->chan[ch].state = DMA_CHAN_STATE_DONE;
221
+ s->chan[ch].control &= ~CONTROL_RUN;
222
+ s->chan[ch].control |= CONTROL_DONE;
223
+
224
+ /* reload exec_ registers if repeat is required */
225
+ if (s->chan[ch].next_config & CONFIG_REPEAT) {
226
+ s->chan[ch].exec_bytes = bytes;
227
+ s->chan[ch].exec_dst = dst;
228
+ s->chan[ch].exec_src = src;
229
+ }
230
+
231
+ return;
232
+
233
+error:
234
+ s->chan[ch].state = DMA_CHAN_STATE_ERROR;
235
+ s->chan[ch].control |= CONTROL_ERR;
236
+ return;
237
+}
121
+}
238
+
122
+
239
+static inline void sifive_pdma_update_irq(SiFivePDMAState *s, int ch)
123
+static void kvm_riscv_destroy_scratch_vcpu(KVMScratchCPU *scratch)
240
+{
124
+{
241
+ bool done_ie, err_ie;
125
+ close(scratch->cpufd);
242
+
126
+ close(scratch->vmfd);
243
+ done_ie = !!(s->chan[ch].control & CONTROL_DONE_IE);
127
+ close(scratch->kvmfd);
244
+ err_ie = !!(s->chan[ch].control & CONTROL_ERR_IE);
245
+
246
+ if (done_ie && (s->chan[ch].control & CONTROL_DONE)) {
247
+ qemu_irq_raise(s->irq[ch * 2]);
248
+ } else {
249
+ qemu_irq_lower(s->irq[ch * 2]);
250
+ }
251
+
252
+ if (err_ie && (s->chan[ch].control & CONTROL_ERR)) {
253
+ qemu_irq_raise(s->irq[ch * 2 + 1]);
254
+ } else {
255
+ qemu_irq_lower(s->irq[ch * 2 + 1]);
256
+ }
257
+
258
+ s->chan[ch].state = DMA_CHAN_STATE_IDLE;
259
+}
128
+}
260
+
129
+
261
+static uint64_t sifive_pdma_read(void *opaque, hwaddr offset, unsigned size)
130
+static void kvm_riscv_init_machine_ids(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
262
+{
131
+{
263
+ SiFivePDMAState *s = opaque;
132
+ CPURISCVState *env = &cpu->env;
264
+ int ch = SIFIVE_PDMA_CHAN_NO(offset);
133
+ struct kvm_one_reg reg;
265
+ uint64_t val = 0;
134
+ int ret;
266
+
135
+
267
+ if (ch >= SIFIVE_PDMA_CHANS) {
136
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
268
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: Invalid channel no %d\n",
137
+ KVM_REG_RISCV_CONFIG_REG(mvendorid));
269
+ __func__, ch);
138
+ reg.addr = (uint64_t)&cpu->cfg.mvendorid;
270
+ return 0;
139
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
140
+ if (ret != 0) {
141
+ error_report("Unable to retrieve mvendorid from host, error %d", ret);
271
+ }
142
+ }
272
+
273
+ offset &= 0xfff;
274
+ switch (offset) {
275
+ case DMA_CONTROL:
276
+ val = s->chan[ch].control;
277
+ break;
278
+ case DMA_NEXT_CONFIG:
279
+ val = s->chan[ch].next_config;
280
+ break;
281
+ case DMA_NEXT_BYTES:
282
+ val = s->chan[ch].next_bytes;
283
+ break;
284
+ case DMA_NEXT_DST:
285
+ val = s->chan[ch].next_dst;
286
+ break;
287
+ case DMA_NEXT_SRC:
288
+ val = s->chan[ch].next_src;
289
+ break;
290
+ case DMA_EXEC_CONFIG:
291
+ val = s->chan[ch].exec_config;
292
+ break;
293
+ case DMA_EXEC_BYTES:
294
+ val = s->chan[ch].exec_bytes;
295
+ break;
296
+ case DMA_EXEC_DST:
297
+ val = s->chan[ch].exec_dst;
298
+ break;
299
+ case DMA_EXEC_SRC:
300
+ val = s->chan[ch].exec_src;
301
+ break;
302
+ default:
303
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%" HWADDR_PRIX "\n",
304
+ __func__, offset);
305
+ break;
306
+ }
307
+
308
+ return val;
309
+}
143
+}
310
+
144
+
311
+static void sifive_pdma_write(void *opaque, hwaddr offset,
145
+void kvm_riscv_init_user_properties(Object *cpu_obj)
312
+ uint64_t value, unsigned size)
313
+{
146
+{
314
+ SiFivePDMAState *s = opaque;
147
+ RISCVCPU *cpu = RISCV_CPU(cpu_obj);
315
+ int ch = SIFIVE_PDMA_CHAN_NO(offset);
148
+ KVMScratchCPU kvmcpu;
316
+
149
+
317
+ if (ch >= SIFIVE_PDMA_CHANS) {
150
+ if (!kvm_riscv_create_scratch_vcpu(&kvmcpu)) {
318
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: Invalid channel no %d\n",
319
+ __func__, ch);
320
+ return;
151
+ return;
321
+ }
152
+ }
322
+
153
+
323
+ offset &= 0xfff;
154
+ kvm_riscv_init_machine_ids(cpu, &kvmcpu);
324
+ switch (offset) {
325
+ case DMA_CONTROL:
326
+ s->chan[ch].control = value;
327
+
155
+
328
+ if (value & CONTROL_RUN) {
156
+ kvm_riscv_destroy_scratch_vcpu(&kvmcpu);
329
+ sifive_pdma_run(s, ch);
330
+ }
331
+
332
+ sifive_pdma_update_irq(s, ch);
333
+ break;
334
+ case DMA_NEXT_CONFIG:
335
+ s->chan[ch].next_config = value;
336
+ break;
337
+ case DMA_NEXT_BYTES:
338
+ s->chan[ch].next_bytes = value;
339
+ break;
340
+ case DMA_NEXT_DST:
341
+ s->chan[ch].next_dst = value;
342
+ break;
343
+ case DMA_NEXT_SRC:
344
+ s->chan[ch].next_src = value;
345
+ break;
346
+ case DMA_EXEC_CONFIG:
347
+ case DMA_EXEC_BYTES:
348
+ case DMA_EXEC_DST:
349
+ case DMA_EXEC_SRC:
350
+ /* these are read-only registers */
351
+ break;
352
+ default:
353
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%" HWADDR_PRIX "\n",
354
+ __func__, offset);
355
+ break;
356
+ }
357
+}
157
+}
358
+
158
+
359
+static const MemoryRegionOps sifive_pdma_ops = {
159
const KVMCapabilityInfo kvm_arch_required_capabilities[] = {
360
+ .read = sifive_pdma_read,
160
KVM_CAP_LAST_INFO
361
+ .write = sifive_pdma_write,
161
};
362
+ .endianness = DEVICE_LITTLE_ENDIAN,
363
+ /* there are 32-bit and 64-bit wide registers */
364
+ .impl = {
365
+ .min_access_size = 4,
366
+ .max_access_size = 8,
367
+ }
368
+};
369
+
370
+static void sifive_pdma_realize(DeviceState *dev, Error **errp)
371
+{
372
+ SiFivePDMAState *s = SIFIVE_PDMA(dev);
373
+ int i;
374
+
375
+ memory_region_init_io(&s->iomem, OBJECT(dev), &sifive_pdma_ops, s,
376
+ TYPE_SIFIVE_PDMA, SIFIVE_PDMA_REG_SIZE);
377
+ sysbus_init_mmio(SYS_BUS_DEVICE(dev), &s->iomem);
378
+
379
+ for (i = 0; i < SIFIVE_PDMA_IRQS; i++) {
380
+ sysbus_init_irq(SYS_BUS_DEVICE(dev), &s->irq[i]);
381
+ }
382
+}
383
+
384
+static void sifive_pdma_class_init(ObjectClass *klass, void *data)
385
+{
386
+ DeviceClass *dc = DEVICE_CLASS(klass);
387
+
388
+ dc->desc = "SiFive Platform DMA controller";
389
+ dc->realize = sifive_pdma_realize;
390
+}
391
+
392
+static const TypeInfo sifive_pdma_info = {
393
+ .name = TYPE_SIFIVE_PDMA,
394
+ .parent = TYPE_SYS_BUS_DEVICE,
395
+ .instance_size = sizeof(SiFivePDMAState),
396
+ .class_init = sifive_pdma_class_init,
397
+};
398
+
399
+static void sifive_pdma_register_types(void)
400
+{
401
+ type_register_static(&sifive_pdma_info);
402
+}
403
+
404
+type_init(sifive_pdma_register_types)
405
diff --git a/hw/dma/Kconfig b/hw/dma/Kconfig
406
index XXXXXXX..XXXXXXX 100644
407
--- a/hw/dma/Kconfig
408
+++ b/hw/dma/Kconfig
409
@@ -XXX,XX +XXX,XX @@ config ZYNQ_DEVCFG
410
411
config STP2000
412
bool
413
+
414
+config SIFIVE_PDMA
415
+ bool
416
diff --git a/hw/dma/meson.build b/hw/dma/meson.build
417
index XXXXXXX..XXXXXXX 100644
418
--- a/hw/dma/meson.build
419
+++ b/hw/dma/meson.build
420
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_XLNX_ZYNQMP_ARM', if_true: files('xlnx-zdma.c'))
421
softmmu_ss.add(when: 'CONFIG_OMAP', if_true: files('omap_dma.c', 'soc_dma.c'))
422
softmmu_ss.add(when: 'CONFIG_PXA2XX', if_true: files('pxa2xx_dma.c'))
423
softmmu_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_dma.c'))
424
+softmmu_ss.add(when: 'CONFIG_SIFIVE_PDMA', if_true: files('sifive_pdma.c'))
425
--
162
--
426
2.28.0
163
2.40.1
427
428
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
Allow 'marchid' and 'mimpid' to also be initialized in
4
kvm_riscv_init_machine_ids().
5
6
After this change, the handling of mvendorid/marchid/mimpid for the
7
'host' CPU type will be equal to what we already have for TCG named
8
CPUs, i.e. the user is not able to set these values to a different val
9
than the one that is already preset.
10
11
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
12
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
13
Acked-by: Alistair Francis <alistair.francis@wdc.com>
14
Message-Id: <20230706101738.460804-8-dbarboza@ventanamicro.com>
15
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
16
---
17
target/riscv/kvm.c | 16 ++++++++++++++++
18
1 file changed, 16 insertions(+)
19
20
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
21
index XXXXXXX..XXXXXXX 100644
22
--- a/target/riscv/kvm.c
23
+++ b/target/riscv/kvm.c
24
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_init_machine_ids(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
25
if (ret != 0) {
26
error_report("Unable to retrieve mvendorid from host, error %d", ret);
27
}
28
+
29
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
30
+ KVM_REG_RISCV_CONFIG_REG(marchid));
31
+ reg.addr = (uint64_t)&cpu->cfg.marchid;
32
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
33
+ if (ret != 0) {
34
+ error_report("Unable to retrieve marchid from host, error %d", ret);
35
+ }
36
+
37
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
38
+ KVM_REG_RISCV_CONFIG_REG(mimpid));
39
+ reg.addr = (uint64_t)&cpu->cfg.mimpid;
40
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
41
+ if (ret != 0) {
42
+ error_report("Unable to retrieve mimpid from host, error %d", ret);
43
+ }
44
}
45
46
void kvm_riscv_init_user_properties(Object *cpu_obj)
47
--
48
2.40.1
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
After changing user validation for mvendorid/marchid/mimpid to guarantee
4
that the value is validated on user input time, coupled with the work in
5
fetching KVM default values for them by using a scratch CPU, we're
6
certain that the values in cpu->cfg.(mvendorid|marchid|mimpid) are
7
already good to be written back to KVM.
8
9
There's no need to write the values back for 'host' type CPUs since the
10
values can't be changed, so let's do that just for generic CPUs.
11
12
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
13
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
14
Acked-by: Alistair Francis <alistair.francis@wdc.com>
15
Message-Id: <20230706101738.460804-9-dbarboza@ventanamicro.com>
16
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
17
---
18
target/riscv/kvm.c | 31 +++++++++++++++++++++++++++++++
19
1 file changed, 31 insertions(+)
20
21
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
22
index XXXXXXX..XXXXXXX 100644
23
--- a/target/riscv/kvm.c
24
+++ b/target/riscv/kvm.c
25
@@ -XXX,XX +XXX,XX @@ void kvm_arch_init_irq_routing(KVMState *s)
26
{
27
}
28
29
+static int kvm_vcpu_set_machine_ids(RISCVCPU *cpu, CPUState *cs)
30
+{
31
+ CPURISCVState *env = &cpu->env;
32
+ uint64_t id;
33
+ int ret;
34
+
35
+ id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
36
+ KVM_REG_RISCV_CONFIG_REG(mvendorid));
37
+ ret = kvm_set_one_reg(cs, id, &cpu->cfg.mvendorid);
38
+ if (ret != 0) {
39
+ return ret;
40
+ }
41
+
42
+ id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
43
+ KVM_REG_RISCV_CONFIG_REG(marchid));
44
+ ret = kvm_set_one_reg(cs, id, &cpu->cfg.marchid);
45
+ if (ret != 0) {
46
+ return ret;
47
+ }
48
+
49
+ id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
50
+ KVM_REG_RISCV_CONFIG_REG(mimpid));
51
+ ret = kvm_set_one_reg(cs, id, &cpu->cfg.mimpid);
52
+
53
+ return ret;
54
+}
55
+
56
int kvm_arch_init_vcpu(CPUState *cs)
57
{
58
int ret = 0;
59
@@ -XXX,XX +XXX,XX @@ int kvm_arch_init_vcpu(CPUState *cs)
60
}
61
env->misa_ext = isa;
62
63
+ if (!object_dynamic_cast(OBJECT(cpu), TYPE_RISCV_CPU_HOST)) {
64
+ ret = kvm_vcpu_set_machine_ids(cpu, cs);
65
+ }
66
+
67
return ret;
68
}
69
70
--
71
2.40.1
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
At this moment we're retrieving env->misa_ext during
4
kvm_arch_init_cpu(), leaving env->misa_ext_mask behind.
5
6
We want to set env->misa_ext_mask, and we want to set it as early as
7
possible. The reason is that we're going to use it in the validation
8
process of the KVM MISA properties we're going to add next. Setting it
9
during arch_init_cpu() is too late for user validation.
10
11
Move the code to a new helper that is going to be called during init()
12
time, via kvm_riscv_init_user_properties(), like we're already doing for
13
the machine ID properties. Set both misa_ext and misa_ext_mask to the
14
same value retrieved by the 'isa' config reg.
15
16
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
17
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
18
Acked-by: Alistair Francis <alistair.francis@wdc.com>
19
Message-Id: <20230706101738.460804-11-dbarboza@ventanamicro.com>
20
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
21
---
22
target/riscv/kvm.c | 34 +++++++++++++++++++++++-----------
23
1 file changed, 23 insertions(+), 11 deletions(-)
24
25
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
26
index XXXXXXX..XXXXXXX 100644
27
--- a/target/riscv/kvm.c
28
+++ b/target/riscv/kvm.c
29
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_init_machine_ids(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
30
}
31
}
32
33
+static void kvm_riscv_init_misa_ext_mask(RISCVCPU *cpu,
34
+ KVMScratchCPU *kvmcpu)
35
+{
36
+ CPURISCVState *env = &cpu->env;
37
+ struct kvm_one_reg reg;
38
+ int ret;
39
+
40
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
41
+ KVM_REG_RISCV_CONFIG_REG(isa));
42
+ reg.addr = (uint64_t)&env->misa_ext_mask;
43
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
44
+
45
+ if (ret) {
46
+ error_report("Unable to fetch ISA register from KVM, "
47
+ "error %d", ret);
48
+ kvm_riscv_destroy_scratch_vcpu(kvmcpu);
49
+ exit(EXIT_FAILURE);
50
+ }
51
+
52
+ env->misa_ext = env->misa_ext_mask;
53
+}
54
+
55
void kvm_riscv_init_user_properties(Object *cpu_obj)
56
{
57
RISCVCPU *cpu = RISCV_CPU(cpu_obj);
58
@@ -XXX,XX +XXX,XX @@ void kvm_riscv_init_user_properties(Object *cpu_obj)
59
}
60
61
kvm_riscv_init_machine_ids(cpu, &kvmcpu);
62
+ kvm_riscv_init_misa_ext_mask(cpu, &kvmcpu);
63
64
kvm_riscv_destroy_scratch_vcpu(&kvmcpu);
65
}
66
@@ -XXX,XX +XXX,XX @@ static int kvm_vcpu_set_machine_ids(RISCVCPU *cpu, CPUState *cs)
67
int kvm_arch_init_vcpu(CPUState *cs)
68
{
69
int ret = 0;
70
- target_ulong isa;
71
RISCVCPU *cpu = RISCV_CPU(cs);
72
- CPURISCVState *env = &cpu->env;
73
- uint64_t id;
74
75
qemu_add_vm_change_state_handler(kvm_riscv_vm_state_change, cs);
76
77
- id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
78
- KVM_REG_RISCV_CONFIG_REG(isa));
79
- ret = kvm_get_one_reg(cs, id, &isa);
80
- if (ret) {
81
- return ret;
82
- }
83
- env->misa_ext = isa;
84
-
85
if (!object_dynamic_cast(OBJECT(cpu), TYPE_RISCV_CPU_HOST)) {
86
ret = kvm_vcpu_set_machine_ids(cpu, cs);
87
}
88
--
89
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
Currently the reset vector address is hard-coded in a RISC-V CPU's
3
Next patch will add KVM specific user properties for both MISA and
4
instance_init() routine. In a real world we can have 2 exact same
4
multi-letter extensions. For MISA extensions we want to make use of what
5
CPUs except for the reset vector address, which is pretty common in
5
is already available in misa_ext_cfgs[] to avoid code repetition.
6
the RISC-V core IP licensing business.
6
7
7
misa_ext_info_arr[] array will hold name and description for each MISA
8
Normally reset vector address is a configurable parameter. Let's
8
extension that misa_ext_cfgs[] is declaring. We'll then use this new
9
create a 64-bit property to store the reset vector address which
9
array in KVM code to avoid duplicating strings. Two getters were added
10
covers both 32-bit and 64-bit CPUs.
10
to allow KVM to retrieve the 'name' and 'description' for each MISA
11
11
property.
12
Signed-off-by: Bin Meng <bin.meng@windriver.com>
12
13
There's nothing holding us back from doing the same with multi-letter
14
extensions. For now doing just with MISA extensions is enough.
15
16
It is worth documenting that even using the __bultin_ctz() directive to
17
populate the misa_ext_info_arr[] we are forced to assign 'name' and
18
'description' during runtime in riscv_cpu_add_misa_properties(). The
19
reason is that some Gitlab runners ('clang-user' and 'tsan-build') will
20
throw errors like this if we fetch 'name' and 'description' from the
21
array in the MISA_CFG() macro:
22
23
../target/riscv/cpu.c:1624:5: error: initializer element is not a
24
compile-time constant
25
MISA_CFG(RVA, true),
26
^~~~~~~~~~~~~~~~~~~
27
../target/riscv/cpu.c:1619:53: note: expanded from macro 'MISA_CFG'
28
{.name = misa_ext_info_arr[MISA_INFO_IDX(_bit)].name, \
29
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^~~~
30
31
gcc and others compilers/builders were fine with that change. We can't
32
ignore failures in the Gitlab pipeline though, so code was changed to
33
make every runner happy.
34
35
As a side effect, misa_ext_cfg[] is no longer a 'const' array because
36
it must be set during runtime.
37
38
Suggested-by: Andrew Jones <ajones@ventanamicro.com>
39
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
40
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
41
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
13
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
42
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
14
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
43
Message-Id: <20230706101738.460804-12-dbarboza@ventanamicro.com>
15
Message-Id: <1598924352-89526-2-git-send-email-bmeng.cn@gmail.com>
16
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
44
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
17
---
45
---
18
target/riscv/cpu.h | 1 +
46
target/riscv/cpu.h | 7 ++-
19
target/riscv/cpu.c | 1 +
47
target/riscv/cpu.c | 110 +++++++++++++++++++++++++++++++++------------
20
2 files changed, 2 insertions(+)
48
2 files changed, 88 insertions(+), 29 deletions(-)
21
49
22
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
50
diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
23
index XXXXXXX..XXXXXXX 100644
51
index XXXXXXX..XXXXXXX 100644
24
--- a/target/riscv/cpu.h
52
--- a/target/riscv/cpu.h
25
+++ b/target/riscv/cpu.h
53
+++ b/target/riscv/cpu.h
26
@@ -XXX,XX +XXX,XX @@ typedef struct RISCVCPU {
54
@@ -XXX,XX +XXX,XX @@
27
uint16_t elen;
55
28
bool mmu;
56
#define RV(x) ((target_ulong)1 << (x - 'A'))
29
bool pmp;
57
30
+ uint64_t resetvec;
58
-/* Consider updating misa_ext_cfgs[] when adding new MISA bits here */
31
} cfg;
59
+/*
32
} RISCVCPU;
60
+ * Consider updating misa_ext_info_arr[] and misa_ext_cfgs[]
33
61
+ * when adding new MISA bits here.
62
+ */
63
#define RVI RV('I')
64
#define RVE RV('E') /* E and I are mutually exclusive */
65
#define RVM RV('M')
66
@@ -XXX,XX +XXX,XX @@
67
#define RVJ RV('J')
68
#define RVG RV('G')
69
70
+const char *riscv_get_misa_ext_name(uint32_t bit);
71
+const char *riscv_get_misa_ext_description(uint32_t bit);
72
73
/* Privileged specification version */
74
enum {
34
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
75
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
35
index XXXXXXX..XXXXXXX 100644
76
index XXXXXXX..XXXXXXX 100644
36
--- a/target/riscv/cpu.c
77
--- a/target/riscv/cpu.c
37
+++ b/target/riscv/cpu.c
78
+++ b/target/riscv/cpu.c
38
@@ -XXX,XX +XXX,XX @@ static Property riscv_cpu_properties[] = {
79
@@ -XXX,XX +XXX,XX @@ static void cpu_get_misa_ext_cfg(Object *obj, Visitor *v, const char *name,
39
DEFINE_PROP_UINT16("elen", RISCVCPU, cfg.elen, 64),
80
visit_type_bool(v, name, &value, errp);
40
DEFINE_PROP_BOOL("mmu", RISCVCPU, cfg.mmu, true),
81
}
41
DEFINE_PROP_BOOL("pmp", RISCVCPU, cfg.pmp, true),
82
42
+ DEFINE_PROP_UINT64("resetvec", RISCVCPU, cfg.resetvec, DEFAULT_RSTVEC),
83
-static const RISCVCPUMisaExtConfig misa_ext_cfgs[] = {
43
DEFINE_PROP_END_OF_LIST(),
84
- {.name = "a", .description = "Atomic instructions",
85
- .misa_bit = RVA, .enabled = true},
86
- {.name = "c", .description = "Compressed instructions",
87
- .misa_bit = RVC, .enabled = true},
88
- {.name = "d", .description = "Double-precision float point",
89
- .misa_bit = RVD, .enabled = true},
90
- {.name = "f", .description = "Single-precision float point",
91
- .misa_bit = RVF, .enabled = true},
92
- {.name = "i", .description = "Base integer instruction set",
93
- .misa_bit = RVI, .enabled = true},
94
- {.name = "e", .description = "Base integer instruction set (embedded)",
95
- .misa_bit = RVE, .enabled = false},
96
- {.name = "m", .description = "Integer multiplication and division",
97
- .misa_bit = RVM, .enabled = true},
98
- {.name = "s", .description = "Supervisor-level instructions",
99
- .misa_bit = RVS, .enabled = true},
100
- {.name = "u", .description = "User-level instructions",
101
- .misa_bit = RVU, .enabled = true},
102
- {.name = "h", .description = "Hypervisor",
103
- .misa_bit = RVH, .enabled = true},
104
- {.name = "x-j", .description = "Dynamic translated languages",
105
- .misa_bit = RVJ, .enabled = false},
106
- {.name = "v", .description = "Vector operations",
107
- .misa_bit = RVV, .enabled = false},
108
- {.name = "g", .description = "General purpose (IMAFD_Zicsr_Zifencei)",
109
- .misa_bit = RVG, .enabled = false},
110
+typedef struct misa_ext_info {
111
+ const char *name;
112
+ const char *description;
113
+} MISAExtInfo;
114
+
115
+#define MISA_INFO_IDX(_bit) \
116
+ __builtin_ctz(_bit)
117
+
118
+#define MISA_EXT_INFO(_bit, _propname, _descr) \
119
+ [MISA_INFO_IDX(_bit)] = {.name = _propname, .description = _descr}
120
+
121
+static const MISAExtInfo misa_ext_info_arr[] = {
122
+ MISA_EXT_INFO(RVA, "a", "Atomic instructions"),
123
+ MISA_EXT_INFO(RVC, "c", "Compressed instructions"),
124
+ MISA_EXT_INFO(RVD, "d", "Double-precision float point"),
125
+ MISA_EXT_INFO(RVF, "f", "Single-precision float point"),
126
+ MISA_EXT_INFO(RVI, "i", "Base integer instruction set"),
127
+ MISA_EXT_INFO(RVE, "e", "Base integer instruction set (embedded)"),
128
+ MISA_EXT_INFO(RVM, "m", "Integer multiplication and division"),
129
+ MISA_EXT_INFO(RVS, "s", "Supervisor-level instructions"),
130
+ MISA_EXT_INFO(RVU, "u", "User-level instructions"),
131
+ MISA_EXT_INFO(RVH, "h", "Hypervisor"),
132
+ MISA_EXT_INFO(RVJ, "x-j", "Dynamic translated languages"),
133
+ MISA_EXT_INFO(RVV, "v", "Vector operations"),
134
+ MISA_EXT_INFO(RVG, "g", "General purpose (IMAFD_Zicsr_Zifencei)"),
135
+};
136
+
137
+static int riscv_validate_misa_info_idx(uint32_t bit)
138
+{
139
+ int idx;
140
+
141
+ /*
142
+ * Our lowest valid input (RVA) is 1 and
143
+ * __builtin_ctz() is UB with zero.
144
+ */
145
+ g_assert(bit != 0);
146
+ idx = MISA_INFO_IDX(bit);
147
+
148
+ g_assert(idx < ARRAY_SIZE(misa_ext_info_arr));
149
+ return idx;
150
+}
151
+
152
+const char *riscv_get_misa_ext_name(uint32_t bit)
153
+{
154
+ int idx = riscv_validate_misa_info_idx(bit);
155
+ const char *val = misa_ext_info_arr[idx].name;
156
+
157
+ g_assert(val != NULL);
158
+ return val;
159
+}
160
+
161
+const char *riscv_get_misa_ext_description(uint32_t bit)
162
+{
163
+ int idx = riscv_validate_misa_info_idx(bit);
164
+ const char *val = misa_ext_info_arr[idx].description;
165
+
166
+ g_assert(val != NULL);
167
+ return val;
168
+}
169
+
170
+#define MISA_CFG(_bit, _enabled) \
171
+ {.misa_bit = _bit, .enabled = _enabled}
172
+
173
+static RISCVCPUMisaExtConfig misa_ext_cfgs[] = {
174
+ MISA_CFG(RVA, true),
175
+ MISA_CFG(RVC, true),
176
+ MISA_CFG(RVD, true),
177
+ MISA_CFG(RVF, true),
178
+ MISA_CFG(RVI, true),
179
+ MISA_CFG(RVE, false),
180
+ MISA_CFG(RVM, true),
181
+ MISA_CFG(RVS, true),
182
+ MISA_CFG(RVU, true),
183
+ MISA_CFG(RVH, true),
184
+ MISA_CFG(RVJ, false),
185
+ MISA_CFG(RVV, false),
186
+ MISA_CFG(RVG, false),
44
};
187
};
45
188
189
static void riscv_cpu_add_misa_properties(Object *cpu_obj)
190
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_misa_properties(Object *cpu_obj)
191
int i;
192
193
for (i = 0; i < ARRAY_SIZE(misa_ext_cfgs); i++) {
194
- const RISCVCPUMisaExtConfig *misa_cfg = &misa_ext_cfgs[i];
195
+ RISCVCPUMisaExtConfig *misa_cfg = &misa_ext_cfgs[i];
196
+ int bit = misa_cfg->misa_bit;
197
+
198
+ misa_cfg->name = riscv_get_misa_ext_name(bit);
199
+ misa_cfg->description = riscv_get_misa_ext_description(bit);
200
201
object_property_add(cpu_obj, misa_cfg->name, "bool",
202
cpu_get_misa_ext_cfg,
46
--
203
--
47
2.28.0
204
2.40.1
48
205
49
206
diff view generated by jsdifflib
New patch
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
1
2
3
Using all TCG user properties in KVM is tricky. First because KVM
4
supports only a small subset of what TCG provides, so most of the
5
cpu->cfg flags do nothing for KVM.
6
7
Second, and more important, we don't have a way of telling if any given
8
value is an user input or not. For TCG this has a small impact since we
9
just validating everything and error out if needed. But for KVM it would
10
be good to know if a given value was set by the user or if it's a value
11
already provided by KVM. Otherwise we don't know how to handle failed
12
kvm_set_one_regs() when writing the configurations back.
13
14
These characteristics make it overly complicated to use the same user
15
facing flags for both KVM and TCG. A simpler approach is to create KVM
16
specific properties that have specialized logic, forking KVM and TCG use
17
cases for those cases only. Fully separating KVM/TCG properties is
18
unneeded at this point - in fact we want the user experience to be as
19
equal as possible, regardless of the acceleration chosen.
20
21
We'll start this fork with the MISA properties, adding the MISA bits
22
that the KVM driver currently supports. A new KVMCPUConfig type is
23
introduced. It'll hold general information about an extension. For MISA
24
extensions we're going to use the newly created getters of
25
misa_ext_infos[] to populate their name and description. 'offset' holds
26
the MISA bit (RVA, RVC, ...). We're calling it 'offset' instead of
27
'misa_bit' because this same KVMCPUConfig struct will be used to
28
multi-letter extensions later on.
29
30
This new type also holds a 'user_set' flag. This flag will be set when
31
the user set an option that's different than what is already configured
32
in the host, requiring KVM intervention to write the regs back during
33
kvm_arch_init_vcpu(). Similar mechanics will be implemented for
34
multi-letter extensions as well.
35
36
There is no need to duplicate more code than necessary, so we're going
37
to use the existing kvm_riscv_init_user_properties() to add the KVM
38
specific properties. Any code that is adding a TCG user prop is then
39
changed slightly to verify first if there's a KVM prop with the same
40
name already added.
41
42
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
43
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
44
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
45
Message-Id: <20230706101738.460804-13-dbarboza@ventanamicro.com>
46
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
47
---
48
target/riscv/cpu.c | 5 +++
49
target/riscv/kvm.c | 78 ++++++++++++++++++++++++++++++++++++++++++++++
50
2 files changed, 83 insertions(+)
51
52
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
53
index XXXXXXX..XXXXXXX 100644
54
--- a/target/riscv/cpu.c
55
+++ b/target/riscv/cpu.c
56
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_misa_properties(Object *cpu_obj)
57
misa_cfg->name = riscv_get_misa_ext_name(bit);
58
misa_cfg->description = riscv_get_misa_ext_description(bit);
59
60
+ /* Check if KVM already created the property */
61
+ if (object_property_find(cpu_obj, misa_cfg->name)) {
62
+ continue;
63
+ }
64
+
65
object_property_add(cpu_obj, misa_cfg->name, "bool",
66
cpu_get_misa_ext_cfg,
67
cpu_set_misa_ext_cfg,
68
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
69
index XXXXXXX..XXXXXXX 100644
70
--- a/target/riscv/kvm.c
71
+++ b/target/riscv/kvm.c
72
@@ -XXX,XX +XXX,XX @@
73
#include <linux/kvm.h>
74
75
#include "qemu/timer.h"
76
+#include "qapi/error.h"
77
#include "qemu/error-report.h"
78
#include "qemu/main-loop.h"
79
+#include "qapi/visitor.h"
80
#include "sysemu/sysemu.h"
81
#include "sysemu/kvm.h"
82
#include "sysemu/kvm_int.h"
83
@@ -XXX,XX +XXX,XX @@ static uint64_t kvm_riscv_reg_id(CPURISCVState *env, uint64_t type,
84
} \
85
} while (0)
86
87
+typedef struct KVMCPUConfig {
88
+ const char *name;
89
+ const char *description;
90
+ target_ulong offset;
91
+ int kvm_reg_id;
92
+ bool user_set;
93
+} KVMCPUConfig;
94
+
95
+#define KVM_MISA_CFG(_bit, _reg_id) \
96
+ {.offset = _bit, .kvm_reg_id = _reg_id}
97
+
98
+/* KVM ISA extensions */
99
+static KVMCPUConfig kvm_misa_ext_cfgs[] = {
100
+ KVM_MISA_CFG(RVA, KVM_RISCV_ISA_EXT_A),
101
+ KVM_MISA_CFG(RVC, KVM_RISCV_ISA_EXT_C),
102
+ KVM_MISA_CFG(RVD, KVM_RISCV_ISA_EXT_D),
103
+ KVM_MISA_CFG(RVF, KVM_RISCV_ISA_EXT_F),
104
+ KVM_MISA_CFG(RVH, KVM_RISCV_ISA_EXT_H),
105
+ KVM_MISA_CFG(RVI, KVM_RISCV_ISA_EXT_I),
106
+ KVM_MISA_CFG(RVM, KVM_RISCV_ISA_EXT_M),
107
+};
108
+
109
+static void kvm_cpu_set_misa_ext_cfg(Object *obj, Visitor *v,
110
+ const char *name,
111
+ void *opaque, Error **errp)
112
+{
113
+ KVMCPUConfig *misa_ext_cfg = opaque;
114
+ target_ulong misa_bit = misa_ext_cfg->offset;
115
+ RISCVCPU *cpu = RISCV_CPU(obj);
116
+ CPURISCVState *env = &cpu->env;
117
+ bool value, host_bit;
118
+
119
+ if (!visit_type_bool(v, name, &value, errp)) {
120
+ return;
121
+ }
122
+
123
+ host_bit = env->misa_ext_mask & misa_bit;
124
+
125
+ if (value == host_bit) {
126
+ return;
127
+ }
128
+
129
+ if (!value) {
130
+ misa_ext_cfg->user_set = true;
131
+ return;
132
+ }
133
+
134
+ /*
135
+ * Forbid users to enable extensions that aren't
136
+ * available in the hart.
137
+ */
138
+ error_setg(errp, "Enabling MISA bit '%s' is not allowed: it's not "
139
+ "enabled in the host", misa_ext_cfg->name);
140
+}
141
+
142
+static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
143
+{
144
+ int i;
145
+
146
+ for (i = 0; i < ARRAY_SIZE(kvm_misa_ext_cfgs); i++) {
147
+ KVMCPUConfig *misa_cfg = &kvm_misa_ext_cfgs[i];
148
+ int bit = misa_cfg->offset;
149
+
150
+ misa_cfg->name = riscv_get_misa_ext_name(bit);
151
+ misa_cfg->description = riscv_get_misa_ext_description(bit);
152
+
153
+ object_property_add(cpu_obj, misa_cfg->name, "bool",
154
+ NULL,
155
+ kvm_cpu_set_misa_ext_cfg,
156
+ NULL, misa_cfg);
157
+ object_property_set_description(cpu_obj, misa_cfg->name,
158
+ misa_cfg->description);
159
+ }
160
+}
161
+
162
static int kvm_riscv_get_regs_core(CPUState *cs)
163
{
164
int ret = 0;
165
@@ -XXX,XX +XXX,XX @@ void kvm_riscv_init_user_properties(Object *cpu_obj)
166
return;
167
}
168
169
+ kvm_riscv_add_cpu_user_properties(cpu_obj);
170
kvm_riscv_init_machine_ids(cpu, &kvmcpu);
171
kvm_riscv_init_misa_ext_mask(cpu, &kvmcpu);
172
173
--
174
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
Our design philosophy with KVM properties can be resumed in two main
4
should only contain the RISC-V SoC / machine codes plus generic
4
decisions based on KVM interface availability and what the user wants to
5
codes. Let's move riscv_htif model to hw/char directory.
5
do:
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
- if the user disables an extension that the host KVM module doesn't
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
know about (i.e. it doesn't implement the kvm_get_one_reg() interface),
9
Message-Id: <1599129623-68957-8-git-send-email-bmeng.cn@gmail.com>
9
keep booting the CPU. This will avoid users having to deal with issues
10
with older KVM versions while disabling features they don't care;
11
12
- for any other case we're going to error out immediately. If the user
13
wants to enable a feature that KVM doesn't know about this a problem that
14
is worth aborting - the user must know that the feature wasn't enabled
15
in the hart. Likewise, if KVM knows about the extension, the user wants
16
to enable/disable it, and we fail to do it so, that's also a problem we
17
can't shrug it off.
18
19
In the case of MISA bits we won't even try enabling bits that aren't
20
already available in the host. The ioctl() is so likely to fail that
21
it's not worth trying. This check is already done in the previous patch,
22
in kvm_cpu_set_misa_ext_cfg(), thus we don't need to worry about it now.
23
24
In kvm_riscv_update_cpu_misa_ext() we'll go through every potential user
25
option and do as follows:
26
27
- if the user didn't set the property or set to the same value of the
28
host, do nothing;
29
30
- Disable the given extension in KVM. Error out if anything goes wrong.
31
32
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
33
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
34
Acked-by: Alistair Francis <alistair.francis@wdc.com>
35
Message-Id: <20230706101738.460804-14-dbarboza@ventanamicro.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
36
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
37
---
12
include/hw/{riscv => char}/riscv_htif.h | 0
38
target/riscv/kvm.c | 40 ++++++++++++++++++++++++++++++++++++++++
13
hw/{riscv => char}/riscv_htif.c | 2 +-
39
1 file changed, 40 insertions(+)
14
hw/riscv/spike.c | 2 +-
15
hw/char/Kconfig | 3 +++
16
hw/char/meson.build | 1 +
17
hw/riscv/Kconfig | 3 ---
18
hw/riscv/meson.build | 1 -
19
7 files changed, 6 insertions(+), 6 deletions(-)
20
rename include/hw/{riscv => char}/riscv_htif.h (100%)
21
rename hw/{riscv => char}/riscv_htif.c (99%)
22
40
23
diff --git a/include/hw/riscv/riscv_htif.h b/include/hw/char/riscv_htif.h
41
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
24
similarity index 100%
25
rename from include/hw/riscv/riscv_htif.h
26
rename to include/hw/char/riscv_htif.h
27
diff --git a/hw/riscv/riscv_htif.c b/hw/char/riscv_htif.c
28
similarity index 99%
29
rename from hw/riscv/riscv_htif.c
30
rename to hw/char/riscv_htif.c
31
index XXXXXXX..XXXXXXX 100644
42
index XXXXXXX..XXXXXXX 100644
32
--- a/hw/riscv/riscv_htif.c
43
--- a/target/riscv/kvm.c
33
+++ b/hw/char/riscv_htif.c
44
+++ b/target/riscv/kvm.c
34
@@ -XXX,XX +XXX,XX @@
45
@@ -XXX,XX +XXX,XX @@ static void kvm_cpu_set_misa_ext_cfg(Object *obj, Visitor *v,
35
#include "qapi/error.h"
46
"enabled in the host", misa_ext_cfg->name);
36
#include "qemu/log.h"
47
}
37
#include "hw/sysbus.h"
48
38
+#include "hw/char/riscv_htif.h"
49
+static void kvm_riscv_update_cpu_misa_ext(RISCVCPU *cpu, CPUState *cs)
39
#include "hw/char/serial.h"
50
+{
40
#include "chardev/char.h"
51
+ CPURISCVState *env = &cpu->env;
41
#include "chardev/char-fe.h"
52
+ uint64_t id, reg;
42
-#include "hw/riscv/riscv_htif.h"
53
+ int i, ret;
43
#include "qemu/timer.h"
44
#include "qemu/error-report.h"
45
46
diff --git a/hw/riscv/spike.c b/hw/riscv/spike.c
47
index XXXXXXX..XXXXXXX 100644
48
--- a/hw/riscv/spike.c
49
+++ b/hw/riscv/spike.c
50
@@ -XXX,XX +XXX,XX @@
51
#include "hw/loader.h"
52
#include "hw/sysbus.h"
53
#include "target/riscv/cpu.h"
54
-#include "hw/riscv/riscv_htif.h"
55
#include "hw/riscv/riscv_hart.h"
56
#include "hw/riscv/spike.h"
57
#include "hw/riscv/boot.h"
58
#include "hw/riscv/numa.h"
59
+#include "hw/char/riscv_htif.h"
60
#include "hw/intc/sifive_clint.h"
61
#include "chardev/char.h"
62
#include "sysemu/arch_init.h"
63
diff --git a/hw/char/Kconfig b/hw/char/Kconfig
64
index XXXXXXX..XXXXXXX 100644
65
--- a/hw/char/Kconfig
66
+++ b/hw/char/Kconfig
67
@@ -XXX,XX +XXX,XX @@
68
config ESCC
69
bool
70
71
+config HTIF
72
+ bool
73
+
54
+
74
config PARALLEL
55
+ for (i = 0; i < ARRAY_SIZE(kvm_misa_ext_cfgs); i++) {
75
bool
56
+ KVMCPUConfig *misa_cfg = &kvm_misa_ext_cfgs[i];
76
default y
57
+ target_ulong misa_bit = misa_cfg->offset;
77
diff --git a/hw/char/meson.build b/hw/char/meson.build
58
+
78
index XXXXXXX..XXXXXXX 100644
59
+ if (!misa_cfg->user_set) {
79
--- a/hw/char/meson.build
60
+ continue;
80
+++ b/hw/char/meson.build
61
+ }
81
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_SH4', if_true: files('sh_serial.c'))
62
+
82
softmmu_ss.add(when: 'CONFIG_STM32F2XX_USART', if_true: files('stm32f2xx_usart.c'))
63
+ /* If we're here we're going to disable the MISA bit */
83
softmmu_ss.add(when: 'CONFIG_MCHP_PFSOC_MMUART', if_true: files('mchp_pfsoc_mmuart.c'))
64
+ reg = 0;
84
65
+ id = kvm_riscv_reg_id(env, KVM_REG_RISCV_ISA_EXT,
85
+specific_ss.add(when: 'CONFIG_HTIF', if_true: files('riscv_htif.c'))
66
+ misa_cfg->kvm_reg_id);
86
specific_ss.add(when: 'CONFIG_TERMINAL3270', if_true: files('terminal3270.c'))
67
+ ret = kvm_set_one_reg(cs, id, &reg);
87
specific_ss.add(when: 'CONFIG_VIRTIO', if_true: files('virtio-serial-bus.c'))
68
+ if (ret != 0) {
88
specific_ss.add(when: 'CONFIG_PSERIES', if_true: files('spapr_vty.c'))
69
+ /*
89
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
70
+ * We're not checking for -EINVAL because if the bit is about
90
index XXXXXXX..XXXXXXX 100644
71
+ * to be disabled, it means that it was already enabled by
91
--- a/hw/riscv/Kconfig
72
+ * KVM. We determined that by fetching the 'isa' register
92
+++ b/hw/riscv/Kconfig
73
+ * during init() time. Any error at this point is worth
93
@@ -XXX,XX +XXX,XX @@
74
+ * aborting.
94
-config HTIF
75
+ */
95
- bool
76
+ error_report("Unable to set KVM reg %s, error %d",
96
-
77
+ misa_cfg->name, ret);
97
config HART
78
+ exit(EXIT_FAILURE);
98
bool
79
+ }
99
80
+ env->misa_ext &= ~misa_bit;
100
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
81
+ }
101
index XXXXXXX..XXXXXXX 100644
82
+}
102
--- a/hw/riscv/meson.build
83
+
103
+++ b/hw/riscv/meson.build
84
static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
104
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
85
{
105
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
86
int i;
106
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
87
@@ -XXX,XX +XXX,XX @@ int kvm_arch_init_vcpu(CPUState *cs)
107
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
88
108
-riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('riscv_htif.c'))
89
if (!object_dynamic_cast(OBJECT(cpu), TYPE_RISCV_CPU_HOST)) {
109
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
90
ret = kvm_vcpu_set_machine_ids(cpu, cs);
110
riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c'))
91
+ if (ret != 0) {
92
+ return ret;
93
+ }
94
}
95
96
+ kvm_riscv_update_cpu_misa_ext(cpu, cs);
97
+
98
return ret;
99
}
111
100
112
--
101
--
113
2.28.0
102
2.40.1
114
115
diff view generated by jsdifflib
New patch
1
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
3
Let's add KVM user properties for the multi-letter extensions that KVM
4
currently supports: zicbom, zicboz, zihintpause, zbb, ssaia, sstc,
5
svinval and svpbmt.
6
7
As with MISA extensions, we're using the KVMCPUConfig type to hold
8
information about the state of each extension. However, multi-letter
9
extensions have more cases to cover than MISA extensions, so we're
10
adding an extra 'supported' flag as well. This flag will reflect if a
11
given extension is supported by KVM, i.e. KVM knows how to handle it.
12
This is determined during KVM extension discovery in
13
kvm_riscv_init_multiext_cfg(), where we test for EINVAL errors. Any
14
other error will cause an abort.
15
16
The use of the 'user_set' is similar to what we already do with MISA
17
extensions: the flag set only if the user is changing the extension
18
state.
19
20
The 'supported' flag will be used later on to make an exception for
21
users that are disabling multi-letter extensions that are unknown to
22
KVM.
23
24
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
25
Acked-by: Alistair Francis <alistair.francis@wdc.com>
26
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
27
Message-Id: <20230706101738.460804-15-dbarboza@ventanamicro.com>
28
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
29
---
30
target/riscv/cpu.c | 8 +++
31
target/riscv/kvm.c | 119 +++++++++++++++++++++++++++++++++++++++++++++
32
2 files changed, 127 insertions(+)
33
34
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
35
index XXXXXXX..XXXXXXX 100644
36
--- a/target/riscv/cpu.c
37
+++ b/target/riscv/cpu.c
38
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
39
riscv_cpu_add_misa_properties(obj);
40
41
for (prop = riscv_cpu_extensions; prop && prop->name; prop++) {
42
+#ifndef CONFIG_USER_ONLY
43
+ if (kvm_enabled()) {
44
+ /* Check if KVM created the property already */
45
+ if (object_property_find(obj, prop->name)) {
46
+ continue;
47
+ }
48
+ }
49
+#endif
50
qdev_property_add_static(dev, prop);
51
}
52
53
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
54
index XXXXXXX..XXXXXXX 100644
55
--- a/target/riscv/kvm.c
56
+++ b/target/riscv/kvm.c
57
@@ -XXX,XX +XXX,XX @@ typedef struct KVMCPUConfig {
58
target_ulong offset;
59
int kvm_reg_id;
60
bool user_set;
61
+ bool supported;
62
} KVMCPUConfig;
63
64
#define KVM_MISA_CFG(_bit, _reg_id) \
65
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_update_cpu_misa_ext(RISCVCPU *cpu, CPUState *cs)
66
}
67
}
68
69
+#define CPUCFG(_prop) offsetof(struct RISCVCPUConfig, _prop)
70
+
71
+#define KVM_EXT_CFG(_name, _prop, _reg_id) \
72
+ {.name = _name, .offset = CPUCFG(_prop), \
73
+ .kvm_reg_id = _reg_id}
74
+
75
+static KVMCPUConfig kvm_multi_ext_cfgs[] = {
76
+ KVM_EXT_CFG("zicbom", ext_icbom, KVM_RISCV_ISA_EXT_ZICBOM),
77
+ KVM_EXT_CFG("zicboz", ext_icboz, KVM_RISCV_ISA_EXT_ZICBOZ),
78
+ KVM_EXT_CFG("zihintpause", ext_zihintpause, KVM_RISCV_ISA_EXT_ZIHINTPAUSE),
79
+ KVM_EXT_CFG("zbb", ext_zbb, KVM_RISCV_ISA_EXT_ZBB),
80
+ KVM_EXT_CFG("ssaia", ext_ssaia, KVM_RISCV_ISA_EXT_SSAIA),
81
+ KVM_EXT_CFG("sstc", ext_sstc, KVM_RISCV_ISA_EXT_SSTC),
82
+ KVM_EXT_CFG("svinval", ext_svinval, KVM_RISCV_ISA_EXT_SVINVAL),
83
+ KVM_EXT_CFG("svpbmt", ext_svpbmt, KVM_RISCV_ISA_EXT_SVPBMT),
84
+};
85
+
86
+static void kvm_cpu_cfg_set(RISCVCPU *cpu, KVMCPUConfig *multi_ext,
87
+ uint32_t val)
88
+{
89
+ int cpu_cfg_offset = multi_ext->offset;
90
+ bool *ext_enabled = (void *)&cpu->cfg + cpu_cfg_offset;
91
+
92
+ *ext_enabled = val;
93
+}
94
+
95
+static uint32_t kvm_cpu_cfg_get(RISCVCPU *cpu,
96
+ KVMCPUConfig *multi_ext)
97
+{
98
+ int cpu_cfg_offset = multi_ext->offset;
99
+ bool *ext_enabled = (void *)&cpu->cfg + cpu_cfg_offset;
100
+
101
+ return *ext_enabled;
102
+}
103
+
104
+static void kvm_cpu_set_multi_ext_cfg(Object *obj, Visitor *v,
105
+ const char *name,
106
+ void *opaque, Error **errp)
107
+{
108
+ KVMCPUConfig *multi_ext_cfg = opaque;
109
+ RISCVCPU *cpu = RISCV_CPU(obj);
110
+ bool value, host_val;
111
+
112
+ if (!visit_type_bool(v, name, &value, errp)) {
113
+ return;
114
+ }
115
+
116
+ host_val = kvm_cpu_cfg_get(cpu, multi_ext_cfg);
117
+
118
+ /*
119
+ * Ignore if the user is setting the same value
120
+ * as the host.
121
+ */
122
+ if (value == host_val) {
123
+ return;
124
+ }
125
+
126
+ if (!multi_ext_cfg->supported) {
127
+ /*
128
+ * Error out if the user is trying to enable an
129
+ * extension that KVM doesn't support. Ignore
130
+ * option otherwise.
131
+ */
132
+ if (value) {
133
+ error_setg(errp, "KVM does not support disabling extension %s",
134
+ multi_ext_cfg->name);
135
+ }
136
+
137
+ return;
138
+ }
139
+
140
+ multi_ext_cfg->user_set = true;
141
+ kvm_cpu_cfg_set(cpu, multi_ext_cfg, value);
142
+}
143
+
144
static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
145
{
146
int i;
147
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
148
object_property_set_description(cpu_obj, misa_cfg->name,
149
misa_cfg->description);
150
}
151
+
152
+ for (i = 0; i < ARRAY_SIZE(kvm_multi_ext_cfgs); i++) {
153
+ KVMCPUConfig *multi_cfg = &kvm_multi_ext_cfgs[i];
154
+
155
+ object_property_add(cpu_obj, multi_cfg->name, "bool",
156
+ NULL,
157
+ kvm_cpu_set_multi_ext_cfg,
158
+ NULL, multi_cfg);
159
+ }
160
}
161
162
static int kvm_riscv_get_regs_core(CPUState *cs)
163
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_init_misa_ext_mask(RISCVCPU *cpu,
164
env->misa_ext = env->misa_ext_mask;
165
}
166
167
+static void kvm_riscv_init_multiext_cfg(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
168
+{
169
+ CPURISCVState *env = &cpu->env;
170
+ uint64_t val;
171
+ int i, ret;
172
+
173
+ for (i = 0; i < ARRAY_SIZE(kvm_multi_ext_cfgs); i++) {
174
+ KVMCPUConfig *multi_ext_cfg = &kvm_multi_ext_cfgs[i];
175
+ struct kvm_one_reg reg;
176
+
177
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_ISA_EXT,
178
+ multi_ext_cfg->kvm_reg_id);
179
+ reg.addr = (uint64_t)&val;
180
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
181
+ if (ret != 0) {
182
+ if (errno == EINVAL) {
183
+ /* Silently default to 'false' if KVM does not support it. */
184
+ multi_ext_cfg->supported = false;
185
+ val = false;
186
+ } else {
187
+ error_report("Unable to read ISA_EXT KVM register %s, "
188
+ "error %d", multi_ext_cfg->name, ret);
189
+ kvm_riscv_destroy_scratch_vcpu(kvmcpu);
190
+ exit(EXIT_FAILURE);
191
+ }
192
+ } else {
193
+ multi_ext_cfg->supported = true;
194
+ }
195
+
196
+ kvm_cpu_cfg_set(cpu, multi_ext_cfg, val);
197
+ }
198
+}
199
+
200
void kvm_riscv_init_user_properties(Object *cpu_obj)
201
{
202
RISCVCPU *cpu = RISCV_CPU(cpu_obj);
203
@@ -XXX,XX +XXX,XX @@ void kvm_riscv_init_user_properties(Object *cpu_obj)
204
kvm_riscv_add_cpu_user_properties(cpu_obj);
205
kvm_riscv_init_machine_ids(cpu, &kvmcpu);
206
kvm_riscv_init_misa_ext_mask(cpu, &kvmcpu);
207
+ kvm_riscv_init_multiext_cfg(cpu, &kvmcpu);
208
209
kvm_riscv_destroy_scratch_vcpu(&kvmcpu);
210
}
211
--
212
2.40.1
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
This is an effort to clean up the hw/riscv directory. Ideally it
3
riscv_cpu_add_user_properties() ended up with an excess of "#ifndef
4
should only contain the RISC-V SoC / machine codes plus generic
4
CONFIG_USER_ONLY" blocks after changes that added KVM properties
5
codes. Let's move sifive_e_prci model to hw/misc directory.
5
handling.
6
6
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
KVM specific properties are required to be created earlier than their
8
TCG counterparts, but the remaining props can be created at any order.
9
Move riscv_add_satp_mode_properties() to the start of the function,
10
inside the !CONFIG_USER_ONLY block already present there, to remove the
11
last ifndef block.
12
13
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
14
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
15
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
16
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1599129623-68957-2-git-send-email-bmeng.cn@gmail.com>
17
Message-Id: <20230706101738.460804-16-dbarboza@ventanamicro.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
18
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
19
---
12
include/hw/{riscv => misc}/sifive_e_prci.h | 0
20
target/riscv/cpu.c | 6 ++----
13
hw/{riscv => misc}/sifive_e_prci.c | 2 +-
21
1 file changed, 2 insertions(+), 4 deletions(-)
14
hw/riscv/sifive_e.c | 2 +-
15
hw/misc/Kconfig | 3 +++
16
hw/misc/meson.build | 3 +++
17
hw/riscv/Kconfig | 1 +
18
hw/riscv/meson.build | 1 -
19
7 files changed, 9 insertions(+), 3 deletions(-)
20
rename include/hw/{riscv => misc}/sifive_e_prci.h (100%)
21
rename hw/{riscv => misc}/sifive_e_prci.c (99%)
22
22
23
diff --git a/include/hw/riscv/sifive_e_prci.h b/include/hw/misc/sifive_e_prci.h
23
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
24
similarity index 100%
25
rename from include/hw/riscv/sifive_e_prci.h
26
rename to include/hw/misc/sifive_e_prci.h
27
diff --git a/hw/riscv/sifive_e_prci.c b/hw/misc/sifive_e_prci.c
28
similarity index 99%
29
rename from hw/riscv/sifive_e_prci.c
30
rename to hw/misc/sifive_e_prci.c
31
index XXXXXXX..XXXXXXX 100644
24
index XXXXXXX..XXXXXXX 100644
32
--- a/hw/riscv/sifive_e_prci.c
25
--- a/target/riscv/cpu.c
33
+++ b/hw/misc/sifive_e_prci.c
26
+++ b/target/riscv/cpu.c
34
@@ -XXX,XX +XXX,XX @@
27
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
35
#include "qemu/log.h"
28
DeviceState *dev = DEVICE(obj);
36
#include "qemu/module.h"
29
37
#include "hw/hw.h"
30
#ifndef CONFIG_USER_ONLY
38
-#include "hw/riscv/sifive_e_prci.h"
31
+ riscv_add_satp_mode_properties(obj);
39
+#include "hw/misc/sifive_e_prci.h"
40
41
static uint64_t sifive_e_prci_read(void *opaque, hwaddr addr, unsigned int size)
42
{
43
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
44
index XXXXXXX..XXXXXXX 100644
45
--- a/hw/riscv/sifive_e.c
46
+++ b/hw/riscv/sifive_e.c
47
@@ -XXX,XX +XXX,XX @@
48
#include "hw/riscv/sifive_clint.h"
49
#include "hw/riscv/sifive_uart.h"
50
#include "hw/riscv/sifive_e.h"
51
-#include "hw/riscv/sifive_e_prci.h"
52
#include "hw/riscv/boot.h"
53
+#include "hw/misc/sifive_e_prci.h"
54
#include "chardev/char.h"
55
#include "sysemu/arch_init.h"
56
#include "sysemu/sysemu.h"
57
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
58
index XXXXXXX..XXXXXXX 100644
59
--- a/hw/misc/Kconfig
60
+++ b/hw/misc/Kconfig
61
@@ -XXX,XX +XXX,XX @@ config MAC_VIA
62
config AVR_POWER
63
bool
64
65
+config SIFIVE_E_PRCI
66
+ bool
67
+
32
+
68
source macio/Kconfig
33
if (kvm_enabled()) {
69
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
34
kvm_riscv_init_user_properties(obj);
70
index XXXXXXX..XXXXXXX 100644
35
}
71
--- a/hw/misc/meson.build
36
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
72
+++ b/hw/misc/meson.build
37
#endif
73
@@ -XXX,XX +XXX,XX @@ softmmu_ss.add(when: 'CONFIG_ARM11SCU', if_true: files('arm11scu.c'))
38
qdev_property_add_static(dev, prop);
74
# Mac devices
39
}
75
softmmu_ss.add(when: 'CONFIG_MOS6522', if_true: files('mos6522.c'))
40
-
76
41
-#ifndef CONFIG_USER_ONLY
77
+# RISC-V devices
42
- riscv_add_satp_mode_properties(obj);
78
+softmmu_ss.add(when: 'CONFIG_SIFIVE_E_PRCI', if_true: files('sifive_e_prci.c'))
43
-#endif
79
+
44
}
80
# PKUnity SoC devices
45
81
softmmu_ss.add(when: 'CONFIG_PUV3', if_true: files('puv3_pm.c'))
46
static Property riscv_cpu_properties[] = {
82
83
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
84
index XXXXXXX..XXXXXXX 100644
85
--- a/hw/riscv/Kconfig
86
+++ b/hw/riscv/Kconfig
87
@@ -XXX,XX +XXX,XX @@ config SIFIVE_E
88
bool
89
select HART
90
select SIFIVE
91
+ select SIFIVE_E_PRCI
92
select UNIMP
93
94
config SIFIVE_U
95
diff --git a/hw/riscv/meson.build b/hw/riscv/meson.build
96
index XXXXXXX..XXXXXXX 100644
97
--- a/hw/riscv/meson.build
98
+++ b/hw/riscv/meson.build
99
@@ -XXX,XX +XXX,XX @@ riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_plic.c'))
100
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_test.c'))
101
riscv_ss.add(when: 'CONFIG_SIFIVE', if_true: files('sifive_uart.c'))
102
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
103
-riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e_prci.c'))
104
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
105
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_otp.c'))
106
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u_prci.c'))
107
--
47
--
108
2.28.0
48
2.40.1
109
49
110
50
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
Microchip PolarFire SoC integrates 2 Candence GEMs to provide
3
riscv_isa_string_ext() is being used by riscv_isa_string(), which is
4
IEEE 802.3 standard-compliant 10/100/1000 Mbps ethernet interface.
4
then used by boards to retrieve the 'riscv,isa' string to be written in
5
the FDT. All this happens after riscv_cpu_realize(), meaning that we're
6
already past riscv_cpu_validate_set_extensions() and, more important,
7
riscv_cpu_disable_priv_spec_isa_exts().
5
8
6
On the Icicle Kit board, GEM0 connects to a PHY at address 8 while
9
This means that all extensions that needed to be disabled due to
7
GEM1 connects to a PHY at address 9.
10
priv_spec mismatch are already disabled. Checking this again during
11
riscv_isa_string_ext() is unneeded. Remove it.
8
12
9
The 2nd stage bootloader (U-Boot) is using GEM1 by default, so we
13
As a bonus, riscv_isa_string_ext() can now be used with the 'host'
10
must specify 2 '-nic' options from the command line in order to get
14
KVM-only CPU type since it doesn't have a env->priv_ver assigned and it
11
a working ethernet.
15
would fail this check for no good reason.
12
16
13
Signed-off-by: Bin Meng <bin.meng@windriver.com>
17
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
18
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
14
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
19
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
15
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
20
Message-Id: <20230706101738.460804-17-dbarboza@ventanamicro.com>
16
Message-Id: <1598924352-89526-14-git-send-email-bmeng.cn@gmail.com>
17
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
21
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
18
---
22
---
19
include/hw/riscv/microchip_pfsoc.h | 7 ++++++
23
target/riscv/cpu.c | 3 +--
20
hw/riscv/microchip_pfsoc.c | 39 ++++++++++++++++++++++++++++++
24
1 file changed, 1 insertion(+), 2 deletions(-)
21
2 files changed, 46 insertions(+)
22
25
23
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
26
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
24
index XXXXXXX..XXXXXXX 100644
27
index XXXXXXX..XXXXXXX 100644
25
--- a/include/hw/riscv/microchip_pfsoc.h
28
--- a/target/riscv/cpu.c
26
+++ b/include/hw/riscv/microchip_pfsoc.h
29
+++ b/target/riscv/cpu.c
27
@@ -XXX,XX +XXX,XX @@
30
@@ -XXX,XX +XXX,XX @@ static void riscv_isa_string_ext(RISCVCPU *cpu, char **isa_str,
28
29
#include "hw/char/mchp_pfsoc_mmuart.h"
30
#include "hw/dma/sifive_pdma.h"
31
+#include "hw/net/cadence_gem.h"
32
#include "hw/sd/cadence_sdhci.h"
33
34
typedef struct MicrochipPFSoCState {
35
@@ -XXX,XX +XXX,XX @@ typedef struct MicrochipPFSoCState {
36
MchpPfSoCMMUartState *serial3;
37
MchpPfSoCMMUartState *serial4;
38
SiFivePDMAState dma;
39
+ CadenceGEMState gem0;
40
+ CadenceGEMState gem1;
41
CadenceSDHCIState sdhci;
42
} MicrochipPFSoCState;
43
44
@@ -XXX,XX +XXX,XX @@ enum {
45
MICROCHIP_PFSOC_MMUART2,
46
MICROCHIP_PFSOC_MMUART3,
47
MICROCHIP_PFSOC_MMUART4,
48
+ MICROCHIP_PFSOC_GEM0,
49
+ MICROCHIP_PFSOC_GEM1,
50
MICROCHIP_PFSOC_ENVM_CFG,
51
MICROCHIP_PFSOC_ENVM_DATA,
52
MICROCHIP_PFSOC_IOSCB_CFG,
53
@@ -XXX,XX +XXX,XX @@ enum {
54
MICROCHIP_PFSOC_DMA_IRQ5 = 10,
55
MICROCHIP_PFSOC_DMA_IRQ6 = 11,
56
MICROCHIP_PFSOC_DMA_IRQ7 = 12,
57
+ MICROCHIP_PFSOC_GEM0_IRQ = 64,
58
+ MICROCHIP_PFSOC_GEM1_IRQ = 70,
59
MICROCHIP_PFSOC_EMMC_SD_IRQ = 88,
60
MICROCHIP_PFSOC_MMUART0_IRQ = 90,
61
MICROCHIP_PFSOC_MMUART1_IRQ = 91,
62
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
63
index XXXXXXX..XXXXXXX 100644
64
--- a/hw/riscv/microchip_pfsoc.c
65
+++ b/hw/riscv/microchip_pfsoc.c
66
@@ -XXX,XX +XXX,XX @@
67
* 3) MMUARTs (Multi-Mode UART)
68
* 4) Cadence eMMC/SDHC controller and an SD card connected to it
69
* 5) SiFive Platform DMA (Direct Memory Access Controller)
70
+ * 6) GEM (Gigabit Ethernet MAC Controller)
71
*
72
* This board currently generates devicetree dynamically that indicates at least
73
* two harts and up to five harts.
74
@@ -XXX,XX +XXX,XX @@
75
#define BIOS_FILENAME "hss.bin"
76
#define RESET_VECTOR 0x20220000
77
78
+/* GEM version */
79
+#define GEM_REVISION 0x0107010c
80
+
81
static const struct MemmapEntry {
82
hwaddr base;
83
hwaddr size;
84
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
85
[MICROCHIP_PFSOC_MMUART2] = { 0x20102000, 0x1000 },
86
[MICROCHIP_PFSOC_MMUART3] = { 0x20104000, 0x1000 },
87
[MICROCHIP_PFSOC_MMUART4] = { 0x20106000, 0x1000 },
88
+ [MICROCHIP_PFSOC_GEM0] = { 0x20110000, 0x2000 },
89
+ [MICROCHIP_PFSOC_GEM1] = { 0x20112000, 0x2000 },
90
[MICROCHIP_PFSOC_ENVM_CFG] = { 0x20200000, 0x1000 },
91
[MICROCHIP_PFSOC_ENVM_DATA] = { 0x20220000, 0x20000 },
92
[MICROCHIP_PFSOC_IOSCB_CFG] = { 0x37080000, 0x1000 },
93
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_instance_init(Object *obj)
94
object_initialize_child(obj, "dma-controller", &s->dma,
95
TYPE_SIFIVE_PDMA);
96
97
+ object_initialize_child(obj, "gem0", &s->gem0, TYPE_CADENCE_GEM);
98
+ object_initialize_child(obj, "gem1", &s->gem1, TYPE_CADENCE_GEM);
99
+
100
object_initialize_child(obj, "sd-controller", &s->sdhci,
101
TYPE_CADENCE_SDHCI);
102
}
103
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
104
MemoryRegion *envm_data = g_new(MemoryRegion, 1);
105
char *plic_hart_config;
106
size_t plic_hart_config_len;
107
+ NICInfo *nd;
108
int i;
31
int i;
109
32
110
sysbus_realize(SYS_BUS_DEVICE(&s->e_cpus), &error_abort);
33
for (i = 0; i < ARRAY_SIZE(isa_edata_arr); i++) {
111
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
34
- if (cpu->env.priv_ver >= isa_edata_arr[i].min_version &&
112
qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_MMUART4_IRQ),
35
- isa_ext_is_enabled(cpu, &isa_edata_arr[i])) {
113
serial_hd(4));
36
+ if (isa_ext_is_enabled(cpu, &isa_edata_arr[i])) {
114
37
new = g_strconcat(old, "_", isa_edata_arr[i].name, NULL);
115
+ /* GEMs */
38
g_free(old);
116
+
39
old = new;
117
+ nd = &nd_table[0];
118
+ if (nd->used) {
119
+ qemu_check_nic_model(nd, TYPE_CADENCE_GEM);
120
+ qdev_set_nic_properties(DEVICE(&s->gem0), nd);
121
+ }
122
+ nd = &nd_table[1];
123
+ if (nd->used) {
124
+ qemu_check_nic_model(nd, TYPE_CADENCE_GEM);
125
+ qdev_set_nic_properties(DEVICE(&s->gem1), nd);
126
+ }
127
+
128
+ object_property_set_int(OBJECT(&s->gem0), "revision", GEM_REVISION, errp);
129
+ object_property_set_int(OBJECT(&s->gem0), "phy-addr", 8, errp);
130
+ sysbus_realize(SYS_BUS_DEVICE(&s->gem0), errp);
131
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->gem0), 0,
132
+ memmap[MICROCHIP_PFSOC_GEM0].base);
133
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->gem0), 0,
134
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_GEM0_IRQ));
135
+
136
+ object_property_set_int(OBJECT(&s->gem1), "revision", GEM_REVISION, errp);
137
+ object_property_set_int(OBJECT(&s->gem1), "phy-addr", 9, errp);
138
+ sysbus_realize(SYS_BUS_DEVICE(&s->gem1), errp);
139
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->gem1), 0,
140
+ memmap[MICROCHIP_PFSOC_GEM1].base);
141
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->gem1), 0,
142
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_GEM1_IRQ));
143
+
144
/* eNVM */
145
memory_region_init_rom(envm_data, OBJECT(dev), "microchip.pfsoc.envm.data",
146
memmap[MICROCHIP_PFSOC_ENVM_DATA].size,
147
--
40
--
148
2.28.0
41
2.40.1
149
150
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
On the Icicle Kit board, the HSS firmware utilizes the on-chip DMA
3
KVM-specific properties are being created inside target/riscv/kvm.c. But
4
controller to move the 2nd stage bootloader in the system memory.
4
at this moment we're gathering all the remaining properties from TCG and
5
Let's connect a DMA controller to Microchip PolarFire SoC.
5
adding them as is when running KVM. This creates a situation where
6
non-KVM properties are setting flags to 'true' due to its default
7
settings (e.g. Zawrs). Users can also freely enable them via command
8
line.
6
9
7
Signed-off-by: Bin Meng <bin.meng@windriver.com>
10
This doesn't impact runtime per se because KVM doesn't care about these
11
flags, but code such as riscv_isa_string_ext() take those flags into
12
account. The result is that, for a KVM guest, setting non-KVM properties
13
will make them appear in the riscv,isa DT.
14
15
We want to keep the same API for both TCG and KVM and at the same time,
16
when running KVM, forbid non-KVM extensions to be enabled internally. We
17
accomplish both by changing riscv_cpu_add_user_properties() to add a
18
mock boolean property for every non-KVM extension in
19
riscv_cpu_extensions[]. Then, when running KVM, users are still free to
20
set extensions at will, but we'll error out if a non-KVM extension is
21
enabled. Setting such extension to 'false' will be ignored.
22
23
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
24
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
8
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
25
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
9
Message-Id: <1598924352-89526-11-git-send-email-bmeng.cn@gmail.com>
26
Message-Id: <20230706101738.460804-18-dbarboza@ventanamicro.com>
10
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
27
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
11
---
28
---
12
include/hw/riscv/microchip_pfsoc.h | 11 +++++++++++
29
target/riscv/cpu.c | 36 ++++++++++++++++++++++++++++++++++++
13
hw/riscv/microchip_pfsoc.c | 15 +++++++++++++++
30
1 file changed, 36 insertions(+)
14
hw/riscv/Kconfig | 1 +
15
3 files changed, 27 insertions(+)
16
31
17
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
32
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
18
index XXXXXXX..XXXXXXX 100644
33
index XXXXXXX..XXXXXXX 100644
19
--- a/include/hw/riscv/microchip_pfsoc.h
34
--- a/target/riscv/cpu.c
20
+++ b/include/hw/riscv/microchip_pfsoc.h
35
+++ b/target/riscv/cpu.c
21
@@ -XXX,XX +XXX,XX @@
36
@@ -XXX,XX +XXX,XX @@ static Property riscv_cpu_extensions[] = {
22
#define HW_MICROCHIP_PFSOC_H
37
DEFINE_PROP_END_OF_LIST(),
23
24
#include "hw/char/mchp_pfsoc_mmuart.h"
25
+#include "hw/dma/sifive_pdma.h"
26
#include "hw/sd/cadence_sdhci.h"
27
28
typedef struct MicrochipPFSoCState {
29
@@ -XXX,XX +XXX,XX @@ typedef struct MicrochipPFSoCState {
30
MchpPfSoCMMUartState *serial2;
31
MchpPfSoCMMUartState *serial3;
32
MchpPfSoCMMUartState *serial4;
33
+ SiFivePDMAState dma;
34
CadenceSDHCIState sdhci;
35
} MicrochipPFSoCState;
36
37
@@ -XXX,XX +XXX,XX @@ enum {
38
MICROCHIP_PFSOC_BUSERR_UNIT4,
39
MICROCHIP_PFSOC_CLINT,
40
MICROCHIP_PFSOC_L2CC,
41
+ MICROCHIP_PFSOC_DMA,
42
MICROCHIP_PFSOC_L2LIM,
43
MICROCHIP_PFSOC_PLIC,
44
MICROCHIP_PFSOC_MMUART0,
45
@@ -XXX,XX +XXX,XX @@ enum {
46
};
38
};
47
39
48
enum {
49
+ MICROCHIP_PFSOC_DMA_IRQ0 = 5,
50
+ MICROCHIP_PFSOC_DMA_IRQ1 = 6,
51
+ MICROCHIP_PFSOC_DMA_IRQ2 = 7,
52
+ MICROCHIP_PFSOC_DMA_IRQ3 = 8,
53
+ MICROCHIP_PFSOC_DMA_IRQ4 = 9,
54
+ MICROCHIP_PFSOC_DMA_IRQ5 = 10,
55
+ MICROCHIP_PFSOC_DMA_IRQ6 = 11,
56
+ MICROCHIP_PFSOC_DMA_IRQ7 = 12,
57
MICROCHIP_PFSOC_EMMC_SD_IRQ = 88,
58
MICROCHIP_PFSOC_MMUART0_IRQ = 90,
59
MICROCHIP_PFSOC_MMUART1_IRQ = 91,
60
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
61
index XXXXXXX..XXXXXXX 100644
62
--- a/hw/riscv/microchip_pfsoc.c
63
+++ b/hw/riscv/microchip_pfsoc.c
64
@@ -XXX,XX +XXX,XX @@
65
* 2) eNVM (Embedded Non-Volatile Memory)
66
* 3) MMUARTs (Multi-Mode UART)
67
* 4) Cadence eMMC/SDHC controller and an SD card connected to it
68
+ * 5) SiFive Platform DMA (Direct Memory Access Controller)
69
*
70
* This board currently generates devicetree dynamically that indicates at least
71
* two harts and up to five harts.
72
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
73
[MICROCHIP_PFSOC_BUSERR_UNIT4] = { 0x1704000, 0x1000 },
74
[MICROCHIP_PFSOC_CLINT] = { 0x2000000, 0x10000 },
75
[MICROCHIP_PFSOC_L2CC] = { 0x2010000, 0x1000 },
76
+ [MICROCHIP_PFSOC_DMA] = { 0x3000000, 0x100000 },
77
[MICROCHIP_PFSOC_L2LIM] = { 0x8000000, 0x2000000 },
78
[MICROCHIP_PFSOC_PLIC] = { 0xc000000, 0x4000000 },
79
[MICROCHIP_PFSOC_MMUART0] = { 0x20000000, 0x1000 },
80
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_instance_init(Object *obj)
81
TYPE_RISCV_CPU_SIFIVE_U54);
82
qdev_prop_set_uint64(DEVICE(&s->u_cpus), "resetvec", RESET_VECTOR);
83
84
+ object_initialize_child(obj, "dma-controller", &s->dma,
85
+ TYPE_SIFIVE_PDMA);
86
+
40
+
87
object_initialize_child(obj, "sd-controller", &s->sdhci,
41
+#ifndef CONFIG_USER_ONLY
88
TYPE_CADENCE_SDHCI);
42
+static void cpu_set_cfg_unavailable(Object *obj, Visitor *v,
89
}
43
+ const char *name,
90
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
44
+ void *opaque, Error **errp)
91
memmap[MICROCHIP_PFSOC_PLIC].size);
45
+{
92
g_free(plic_hart_config);
46
+ const char *propname = opaque;
93
47
+ bool value;
94
+ /* DMA */
48
+
95
+ sysbus_realize(SYS_BUS_DEVICE(&s->dma), errp);
49
+ if (!visit_type_bool(v, name, &value, errp)) {
96
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->dma), 0,
50
+ return;
97
+ memmap[MICROCHIP_PFSOC_DMA].base);
98
+ for (i = 0; i < SIFIVE_PDMA_IRQS; i++) {
99
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->dma), i,
100
+ qdev_get_gpio_in(DEVICE(s->plic),
101
+ MICROCHIP_PFSOC_DMA_IRQ0 + i));
102
+ }
51
+ }
103
+
52
+
104
/* SYSREG */
53
+ if (value) {
105
create_unimplemented_device("microchip.pfsoc.sysreg",
54
+ error_setg(errp, "extension %s is not available with KVM",
106
memmap[MICROCHIP_PFSOC_SYSREG].base,
55
+ propname);
107
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
56
+ }
108
index XXXXXXX..XXXXXXX 100644
57
+}
109
--- a/hw/riscv/Kconfig
58
+#endif
110
+++ b/hw/riscv/Kconfig
59
+
111
@@ -XXX,XX +XXX,XX @@ config MICROCHIP_PFSOC
60
/*
112
select SIFIVE
61
* Add CPU properties with user-facing flags.
113
select UNIMP
62
*
114
select MCHP_PFSOC_MMUART
63
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_add_user_properties(Object *obj)
115
+ select SIFIVE_PDMA
64
if (object_property_find(obj, prop->name)) {
116
select CADENCE_SDHCI
65
continue;
66
}
67
+
68
+ /*
69
+ * Set the default to disabled for every extension
70
+ * unknown to KVM and error out if the user attempts
71
+ * to enable any of them.
72
+ *
73
+ * We're giving a pass for non-bool properties since they're
74
+ * not related to the availability of extensions and can be
75
+ * safely ignored as is.
76
+ */
77
+ if (prop->info == &qdev_prop_bool) {
78
+ object_property_add(obj, prop->name, "bool",
79
+ NULL, cpu_set_cfg_unavailable,
80
+ NULL, (void *)prop->name);
81
+ continue;
82
+ }
83
}
84
#endif
85
qdev_property_add_static(dev, prop);
117
--
86
--
118
2.28.0
87
2.40.1
119
120
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
Microchip PolarFire SoC integrates 3 GPIOs controllers. It seems
3
We're now ready to update the multi-letter extensions status for KVM.
4
enough to create unimplemented devices to cover their register
5
spaces at this point.
6
4
7
With this commit, QEMU can boot to U-Boot (2nd stage bootloader)
5
kvm_riscv_update_cpu_cfg_isa_ext() is called called during vcpu creation
8
all the way to the Linux shell login prompt, with a modified HSS
6
time to verify which user options changes host defaults (via the 'user_set'
9
(1st stage bootloader).
7
flag) and tries to write them back to KVM.
10
8
11
For detailed instructions on how to create images for the Icicle
9
Failure to commit a change to KVM is only ignored in case KVM doesn't
12
Kit board, please check QEMU RISC-V WiKi page at:
10
know about the extension (-EINVAL error code) and the user wanted to
13
https://wiki.qemu.org/Documentation/Platforms/RISCV
11
disable the given extension. Otherwise we're going to abort the boot
12
process.
14
13
15
Signed-off-by: Bin Meng <bin.meng@windriver.com>
14
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
15
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
16
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
16
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
17
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
17
Message-Id: <20230706101738.460804-19-dbarboza@ventanamicro.com>
18
Message-Id: <1598924352-89526-15-git-send-email-bmeng.cn@gmail.com>
19
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
18
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
20
---
19
---
21
include/hw/riscv/microchip_pfsoc.h | 3 +++
20
target/riscv/kvm.c | 27 +++++++++++++++++++++++++++
22
hw/riscv/microchip_pfsoc.c | 14 ++++++++++++++
21
1 file changed, 27 insertions(+)
23
2 files changed, 17 insertions(+)
24
22
25
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
23
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
26
index XXXXXXX..XXXXXXX 100644
24
index XXXXXXX..XXXXXXX 100644
27
--- a/include/hw/riscv/microchip_pfsoc.h
25
--- a/target/riscv/kvm.c
28
+++ b/include/hw/riscv/microchip_pfsoc.h
26
+++ b/target/riscv/kvm.c
29
@@ -XXX,XX +XXX,XX @@ enum {
27
@@ -XXX,XX +XXX,XX @@ static void kvm_cpu_set_multi_ext_cfg(Object *obj, Visitor *v,
30
MICROCHIP_PFSOC_MMUART4,
28
kvm_cpu_cfg_set(cpu, multi_ext_cfg, value);
31
MICROCHIP_PFSOC_GEM0,
29
}
32
MICROCHIP_PFSOC_GEM1,
30
33
+ MICROCHIP_PFSOC_GPIO0,
31
+static void kvm_riscv_update_cpu_cfg_isa_ext(RISCVCPU *cpu, CPUState *cs)
34
+ MICROCHIP_PFSOC_GPIO1,
32
+{
35
+ MICROCHIP_PFSOC_GPIO2,
33
+ CPURISCVState *env = &cpu->env;
36
MICROCHIP_PFSOC_ENVM_CFG,
34
+ uint64_t id, reg;
37
MICROCHIP_PFSOC_ENVM_DATA,
35
+ int i, ret;
38
MICROCHIP_PFSOC_IOSCB_CFG,
39
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
40
index XXXXXXX..XXXXXXX 100644
41
--- a/hw/riscv/microchip_pfsoc.c
42
+++ b/hw/riscv/microchip_pfsoc.c
43
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
44
[MICROCHIP_PFSOC_MMUART4] = { 0x20106000, 0x1000 },
45
[MICROCHIP_PFSOC_GEM0] = { 0x20110000, 0x2000 },
46
[MICROCHIP_PFSOC_GEM1] = { 0x20112000, 0x2000 },
47
+ [MICROCHIP_PFSOC_GPIO0] = { 0x20120000, 0x1000 },
48
+ [MICROCHIP_PFSOC_GPIO1] = { 0x20121000, 0x1000 },
49
+ [MICROCHIP_PFSOC_GPIO2] = { 0x20122000, 0x1000 },
50
[MICROCHIP_PFSOC_ENVM_CFG] = { 0x20200000, 0x1000 },
51
[MICROCHIP_PFSOC_ENVM_DATA] = { 0x20220000, 0x20000 },
52
[MICROCHIP_PFSOC_IOSCB_CFG] = { 0x37080000, 0x1000 },
53
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
54
sysbus_connect_irq(SYS_BUS_DEVICE(&s->gem1), 0,
55
qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_GEM1_IRQ));
56
57
+ /* GPIOs */
58
+ create_unimplemented_device("microchip.pfsoc.gpio0",
59
+ memmap[MICROCHIP_PFSOC_GPIO0].base,
60
+ memmap[MICROCHIP_PFSOC_GPIO0].size);
61
+ create_unimplemented_device("microchip.pfsoc.gpio1",
62
+ memmap[MICROCHIP_PFSOC_GPIO1].base,
63
+ memmap[MICROCHIP_PFSOC_GPIO1].size);
64
+ create_unimplemented_device("microchip.pfsoc.gpio2",
65
+ memmap[MICROCHIP_PFSOC_GPIO2].base,
66
+ memmap[MICROCHIP_PFSOC_GPIO2].size);
67
+
36
+
68
/* eNVM */
37
+ for (i = 0; i < ARRAY_SIZE(kvm_multi_ext_cfgs); i++) {
69
memory_region_init_rom(envm_data, OBJECT(dev), "microchip.pfsoc.envm.data",
38
+ KVMCPUConfig *multi_ext_cfg = &kvm_multi_ext_cfgs[i];
70
memmap[MICROCHIP_PFSOC_ENVM_DATA].size,
39
+
40
+ if (!multi_ext_cfg->user_set) {
41
+ continue;
42
+ }
43
+
44
+ id = kvm_riscv_reg_id(env, KVM_REG_RISCV_ISA_EXT,
45
+ multi_ext_cfg->kvm_reg_id);
46
+ reg = kvm_cpu_cfg_get(cpu, multi_ext_cfg);
47
+ ret = kvm_set_one_reg(cs, id, &reg);
48
+ if (ret != 0) {
49
+ error_report("Unable to %s extension %s in KVM, error %d",
50
+ reg ? "enable" : "disable",
51
+ multi_ext_cfg->name, ret);
52
+ exit(EXIT_FAILURE);
53
+ }
54
+ }
55
+}
56
+
57
static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
58
{
59
int i;
60
@@ -XXX,XX +XXX,XX @@ int kvm_arch_init_vcpu(CPUState *cs)
61
}
62
63
kvm_riscv_update_cpu_misa_ext(cpu, cs);
64
+ kvm_riscv_update_cpu_cfg_isa_ext(cpu, cs);
65
66
return ret;
67
}
71
--
68
--
72
2.28.0
69
2.40.1
73
74
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
At present the PHY address of the PHY connected to GEM is hard-coded
3
There are 2 places in which we need to get a pointer to a certain
4
to either 23 (BOARD_PHY_ADDRESS) or 0. This might not be the case for
4
property of the cpu->cfg struct based on property offset. Next patch
5
all boards. Add a new 'phy-addr' property so that board can specify
5
will add a couple more.
6
the PHY address for each GEM instance.
7
6
8
Signed-off-by: Bin Meng <bin.meng@windriver.com>
7
Create a helper to avoid repeating this code over and over.
9
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
8
10
Reviewed-by: Edgar E. Iglesias <edgar.iglesias@xilinx.com>
9
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
10
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
11
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
11
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
12
Message-Id: <1598924352-89526-12-git-send-email-bmeng.cn@gmail.com>
12
Message-Id: <20230706101738.460804-20-dbarboza@ventanamicro.com>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
13
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
14
---
14
---
15
include/hw/net/cadence_gem.h | 2 ++
15
target/riscv/kvm.c | 11 +++++++----
16
hw/net/cadence_gem.c | 5 +++--
16
1 file changed, 7 insertions(+), 4 deletions(-)
17
2 files changed, 5 insertions(+), 2 deletions(-)
18
17
19
diff --git a/include/hw/net/cadence_gem.h b/include/hw/net/cadence_gem.h
18
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
20
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
21
--- a/include/hw/net/cadence_gem.h
20
--- a/target/riscv/kvm.c
22
+++ b/include/hw/net/cadence_gem.h
21
+++ b/target/riscv/kvm.c
23
@@ -XXX,XX +XXX,XX @@ typedef struct CadenceGEMState {
22
@@ -XXX,XX +XXX,XX @@ static KVMCPUConfig kvm_multi_ext_cfgs[] = {
24
/* Mask of register bits which are write 1 to clear */
23
KVM_EXT_CFG("svpbmt", ext_svpbmt, KVM_RISCV_ISA_EXT_SVPBMT),
25
uint32_t regs_w1c[CADENCE_GEM_MAXREG];
24
};
26
25
27
+ /* PHY address */
26
+static void *kvmconfig_get_cfg_addr(RISCVCPU *cpu, KVMCPUConfig *kvmcfg)
28
+ uint8_t phy_addr;
27
+{
29
/* PHY registers backing store */
28
+ return (void *)&cpu->cfg + kvmcfg->offset;
30
uint16_t phy_regs[32];
29
+}
31
30
+
32
diff --git a/hw/net/cadence_gem.c b/hw/net/cadence_gem.c
31
static void kvm_cpu_cfg_set(RISCVCPU *cpu, KVMCPUConfig *multi_ext,
33
index XXXXXXX..XXXXXXX 100644
32
uint32_t val)
34
--- a/hw/net/cadence_gem.c
33
{
35
+++ b/hw/net/cadence_gem.c
34
- int cpu_cfg_offset = multi_ext->offset;
36
@@ -XXX,XX +XXX,XX @@ static uint64_t gem_read(void *opaque, hwaddr offset, unsigned size)
35
- bool *ext_enabled = (void *)&cpu->cfg + cpu_cfg_offset;
37
uint32_t phy_addr, reg_num;
36
+ bool *ext_enabled = kvmconfig_get_cfg_addr(cpu, multi_ext);
38
37
39
phy_addr = (retval & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
38
*ext_enabled = val;
40
- if (phy_addr == BOARD_PHY_ADDRESS || phy_addr == 0) {
39
}
41
+ if (phy_addr == s->phy_addr || phy_addr == 0) {
40
@@ -XXX,XX +XXX,XX @@ static void kvm_cpu_cfg_set(RISCVCPU *cpu, KVMCPUConfig *multi_ext,
42
reg_num = (retval & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
41
static uint32_t kvm_cpu_cfg_get(RISCVCPU *cpu,
43
retval &= 0xFFFF0000;
42
KVMCPUConfig *multi_ext)
44
retval |= gem_phy_read(s, reg_num);
43
{
45
@@ -XXX,XX +XXX,XX @@ static void gem_write(void *opaque, hwaddr offset, uint64_t val,
44
- int cpu_cfg_offset = multi_ext->offset;
46
uint32_t phy_addr, reg_num;
45
- bool *ext_enabled = (void *)&cpu->cfg + cpu_cfg_offset;
47
46
+ bool *ext_enabled = kvmconfig_get_cfg_addr(cpu, multi_ext);
48
phy_addr = (val & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
47
49
- if (phy_addr == BOARD_PHY_ADDRESS || phy_addr == 0) {
48
return *ext_enabled;
50
+ if (phy_addr == s->phy_addr || phy_addr == 0) {
49
}
51
reg_num = (val & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
52
gem_phy_write(s, reg_num, val);
53
}
54
@@ -XXX,XX +XXX,XX @@ static Property gem_properties[] = {
55
DEFINE_NIC_PROPERTIES(CadenceGEMState, conf),
56
DEFINE_PROP_UINT32("revision", CadenceGEMState, revision,
57
GEM_MODID_VALUE),
58
+ DEFINE_PROP_UINT8("phy-addr", CadenceGEMState, phy_addr, BOARD_PHY_ADDRESS),
59
DEFINE_PROP_UINT8("num-priority-queues", CadenceGEMState,
60
num_priority_queues, 1),
61
DEFINE_PROP_UINT8("num-type1-screeners", CadenceGEMState,
62
--
50
--
63
2.28.0
51
2.40.1
64
65
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
2
2
3
Microchip PolarFire SoC integrates one Cadence SDHCI controller.
3
If we don't set a proper cbom_blocksize|cboz_blocksize in the FDT the
4
On the Icicle Kit board, one eMMC chip and an external SD card
4
Linux Kernel will fail to detect the availability of the CBOM/CBOZ
5
connect to this controller depending on different configuration.
5
extensions, regardless of the contents of the 'riscv,isa' DT prop.
6
6
7
As QEMU does not support eMMC yet, we just emulate the SD card
7
The FDT is being written using the cpu->cfg.cbom|z_blocksize attributes,
8
configuration. To test this, the Hart Software Services (HSS)
8
so let's expose them as user properties like it is already done with
9
should choose the SD card configuration:
9
TCG.
10
10
11
$ cp boards/icicle-kit-es/def_config.sdcard .config
11
This will also require us to determine proper blocksize values during
12
$ make BOARD=icicle-kit-es
12
init() time since the FDT is already created during realize(). We'll
13
take a ride in kvm_riscv_init_multiext_cfg() to do it. Note that we
14
don't need to fetch both cbom and cboz blocksizes every time: check for
15
their parent extensions (icbom and icboz) and only read the blocksizes
16
if needed.
13
17
14
The SD card image can be built from the Yocto BSP at:
18
In contrast with cbom|z_blocksize properties from TCG, the user is not
15
https://github.com/polarfire-soc/meta-polarfire-soc-yocto-bsp
19
able to set any value that is different from the 'host' value when
20
running KVM. KVM can be particularly harsh dealing with it: a ENOTSUPP
21
can be thrown for the mere attempt of executing kvm_set_one_reg() for
22
these 2 regs.
16
23
17
Note the generated SD card image should be resized before use:
24
Hopefully we don't need to call kvm_set_one_reg() for these regs.
18
$ qemu-img resize /path/to/sdcard.img 4G
25
We'll check if the user input matches the host value in
26
kvm_cpu_set_cbomz_blksize(), the set() accessor for both blocksize
27
properties. We'll fail fast since it's already known to not be
28
supported.
19
29
20
Launch QEMU with the following command:
30
Signed-off-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
21
$ qemu-system-riscv64 -nographic -M microchip-icicle-kit -sd sdcard.img
31
Reviewed-by: Andrew Jones <ajones@ventanamicro.com>
22
32
Acked-by: Alistair Francis <alistair.francis@wdc.com>
23
Signed-off-by: Bin Meng <bin.meng@windriver.com>
33
Message-Id: <20230706101738.460804-21-dbarboza@ventanamicro.com>
24
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
25
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
26
Message-Id: <1598924352-89526-9-git-send-email-bmeng.cn@gmail.com>
27
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
34
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
28
---
35
---
29
include/hw/riscv/microchip_pfsoc.h | 4 ++++
36
target/riscv/kvm.c | 70 ++++++++++++++++++++++++++++++++++++++++++++++
30
hw/riscv/microchip_pfsoc.c | 23 +++++++++++++++++++++++
37
1 file changed, 70 insertions(+)
31
hw/riscv/Kconfig | 1 +
32
3 files changed, 28 insertions(+)
33
38
34
diff --git a/include/hw/riscv/microchip_pfsoc.h b/include/hw/riscv/microchip_pfsoc.h
39
diff --git a/target/riscv/kvm.c b/target/riscv/kvm.c
35
index XXXXXXX..XXXXXXX 100644
40
index XXXXXXX..XXXXXXX 100644
36
--- a/include/hw/riscv/microchip_pfsoc.h
41
--- a/target/riscv/kvm.c
37
+++ b/include/hw/riscv/microchip_pfsoc.h
42
+++ b/target/riscv/kvm.c
38
@@ -XXX,XX +XXX,XX @@
43
@@ -XXX,XX +XXX,XX @@ static void kvm_cpu_set_multi_ext_cfg(Object *obj, Visitor *v,
39
#define HW_MICROCHIP_PFSOC_H
44
kvm_cpu_cfg_set(cpu, multi_ext_cfg, value);
40
45
}
41
#include "hw/char/mchp_pfsoc_mmuart.h"
46
42
+#include "hw/sd/cadence_sdhci.h"
47
+static KVMCPUConfig kvm_cbom_blocksize = {
43
48
+ .name = "cbom_blocksize",
44
typedef struct MicrochipPFSoCState {
49
+ .offset = CPUCFG(cbom_blocksize),
45
/*< private >*/
50
+ .kvm_reg_id = KVM_REG_RISCV_CONFIG_REG(zicbom_block_size)
46
@@ -XXX,XX +XXX,XX @@ typedef struct MicrochipPFSoCState {
51
+};
47
MchpPfSoCMMUartState *serial2;
48
MchpPfSoCMMUartState *serial3;
49
MchpPfSoCMMUartState *serial4;
50
+ CadenceSDHCIState sdhci;
51
} MicrochipPFSoCState;
52
53
#define TYPE_MICROCHIP_PFSOC "microchip.pfsoc"
54
@@ -XXX,XX +XXX,XX @@ enum {
55
MICROCHIP_PFSOC_MMUART0,
56
MICROCHIP_PFSOC_SYSREG,
57
MICROCHIP_PFSOC_MPUCFG,
58
+ MICROCHIP_PFSOC_EMMC_SD,
59
MICROCHIP_PFSOC_MMUART1,
60
MICROCHIP_PFSOC_MMUART2,
61
MICROCHIP_PFSOC_MMUART3,
62
@@ -XXX,XX +XXX,XX @@ enum {
63
};
64
65
enum {
66
+ MICROCHIP_PFSOC_EMMC_SD_IRQ = 88,
67
MICROCHIP_PFSOC_MMUART0_IRQ = 90,
68
MICROCHIP_PFSOC_MMUART1_IRQ = 91,
69
MICROCHIP_PFSOC_MMUART2_IRQ = 92,
70
diff --git a/hw/riscv/microchip_pfsoc.c b/hw/riscv/microchip_pfsoc.c
71
index XXXXXXX..XXXXXXX 100644
72
--- a/hw/riscv/microchip_pfsoc.c
73
+++ b/hw/riscv/microchip_pfsoc.c
74
@@ -XXX,XX +XXX,XX @@
75
* 1) PLIC (Platform Level Interrupt Controller)
76
* 2) eNVM (Embedded Non-Volatile Memory)
77
* 3) MMUARTs (Multi-Mode UART)
78
+ * 4) Cadence eMMC/SDHC controller and an SD card connected to it
79
*
80
* This board currently generates devicetree dynamically that indicates at least
81
* two harts and up to five harts.
82
@@ -XXX,XX +XXX,XX @@ static const struct MemmapEntry {
83
[MICROCHIP_PFSOC_MMUART0] = { 0x20000000, 0x1000 },
84
[MICROCHIP_PFSOC_SYSREG] = { 0x20002000, 0x2000 },
85
[MICROCHIP_PFSOC_MPUCFG] = { 0x20005000, 0x1000 },
86
+ [MICROCHIP_PFSOC_EMMC_SD] = { 0x20008000, 0x1000 },
87
[MICROCHIP_PFSOC_MMUART1] = { 0x20100000, 0x1000 },
88
[MICROCHIP_PFSOC_MMUART2] = { 0x20102000, 0x1000 },
89
[MICROCHIP_PFSOC_MMUART3] = { 0x20104000, 0x1000 },
90
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_instance_init(Object *obj)
91
qdev_prop_set_string(DEVICE(&s->u_cpus), "cpu-type",
92
TYPE_RISCV_CPU_SIFIVE_U54);
93
qdev_prop_set_uint64(DEVICE(&s->u_cpus), "resetvec", RESET_VECTOR);
94
+
52
+
95
+ object_initialize_child(obj, "sd-controller", &s->sdhci,
53
+static KVMCPUConfig kvm_cboz_blocksize = {
96
+ TYPE_CADENCE_SDHCI);
54
+ .name = "cboz_blocksize",
55
+ .offset = CPUCFG(cboz_blocksize),
56
+ .kvm_reg_id = KVM_REG_RISCV_CONFIG_REG(zicboz_block_size)
57
+};
58
+
59
+static void kvm_cpu_set_cbomz_blksize(Object *obj, Visitor *v,
60
+ const char *name,
61
+ void *opaque, Error **errp)
62
+{
63
+ KVMCPUConfig *cbomz_cfg = opaque;
64
+ RISCVCPU *cpu = RISCV_CPU(obj);
65
+ uint16_t value, *host_val;
66
+
67
+ if (!visit_type_uint16(v, name, &value, errp)) {
68
+ return;
69
+ }
70
+
71
+ host_val = kvmconfig_get_cfg_addr(cpu, cbomz_cfg);
72
+
73
+ if (value != *host_val) {
74
+ error_report("Unable to set %s to a different value than "
75
+ "the host (%u)",
76
+ cbomz_cfg->name, *host_val);
77
+ exit(EXIT_FAILURE);
78
+ }
79
+
80
+ cbomz_cfg->user_set = true;
81
+}
82
+
83
static void kvm_riscv_update_cpu_cfg_isa_ext(RISCVCPU *cpu, CPUState *cs)
84
{
85
CPURISCVState *env = &cpu->env;
86
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_add_cpu_user_properties(Object *cpu_obj)
87
kvm_cpu_set_multi_ext_cfg,
88
NULL, multi_cfg);
89
}
90
+
91
+ object_property_add(cpu_obj, "cbom_blocksize", "uint16",
92
+ NULL, kvm_cpu_set_cbomz_blksize,
93
+ NULL, &kvm_cbom_blocksize);
94
+
95
+ object_property_add(cpu_obj, "cboz_blocksize", "uint16",
96
+ NULL, kvm_cpu_set_cbomz_blksize,
97
+ NULL, &kvm_cboz_blocksize);
97
}
98
}
98
99
99
static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
100
static int kvm_riscv_get_regs_core(CPUState *cs)
100
@@ -XXX,XX +XXX,XX @@ static void microchip_pfsoc_soc_realize(DeviceState *dev, Error **errp)
101
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_init_misa_ext_mask(RISCVCPU *cpu,
101
memmap[MICROCHIP_PFSOC_MPUCFG].base,
102
env->misa_ext = env->misa_ext_mask;
102
memmap[MICROCHIP_PFSOC_MPUCFG].size);
103
}
103
104
104
+ /* SDHCI */
105
+static void kvm_riscv_read_cbomz_blksize(RISCVCPU *cpu, KVMScratchCPU *kvmcpu,
105
+ sysbus_realize(SYS_BUS_DEVICE(&s->sdhci), errp);
106
+ KVMCPUConfig *cbomz_cfg)
106
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->sdhci), 0,
107
+{
107
+ memmap[MICROCHIP_PFSOC_EMMC_SD].base);
108
+ CPURISCVState *env = &cpu->env;
108
+ sysbus_connect_irq(SYS_BUS_DEVICE(&s->sdhci), 0,
109
+ struct kvm_one_reg reg;
109
+ qdev_get_gpio_in(DEVICE(s->plic), MICROCHIP_PFSOC_EMMC_SD_IRQ));
110
+ int ret;
110
+
111
+
111
/* MMUARTs */
112
+ reg.id = kvm_riscv_reg_id(env, KVM_REG_RISCV_CONFIG,
112
s->serial0 = mchp_pfsoc_mmuart_create(system_memory,
113
+ cbomz_cfg->kvm_reg_id);
113
memmap[MICROCHIP_PFSOC_MMUART0].base,
114
+ reg.addr = (uint64_t)kvmconfig_get_cfg_addr(cpu, cbomz_cfg);
114
@@ -XXX,XX +XXX,XX @@ static void microchip_icicle_kit_machine_init(MachineState *machine)
115
+ ret = ioctl(kvmcpu->cpufd, KVM_GET_ONE_REG, &reg);
115
MicrochipIcicleKitState *s = MICROCHIP_ICICLE_KIT_MACHINE(machine);
116
+ if (ret != 0) {
116
MemoryRegion *system_memory = get_system_memory();
117
+ error_report("Unable to read KVM reg %s, error %d",
117
MemoryRegion *main_mem = g_new(MemoryRegion, 1);
118
+ cbomz_cfg->name, ret);
118
+ DriveInfo *dinfo = drive_get_next(IF_SD);
119
+ exit(EXIT_FAILURE);
119
120
+ }
120
/* Sanity check on RAM size */
121
+}
121
if (machine->ram_size < mc->default_ram_size) {
122
@@ -XXX,XX +XXX,XX @@ static void microchip_icicle_kit_machine_init(MachineState *machine)
123
124
/* Load the firmware */
125
riscv_find_and_load_firmware(machine, BIOS_FILENAME, RESET_VECTOR, NULL);
126
+
122
+
127
+ /* Attach an SD card */
123
static void kvm_riscv_init_multiext_cfg(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
128
+ if (dinfo) {
124
{
129
+ CadenceSDHCIState *sdhci = &(s->soc.sdhci);
125
CPURISCVState *env = &cpu->env;
130
+ DeviceState *card = qdev_new(TYPE_SD_CARD);
126
@@ -XXX,XX +XXX,XX @@ static void kvm_riscv_init_multiext_cfg(RISCVCPU *cpu, KVMScratchCPU *kvmcpu)
127
128
kvm_cpu_cfg_set(cpu, multi_ext_cfg, val);
129
}
131
+
130
+
132
+ qdev_prop_set_drive_err(card, "drive", blk_by_legacy_dinfo(dinfo),
131
+ if (cpu->cfg.ext_icbom) {
133
+ &error_fatal);
132
+ kvm_riscv_read_cbomz_blksize(cpu, kvmcpu, &kvm_cbom_blocksize);
134
+ qdev_realize_and_unref(card, sdhci->bus, &error_fatal);
133
+ }
134
+
135
+ if (cpu->cfg.ext_icboz) {
136
+ kvm_riscv_read_cbomz_blksize(cpu, kvmcpu, &kvm_cboz_blocksize);
135
+ }
137
+ }
136
}
138
}
137
139
138
static void microchip_icicle_kit_machine_class_init(ObjectClass *oc, void *data)
140
void kvm_riscv_init_user_properties(Object *cpu_obj)
139
diff --git a/hw/riscv/Kconfig b/hw/riscv/Kconfig
140
index XXXXXXX..XXXXXXX 100644
141
--- a/hw/riscv/Kconfig
142
+++ b/hw/riscv/Kconfig
143
@@ -XXX,XX +XXX,XX @@ config MICROCHIP_PFSOC
144
select SIFIVE
145
select UNIMP
146
select MCHP_PFSOC_MMUART
147
+ select CADENCE_SDHCI
148
--
141
--
149
2.28.0
142
2.40.1
150
151
diff view generated by jsdifflib
1
From: Bin Meng <bin.meng@windriver.com>
1
From: Christoph Müllner <christoph.muellner@vrull.eu>
2
2
3
Now that we have the newly introduced 'resetvec' property in the
3
This patch introduces the RISC-V Zfa extension, which introduces
4
RISC-V CPU and HART, instead of hard-coding the reset vector addr
4
additional floating-point instructions:
5
in the CPU's instance_init(), move that to riscv_cpu_realize()
5
* fli (load-immediate) with pre-defined immediates
6
based on the configured property value from the RISC-V machines.
6
* fminm/fmaxm (like fmin/fmax but with different NaN behaviour)
7
* fround/froundmx (round to integer)
8
* fcvtmod.w.d (Modular Convert-to-Integer)
9
* fmv* to access high bits of float register bigger than XLEN
10
* Quiet comparison instructions (fleq/fltq)
7
11
8
Signed-off-by: Bin Meng <bin.meng@windriver.com>
12
Zfa defines its instructions in combination with the following extensions:
9
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
13
* single-precision floating-point (F)
10
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
14
* double-precision floating-point (D)
11
Message-Id: <1598924352-89526-4-git-send-email-bmeng.cn@gmail.com>
15
* quad-precision floating-point (Q)
16
* half-precision floating-point (Zfh)
17
18
Since QEMU does not support the RISC-V quad-precision floating-point
19
ISA extension (Q), this patch does not include the instructions that
20
depend on this extension. All other instructions are included in this
21
patch.
22
23
The Zfa specification can be found here:
24
https://github.com/riscv/riscv-isa-manual/blob/master/src/zfa.tex
25
The Zfa specifciation is frozen and is in public review since May 3, 2023:
26
https://groups.google.com/a/groups.riscv.org/g/isa-dev/c/SED4ntBkabg
27
28
The patch also includes a TCG test for the fcvtmod.w.d instruction.
29
The test cases test for correct results and flag behaviour.
30
Note, that the Zfa specification requires fcvtmod's flag behaviour
31
to be identical to a fcvt with the same operands (which is also
32
tested).
33
34
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
35
Signed-off-by: Christoph Müllner <christoph.muellner@vrull.eu>
36
Message-Id: <20230710071243.282464-1-christoph.muellner@vrull.eu>
12
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
37
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
13
---
38
---
14
hw/riscv/opentitan.c | 1 +
39
disas/riscv.h | 3 +
15
hw/riscv/sifive_e.c | 1 +
40
target/riscv/cpu_cfg.h | 1 +
16
hw/riscv/sifive_u.c | 2 ++
41
target/riscv/helper.h | 19 +
17
target/riscv/cpu.c | 7 ++-----
42
target/riscv/insn32.decode | 26 ++
18
4 files changed, 6 insertions(+), 5 deletions(-)
43
disas/riscv.c | 139 ++++++
44
target/riscv/cpu.c | 8 +
45
target/riscv/fpu_helper.c | 154 +++++++
46
target/riscv/translate.c | 1 +
47
tests/tcg/riscv64/test-fcvtmod.c | 345 ++++++++++++++
48
target/riscv/insn_trans/trans_rvzfa.c.inc | 521 ++++++++++++++++++++++
49
tests/tcg/riscv64/Makefile.target | 6 +
50
11 files changed, 1223 insertions(+)
51
create mode 100644 tests/tcg/riscv64/test-fcvtmod.c
52
create mode 100644 target/riscv/insn_trans/trans_rvzfa.c.inc
19
53
20
diff --git a/hw/riscv/opentitan.c b/hw/riscv/opentitan.c
54
diff --git a/disas/riscv.h b/disas/riscv.h
21
index XXXXXXX..XXXXXXX 100644
55
index XXXXXXX..XXXXXXX 100644
22
--- a/hw/riscv/opentitan.c
56
--- a/disas/riscv.h
23
+++ b/hw/riscv/opentitan.c
57
+++ b/disas/riscv.h
24
@@ -XXX,XX +XXX,XX @@ static void lowrisc_ibex_soc_realize(DeviceState *dev_soc, Error **errp)
58
@@ -XXX,XX +XXX,XX @@ typedef enum {
25
&error_abort);
59
rv_codec_r_imm2,
26
object_property_set_int(OBJECT(&s->cpus), "num-harts", ms->smp.cpus,
60
rv_codec_r2_immhl,
27
&error_abort);
61
rv_codec_r2_imm2_imm5,
28
+ object_property_set_int(OBJECT(&s->cpus), "resetvec", 0x8090, &error_abort);
62
+ rv_codec_fli,
29
sysbus_realize(SYS_BUS_DEVICE(&s->cpus), &error_abort);
63
} rv_codec;
30
64
31
/* Boot ROM */
65
/* structures */
32
diff --git a/hw/riscv/sifive_e.c b/hw/riscv/sifive_e.c
66
@@ -XXX,XX +XXX,XX @@ enum {
67
#define rv_fmt_rd_offset "O\t0,o"
68
#define rv_fmt_rd_rs1_rs2 "O\t0,1,2"
69
#define rv_fmt_frd_rs1 "O\t3,1"
70
+#define rv_fmt_frd_rs1_rs2 "O\t3,1,2"
71
#define rv_fmt_frd_frs1 "O\t3,4"
72
#define rv_fmt_rd_frs1 "O\t0,4"
73
#define rv_fmt_rd_frs1_frs2 "O\t0,4,5"
74
@@ -XXX,XX +XXX,XX @@ enum {
75
#define rv_fmt_rd_rs1_immh_imml "O\t0,1,i,j"
76
#define rv_fmt_rd_rs1_immh_imml_addr "O\t0,(1),i,j"
77
#define rv_fmt_rd2_imm "O\t0,2,(1),i"
78
+#define rv_fmt_fli "O\t3,h"
79
80
#endif /* DISAS_RISCV_H */
81
diff --git a/target/riscv/cpu_cfg.h b/target/riscv/cpu_cfg.h
33
index XXXXXXX..XXXXXXX 100644
82
index XXXXXXX..XXXXXXX 100644
34
--- a/hw/riscv/sifive_e.c
83
--- a/target/riscv/cpu_cfg.h
35
+++ b/hw/riscv/sifive_e.c
84
+++ b/target/riscv/cpu_cfg.h
36
@@ -XXX,XX +XXX,XX @@ static void sifive_e_soc_init(Object *obj)
85
@@ -XXX,XX +XXX,XX @@ struct RISCVCPUConfig {
37
object_initialize_child(obj, "cpus", &s->cpus, TYPE_RISCV_HART_ARRAY);
86
bool ext_svpbmt;
38
object_property_set_int(OBJECT(&s->cpus), "num-harts", ms->smp.cpus,
87
bool ext_zdinx;
39
&error_abort);
88
bool ext_zawrs;
40
+ object_property_set_int(OBJECT(&s->cpus), "resetvec", 0x1004, &error_abort);
89
+ bool ext_zfa;
41
object_initialize_child(obj, "riscv.sifive.e.gpio0", &s->gpio,
90
bool ext_zfbfmin;
42
TYPE_SIFIVE_GPIO);
91
bool ext_zfh;
43
}
92
bool ext_zfhmin;
44
diff --git a/hw/riscv/sifive_u.c b/hw/riscv/sifive_u.c
93
diff --git a/target/riscv/helper.h b/target/riscv/helper.h
45
index XXXXXXX..XXXXXXX 100644
94
index XXXXXXX..XXXXXXX 100644
46
--- a/hw/riscv/sifive_u.c
95
--- a/target/riscv/helper.h
47
+++ b/hw/riscv/sifive_u.c
96
+++ b/target/riscv/helper.h
48
@@ -XXX,XX +XXX,XX @@ static void sifive_u_soc_instance_init(Object *obj)
97
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_3(fsub_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
49
qdev_prop_set_uint32(DEVICE(&s->e_cpus), "num-harts", 1);
98
DEF_HELPER_FLAGS_3(fmul_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
50
qdev_prop_set_uint32(DEVICE(&s->e_cpus), "hartid-base", 0);
99
DEF_HELPER_FLAGS_3(fdiv_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
51
qdev_prop_set_string(DEVICE(&s->e_cpus), "cpu-type", SIFIVE_E_CPU);
100
DEF_HELPER_FLAGS_3(fmin_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
52
+ qdev_prop_set_uint64(DEVICE(&s->e_cpus), "resetvec", 0x1004);
101
+DEF_HELPER_FLAGS_3(fminm_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
53
102
DEF_HELPER_FLAGS_3(fmax_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
54
object_initialize_child(obj, "u-cluster", &s->u_cluster, TYPE_CPU_CLUSTER);
103
+DEF_HELPER_FLAGS_3(fmaxm_s, TCG_CALL_NO_RWG, i64, env, i64, i64)
55
qdev_prop_set_uint32(DEVICE(&s->u_cluster), "cluster-id", 1);
104
DEF_HELPER_FLAGS_2(fsqrt_s, TCG_CALL_NO_RWG, i64, env, i64)
56
@@ -XXX,XX +XXX,XX @@ static void sifive_u_soc_instance_init(Object *obj)
105
DEF_HELPER_FLAGS_3(fle_s, TCG_CALL_NO_RWG, tl, env, i64, i64)
57
qdev_prop_set_uint32(DEVICE(&s->u_cpus), "num-harts", ms->smp.cpus - 1);
106
+DEF_HELPER_FLAGS_3(fleq_s, TCG_CALL_NO_RWG, tl, env, i64, i64)
58
qdev_prop_set_uint32(DEVICE(&s->u_cpus), "hartid-base", 1);
107
DEF_HELPER_FLAGS_3(flt_s, TCG_CALL_NO_RWG, tl, env, i64, i64)
59
qdev_prop_set_string(DEVICE(&s->u_cpus), "cpu-type", SIFIVE_U_CPU);
108
+DEF_HELPER_FLAGS_3(fltq_s, TCG_CALL_NO_RWG, tl, env, i64, i64)
60
+ qdev_prop_set_uint64(DEVICE(&s->u_cpus), "resetvec", 0x1004);
109
DEF_HELPER_FLAGS_3(feq_s, TCG_CALL_NO_RWG, tl, env, i64, i64)
61
110
DEF_HELPER_FLAGS_2(fcvt_w_s, TCG_CALL_NO_RWG, tl, env, i64)
62
object_initialize_child(obj, "prci", &s->prci, TYPE_SIFIVE_U_PRCI);
111
DEF_HELPER_FLAGS_2(fcvt_wu_s, TCG_CALL_NO_RWG, tl, env, i64)
63
object_initialize_child(obj, "otp", &s->otp, TYPE_SIFIVE_U_OTP);
112
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_2(fcvt_s_wu, TCG_CALL_NO_RWG, i64, env, tl)
113
DEF_HELPER_FLAGS_2(fcvt_s_l, TCG_CALL_NO_RWG, i64, env, tl)
114
DEF_HELPER_FLAGS_2(fcvt_s_lu, TCG_CALL_NO_RWG, i64, env, tl)
115
DEF_HELPER_FLAGS_2(fclass_s, TCG_CALL_NO_RWG_SE, tl, env, i64)
116
+DEF_HELPER_FLAGS_2(fround_s, TCG_CALL_NO_RWG_SE, i64, env, i64)
117
+DEF_HELPER_FLAGS_2(froundnx_s, TCG_CALL_NO_RWG_SE, i64, env, i64)
118
119
/* Floating Point - Double Precision */
120
DEF_HELPER_FLAGS_3(fadd_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
121
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_3(fsub_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
122
DEF_HELPER_FLAGS_3(fmul_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
123
DEF_HELPER_FLAGS_3(fdiv_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
124
DEF_HELPER_FLAGS_3(fmin_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
125
+DEF_HELPER_FLAGS_3(fminm_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
126
DEF_HELPER_FLAGS_3(fmax_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
127
+DEF_HELPER_FLAGS_3(fmaxm_d, TCG_CALL_NO_RWG, i64, env, i64, i64)
128
DEF_HELPER_FLAGS_2(fcvt_s_d, TCG_CALL_NO_RWG, i64, env, i64)
129
DEF_HELPER_FLAGS_2(fcvt_d_s, TCG_CALL_NO_RWG, i64, env, i64)
130
DEF_HELPER_FLAGS_2(fsqrt_d, TCG_CALL_NO_RWG, i64, env, i64)
131
DEF_HELPER_FLAGS_3(fle_d, TCG_CALL_NO_RWG, tl, env, i64, i64)
132
+DEF_HELPER_FLAGS_3(fleq_d, TCG_CALL_NO_RWG, tl, env, i64, i64)
133
DEF_HELPER_FLAGS_3(flt_d, TCG_CALL_NO_RWG, tl, env, i64, i64)
134
+DEF_HELPER_FLAGS_3(fltq_d, TCG_CALL_NO_RWG, tl, env, i64, i64)
135
DEF_HELPER_FLAGS_3(feq_d, TCG_CALL_NO_RWG, tl, env, i64, i64)
136
DEF_HELPER_FLAGS_2(fcvt_w_d, TCG_CALL_NO_RWG, tl, env, i64)
137
+DEF_HELPER_FLAGS_2(fcvtmod_w_d, TCG_CALL_NO_RWG, i64, env, i64)
138
DEF_HELPER_FLAGS_2(fcvt_wu_d, TCG_CALL_NO_RWG, tl, env, i64)
139
DEF_HELPER_FLAGS_2(fcvt_l_d, TCG_CALL_NO_RWG, tl, env, i64)
140
DEF_HELPER_FLAGS_2(fcvt_lu_d, TCG_CALL_NO_RWG, tl, env, i64)
141
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_2(fcvt_d_wu, TCG_CALL_NO_RWG, i64, env, tl)
142
DEF_HELPER_FLAGS_2(fcvt_d_l, TCG_CALL_NO_RWG, i64, env, tl)
143
DEF_HELPER_FLAGS_2(fcvt_d_lu, TCG_CALL_NO_RWG, i64, env, tl)
144
DEF_HELPER_FLAGS_1(fclass_d, TCG_CALL_NO_RWG_SE, tl, i64)
145
+DEF_HELPER_FLAGS_2(fround_d, TCG_CALL_NO_RWG_SE, i64, env, i64)
146
+DEF_HELPER_FLAGS_2(froundnx_d, TCG_CALL_NO_RWG_SE, i64, env, i64)
147
148
/* Bitmanip */
149
DEF_HELPER_FLAGS_2(clmul, TCG_CALL_NO_RWG_SE, tl, tl, tl)
150
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_3(fsub_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
151
DEF_HELPER_FLAGS_3(fmul_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
152
DEF_HELPER_FLAGS_3(fdiv_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
153
DEF_HELPER_FLAGS_3(fmin_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
154
+DEF_HELPER_FLAGS_3(fminm_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
155
DEF_HELPER_FLAGS_3(fmax_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
156
+DEF_HELPER_FLAGS_3(fmaxm_h, TCG_CALL_NO_RWG, i64, env, i64, i64)
157
DEF_HELPER_FLAGS_2(fsqrt_h, TCG_CALL_NO_RWG, i64, env, i64)
158
DEF_HELPER_FLAGS_3(fle_h, TCG_CALL_NO_RWG, tl, env, i64, i64)
159
+DEF_HELPER_FLAGS_3(fleq_h, TCG_CALL_NO_RWG, tl, env, i64, i64)
160
DEF_HELPER_FLAGS_3(flt_h, TCG_CALL_NO_RWG, tl, env, i64, i64)
161
+DEF_HELPER_FLAGS_3(fltq_h, TCG_CALL_NO_RWG, tl, env, i64, i64)
162
DEF_HELPER_FLAGS_3(feq_h, TCG_CALL_NO_RWG, tl, env, i64, i64)
163
DEF_HELPER_FLAGS_2(fcvt_s_h, TCG_CALL_NO_RWG, i64, env, i64)
164
DEF_HELPER_FLAGS_2(fcvt_h_s, TCG_CALL_NO_RWG, i64, env, i64)
165
@@ -XXX,XX +XXX,XX @@ DEF_HELPER_FLAGS_2(fcvt_h_wu, TCG_CALL_NO_RWG, i64, env, tl)
166
DEF_HELPER_FLAGS_2(fcvt_h_l, TCG_CALL_NO_RWG, i64, env, tl)
167
DEF_HELPER_FLAGS_2(fcvt_h_lu, TCG_CALL_NO_RWG, i64, env, tl)
168
DEF_HELPER_FLAGS_2(fclass_h, TCG_CALL_NO_RWG_SE, tl, env, i64)
169
+DEF_HELPER_FLAGS_2(fround_h, TCG_CALL_NO_RWG_SE, i64, env, i64)
170
+DEF_HELPER_FLAGS_2(froundnx_h, TCG_CALL_NO_RWG_SE, i64, env, i64)
171
172
/* Cache-block operations */
173
DEF_HELPER_2(cbo_clean_flush, void, env, tl)
174
diff --git a/target/riscv/insn32.decode b/target/riscv/insn32.decode
175
index XXXXXXX..XXXXXXX 100644
176
--- a/target/riscv/insn32.decode
177
+++ b/target/riscv/insn32.decode
178
@@ -XXX,XX +XXX,XX @@ binvi 01101. ........... 001 ..... 0010011 @sh
179
bset 0010100 .......... 001 ..... 0110011 @r
180
bseti 00101. ........... 001 ..... 0010011 @sh
181
182
+# *** Zfa Standard Extension ***
183
+fli_s 1111000 00001 ..... 000 ..... 1010011 @r2
184
+fli_d 1111001 00001 ..... 000 ..... 1010011 @r2
185
+fli_h 1111010 00001 ..... 000 ..... 1010011 @r2
186
+fminm_s 0010100 ..... ..... 010 ..... 1010011 @r
187
+fmaxm_s 0010100 ..... ..... 011 ..... 1010011 @r
188
+fminm_d 0010101 ..... ..... 010 ..... 1010011 @r
189
+fmaxm_d 0010101 ..... ..... 011 ..... 1010011 @r
190
+fminm_h 0010110 ..... ..... 010 ..... 1010011 @r
191
+fmaxm_h 0010110 ..... ..... 011 ..... 1010011 @r
192
+fround_s 0100000 00100 ..... ... ..... 1010011 @r2_rm
193
+froundnx_s 0100000 00101 ..... ... ..... 1010011 @r2_rm
194
+fround_d 0100001 00100 ..... ... ..... 1010011 @r2_rm
195
+froundnx_d 0100001 00101 ..... ... ..... 1010011 @r2_rm
196
+fround_h 0100010 00100 ..... ... ..... 1010011 @r2_rm
197
+froundnx_h 0100010 00101 ..... ... ..... 1010011 @r2_rm
198
+fcvtmod_w_d 1100001 01000 ..... 001 ..... 1010011 @r2
199
+fmvh_x_d 1110001 00001 ..... 000 ..... 1010011 @r2
200
+fmvp_d_x 1011001 ..... ..... 000 ..... 1010011 @r
201
+fleq_s 1010000 ..... ..... 100 ..... 1010011 @r
202
+fltq_s 1010000 ..... ..... 101 ..... 1010011 @r
203
+fleq_d 1010001 ..... ..... 100 ..... 1010011 @r
204
+fltq_d 1010001 ..... ..... 101 ..... 1010011 @r
205
+fleq_h 1010010 ..... ..... 100 ..... 1010011 @r
206
+fltq_h 1010010 ..... ..... 101 ..... 1010011 @r
207
+
208
# *** RV32 Zfh Extension ***
209
flh ............ ..... 001 ..... 0000111 @i
210
fsh ....... ..... ..... 001 ..... 0100111 @s
211
diff --git a/disas/riscv.c b/disas/riscv.c
212
index XXXXXXX..XXXXXXX 100644
213
--- a/disas/riscv.c
214
+++ b/disas/riscv.c
215
@@ -XXX,XX +XXX,XX @@ typedef enum {
216
rv_op_fsh = 798,
217
rv_op_fmv_h_x = 799,
218
rv_op_fmv_x_h = 800,
219
+ rv_op_fli_s = 801,
220
+ rv_op_fli_d = 802,
221
+ rv_op_fli_q = 803,
222
+ rv_op_fli_h = 804,
223
+ rv_op_fminm_s = 805,
224
+ rv_op_fmaxm_s = 806,
225
+ rv_op_fminm_d = 807,
226
+ rv_op_fmaxm_d = 808,
227
+ rv_op_fminm_q = 809,
228
+ rv_op_fmaxm_q = 810,
229
+ rv_op_fminm_h = 811,
230
+ rv_op_fmaxm_h = 812,
231
+ rv_op_fround_s = 813,
232
+ rv_op_froundnx_s = 814,
233
+ rv_op_fround_d = 815,
234
+ rv_op_froundnx_d = 816,
235
+ rv_op_fround_q = 817,
236
+ rv_op_froundnx_q = 818,
237
+ rv_op_fround_h = 819,
238
+ rv_op_froundnx_h = 820,
239
+ rv_op_fcvtmod_w_d = 821,
240
+ rv_op_fmvh_x_d = 822,
241
+ rv_op_fmvp_d_x = 823,
242
+ rv_op_fmvh_x_q = 824,
243
+ rv_op_fmvp_q_x = 825,
244
+ rv_op_fleq_s = 826,
245
+ rv_op_fltq_s = 827,
246
+ rv_op_fleq_d = 828,
247
+ rv_op_fltq_d = 829,
248
+ rv_op_fleq_q = 830,
249
+ rv_op_fltq_q = 831,
250
+ rv_op_fleq_h = 832,
251
+ rv_op_fltq_h = 833,
252
} rv_op;
253
254
/* register names */
255
@@ -XXX,XX +XXX,XX @@ static const char rv_vreg_name_sym[32][4] = {
256
"v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31"
257
};
258
259
+/* The FLI.[HSDQ] numeric constants (0.0 for symbolic constants).
260
+ * The constants use the hex floating-point literal representation
261
+ * that is printed when using the printf %a format specifier,
262
+ * which matches the output that is generated by the disassembler.
263
+ */
264
+static const char rv_fli_name_const[32][9] =
265
+{
266
+ "0x1p+0", "min", "0x1p-16", "0x1p-15",
267
+ "0x1p-8", "0x1p-7", "0x1p-4", "0x1p-3",
268
+ "0x1p-2", "0x1.4p-2", "0x1.8p-2", "0x1.cp-2",
269
+ "0x1p-1", "0x1.4p-1", "0x1.8p-1", "0x1.cp-1",
270
+ "0x1p+0", "0x1.4p+0", "0x1.8p+0", "0x1.cp+0",
271
+ "0x1p+1", "0x1.4p+1", "0x1.8p+1", "0x1p+2",
272
+ "0x1p+3", "0x1p+4", "0x1p+7", "0x1p+8",
273
+ "0x1p+15", "0x1p+16", "inf", "nan"
274
+};
275
+
276
/* pseudo-instruction constraints */
277
278
static const rvc_constraint rvcc_jal[] = { rvc_rd_eq_ra, rvc_end };
279
@@ -XXX,XX +XXX,XX @@ const rv_opcode_data rvi_opcode_data[] = {
280
{ "fsh", rv_codec_s, rv_fmt_frs2_offset_rs1, NULL, 0, 0, 0 },
281
{ "fmv.h.x", rv_codec_r, rv_fmt_frd_rs1, NULL, 0, 0, 0 },
282
{ "fmv.x.h", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
283
+ { "fli.s", rv_codec_fli, rv_fmt_fli, NULL, 0, 0, 0 },
284
+ { "fli.d", rv_codec_fli, rv_fmt_fli, NULL, 0, 0, 0 },
285
+ { "fli.q", rv_codec_fli, rv_fmt_fli, NULL, 0, 0, 0 },
286
+ { "fli.h", rv_codec_fli, rv_fmt_fli, NULL, 0, 0, 0 },
287
+ { "fminm.s", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
288
+ { "fmaxm.s", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
289
+ { "fminm.d", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
290
+ { "fmaxm.d", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
291
+ { "fminm.q", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
292
+ { "fmaxm.q", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
293
+ { "fminm.h", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
294
+ { "fmaxm.h", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
295
+ { "fround.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
296
+ { "froundnx.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
297
+ { "fround.d", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
298
+ { "froundnx.d", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
299
+ { "fround.q", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
300
+ { "froundnx.q", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
301
+ { "fround.h", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
302
+ { "froundnx.h", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
303
+ { "fcvtmod.w.d", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
304
+ { "fmvh.x.d", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
305
+ { "fmvp.d.x", rv_codec_r, rv_fmt_frd_rs1_rs2, NULL, 0, 0, 0 },
306
+ { "fmvh.x.q", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
307
+ { "fmvp.q.x", rv_codec_r, rv_fmt_frd_rs1_rs2, NULL, 0, 0, 0 },
308
+ { "fleq.s", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
309
+ { "fltq.s", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
310
+ { "fleq.d", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
311
+ { "fltq.d", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
312
+ { "fleq.q", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
313
+ { "fltq.q", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
314
+ { "fleq.h", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
315
+ { "fltq.h", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
316
};
317
318
/* CSR names */
319
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
320
switch ((inst >> 12) & 0b111) {
321
case 0: op = rv_op_fmin_s; break;
322
case 1: op = rv_op_fmax_s; break;
323
+ case 2: op = rv_op_fminm_s; break;
324
+ case 3: op = rv_op_fmaxm_s; break;
325
}
326
break;
327
case 21:
328
switch ((inst >> 12) & 0b111) {
329
case 0: op = rv_op_fmin_d; break;
330
case 1: op = rv_op_fmax_d; break;
331
+ case 2: op = rv_op_fminm_d; break;
332
+ case 3: op = rv_op_fmaxm_d; break;
333
+ }
334
+ break;
335
+ case 22:
336
+ switch (((inst >> 12) & 0b111)) {
337
+ case 2: op = rv_op_fminm_h; break;
338
+ case 3: op = rv_op_fmaxm_h; break;
339
}
340
break;
341
case 23:
342
switch ((inst >> 12) & 0b111) {
343
case 0: op = rv_op_fmin_q; break;
344
case 1: op = rv_op_fmax_q; break;
345
+ case 2: op = rv_op_fminm_q; break;
346
+ case 3: op = rv_op_fmaxm_q; break;
347
}
348
break;
349
case 32:
350
switch ((inst >> 20) & 0b11111) {
351
case 1: op = rv_op_fcvt_s_d; break;
352
case 3: op = rv_op_fcvt_s_q; break;
353
+ case 4: op = rv_op_fround_s; break;
354
+ case 5: op = rv_op_froundnx_s; break;
355
case 6: op = rv_op_fcvt_s_bf16; break;
356
}
357
break;
358
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
359
switch ((inst >> 20) & 0b11111) {
360
case 0: op = rv_op_fcvt_d_s; break;
361
case 3: op = rv_op_fcvt_d_q; break;
362
+ case 4: op = rv_op_fround_d; break;
363
+ case 5: op = rv_op_froundnx_d; break;
364
}
365
break;
366
case 34:
367
switch (((inst >> 20) & 0b11111)) {
368
+ case 4: op = rv_op_fround_h; break;
369
+ case 5: op = rv_op_froundnx_h; break;
370
case 8: op = rv_op_fcvt_bf16_s; break;
371
}
372
break;
373
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
374
switch ((inst >> 20) & 0b11111) {
375
case 0: op = rv_op_fcvt_q_s; break;
376
case 1: op = rv_op_fcvt_q_d; break;
377
+ case 4: op = rv_op_fround_q; break;
378
+ case 5: op = rv_op_froundnx_q; break;
379
}
380
break;
381
case 44:
382
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
383
case 0: op = rv_op_fle_s; break;
384
case 1: op = rv_op_flt_s; break;
385
case 2: op = rv_op_feq_s; break;
386
+ case 4: op = rv_op_fleq_s; break;
387
+ case 5: op = rv_op_fltq_s; break;
388
}
389
break;
390
case 81:
391
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
392
case 0: op = rv_op_fle_d; break;
393
case 1: op = rv_op_flt_d; break;
394
case 2: op = rv_op_feq_d; break;
395
+ case 4: op = rv_op_fleq_d; break;
396
+ case 5: op = rv_op_fltq_d; break;
397
+ }
398
+ break;
399
+ case 82:
400
+ switch (((inst >> 12) & 0b111)) {
401
+ case 4: op = rv_op_fleq_h; break;
402
+ case 5: op = rv_op_fltq_h; break;
403
}
404
break;
405
case 83:
406
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
407
case 0: op = rv_op_fle_q; break;
408
case 1: op = rv_op_flt_q; break;
409
case 2: op = rv_op_feq_q; break;
410
+ case 4: op = rv_op_fleq_q; break;
411
+ case 5: op = rv_op_fltq_q; break;
412
+ }
413
+ break;
414
+ case 89:
415
+        switch (((inst >> 12) & 0b111)) {
416
+ case 0: op = rv_op_fmvp_d_x; break;
417
+ }
418
+ break;
419
+ case 91:
420
+        switch (((inst >> 12) & 0b111)) {
421
+ case 0: op = rv_op_fmvp_q_x; break;
422
}
423
break;
424
case 96:
425
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
426
case 1: op = rv_op_fcvt_wu_d; break;
427
case 2: op = rv_op_fcvt_l_d; break;
428
case 3: op = rv_op_fcvt_lu_d; break;
429
+ case 8: op = rv_op_fcvtmod_w_d; break;
430
}
431
break;
432
case 99:
433
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
434
((inst >> 12) & 0b00000111)) {
435
case 0: op = rv_op_fmv_x_d; break;
436
case 1: op = rv_op_fclass_d; break;
437
+ case 8: op = rv_op_fmvh_x_d; break;
438
}
439
break;
440
case 114:
441
@@ -XXX,XX +XXX,XX @@ static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
442
((inst >> 12) & 0b00000111)) {
443
case 0: op = rv_op_fmv_x_q; break;
444
case 1: op = rv_op_fclass_q; break;
445
+ case 8: op = rv_op_fmvh_x_q; break;
446
}
447
break;
448
case 120:
449
switch (((inst >> 17) & 0b11111000) |
450
((inst >> 12) & 0b00000111)) {
451
case 0: op = rv_op_fmv_s_x; break;
452
+ case 8: op = rv_op_fli_s; break;
453
}
454
break;
455
case 121:
456
switch (((inst >> 17) & 0b11111000) |
457
((inst >> 12) & 0b00000111)) {
458
case 0: op = rv_op_fmv_d_x; break;
459
+ case 8: op = rv_op_fli_d; break;
460
}
461
break;
462
case 122:
463
switch (((inst >> 17) & 0b11111000) |
464
((inst >> 12) & 0b00000111)) {
465
case 0: op = rv_op_fmv_h_x; break;
466
+ case 8: op = rv_op_fli_h; break;
467
}
468
break;
469
case 123:
470
switch (((inst >> 17) & 0b11111000) |
471
((inst >> 12) & 0b00000111)) {
472
case 0: op = rv_op_fmv_q_x; break;
473
+ case 8: op = rv_op_fli_q; break;
474
}
475
break;
476
}
477
@@ -XXX,XX +XXX,XX @@ static void decode_inst_operands(rv_decode *dec, rv_isa isa)
478
break;
479
case rv_codec_zcmt_jt:
480
dec->imm = operand_tbl_index(inst);
481
+    break;
482
+ case rv_codec_fli:
483
+ dec->rd = operand_rd(inst);
484
+ dec->imm = operand_rs1(inst);
485
break;
486
case rv_codec_r2_imm5:
487
dec->rd = operand_rd(inst);
488
@@ -XXX,XX +XXX,XX @@ static void format_inst(char *buf, size_t buflen, size_t tab, rv_decode *dec)
489
append(buf, tmp, buflen);
490
break;
491
}
492
+ case 'h':
493
+ append(buf, rv_fli_name_const[dec->imm], buflen);
494
+ break;
495
default:
496
break;
497
}
64
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
498
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
65
index XXXXXXX..XXXXXXX 100644
499
index XXXXXXX..XXXXXXX 100644
66
--- a/target/riscv/cpu.c
500
--- a/target/riscv/cpu.c
67
+++ b/target/riscv/cpu.c
501
+++ b/target/riscv/cpu.c
68
@@ -XXX,XX +XXX,XX @@ static void riscv_any_cpu_init(Object *obj)
502
@@ -XXX,XX +XXX,XX @@ static const struct isa_ext_data isa_edata_arr[] = {
69
CPURISCVState *env = &RISCV_CPU(obj)->env;
503
ISA_EXT_DATA_ENTRY(zifencei, PRIV_VERSION_1_10_0, ext_ifencei),
70
set_misa(env, RVXLEN | RVI | RVM | RVA | RVF | RVD | RVC | RVU);
504
ISA_EXT_DATA_ENTRY(zihintpause, PRIV_VERSION_1_10_0, ext_zihintpause),
71
set_priv_version(env, PRIV_VERSION_1_11_0);
505
ISA_EXT_DATA_ENTRY(zawrs, PRIV_VERSION_1_12_0, ext_zawrs),
72
- set_resetvec(env, DEFAULT_RSTVEC);
506
+ ISA_EXT_DATA_ENTRY(zfa, PRIV_VERSION_1_12_0, ext_zfa),
507
ISA_EXT_DATA_ENTRY(zfbfmin, PRIV_VERSION_1_12_0, ext_zfbfmin),
508
ISA_EXT_DATA_ENTRY(zfh, PRIV_VERSION_1_11_0, ext_zfh),
509
ISA_EXT_DATA_ENTRY(zfhmin, PRIV_VERSION_1_11_0, ext_zfhmin),
510
@@ -XXX,XX +XXX,XX @@ static void rv64_thead_c906_cpu_init(Object *obj)
511
set_misa(env, MXL_RV64, RVG | RVC | RVS | RVU);
512
env->priv_ver = PRIV_VERSION_1_11_0;
513
514
+ cpu->cfg.ext_zfa = true;
515
cpu->cfg.ext_zfh = true;
516
cpu->cfg.mmu = true;
517
cpu->cfg.ext_xtheadba = true;
518
@@ -XXX,XX +XXX,XX @@ void riscv_cpu_validate_set_extensions(RISCVCPU *cpu, Error **errp)
519
return;
520
}
521
522
+ if (cpu->cfg.ext_zfa && !riscv_has_ext(env, RVF)) {
523
+ error_setg(errp, "Zfa extension requires F extension");
524
+ return;
525
+ }
526
+
527
if (cpu->cfg.ext_zfh) {
528
cpu->cfg.ext_zfhmin = true;
529
}
530
@@ -XXX,XX +XXX,XX @@ static Property riscv_cpu_extensions[] = {
531
DEFINE_PROP_BOOL("Zicsr", RISCVCPU, cfg.ext_icsr, true),
532
DEFINE_PROP_BOOL("Zihintpause", RISCVCPU, cfg.ext_zihintpause, true),
533
DEFINE_PROP_BOOL("Zawrs", RISCVCPU, cfg.ext_zawrs, true),
534
+ DEFINE_PROP_BOOL("Zfa", RISCVCPU, cfg.ext_zfa, true),
535
DEFINE_PROP_BOOL("Zfh", RISCVCPU, cfg.ext_zfh, false),
536
DEFINE_PROP_BOOL("Zfhmin", RISCVCPU, cfg.ext_zfhmin, false),
537
DEFINE_PROP_BOOL("Zve32f", RISCVCPU, cfg.ext_zve32f, false),
538
diff --git a/target/riscv/fpu_helper.c b/target/riscv/fpu_helper.c
539
index XXXXXXX..XXXXXXX 100644
540
--- a/target/riscv/fpu_helper.c
541
+++ b/target/riscv/fpu_helper.c
542
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmin_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
543
float32_minimum_number(frs1, frs2, &env->fp_status));
73
}
544
}
74
545
75
static void riscv_base_cpu_init(Object *obj)
546
+uint64_t helper_fminm_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
76
@@ -XXX,XX +XXX,XX @@ static void riscv_base_cpu_init(Object *obj)
547
+{
77
CPURISCVState *env = &RISCV_CPU(obj)->env;
548
+ float32 frs1 = check_nanbox_s(env, rs1);
78
/* We set this in the realise function */
549
+ float32 frs2 = check_nanbox_s(env, rs2);
79
set_misa(env, 0);
550
+ float32 ret = float32_min(frs1, frs2, &env->fp_status);
80
- set_resetvec(env, DEFAULT_RSTVEC);
551
+ return nanbox_s(env, ret);
552
+}
553
+
554
uint64_t helper_fmax_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
555
{
556
float32 frs1 = check_nanbox_s(env, rs1);
557
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmax_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
558
float32_maximum_number(frs1, frs2, &env->fp_status));
81
}
559
}
82
560
83
static void rvxx_sifive_u_cpu_init(Object *obj)
561
+uint64_t helper_fmaxm_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
84
@@ -XXX,XX +XXX,XX @@ static void rvxx_sifive_u_cpu_init(Object *obj)
562
+{
85
CPURISCVState *env = &RISCV_CPU(obj)->env;
563
+ float32 frs1 = check_nanbox_s(env, rs1);
86
set_misa(env, RVXLEN | RVI | RVM | RVA | RVF | RVD | RVC | RVS | RVU);
564
+ float32 frs2 = check_nanbox_s(env, rs2);
87
set_priv_version(env, PRIV_VERSION_1_10_0);
565
+ float32 ret = float32_max(frs1, frs2, &env->fp_status);
88
- set_resetvec(env, 0x1004);
566
+ return nanbox_s(env, ret);
567
+}
568
+
569
uint64_t helper_fsqrt_s(CPURISCVState *env, uint64_t rs1)
570
{
571
float32 frs1 = check_nanbox_s(env, rs1);
572
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fle_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
573
return float32_le(frs1, frs2, &env->fp_status);
89
}
574
}
90
575
91
static void rvxx_sifive_e_cpu_init(Object *obj)
576
+target_ulong helper_fleq_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
92
@@ -XXX,XX +XXX,XX @@ static void rvxx_sifive_e_cpu_init(Object *obj)
577
+{
93
CPURISCVState *env = &RISCV_CPU(obj)->env;
578
+ float32 frs1 = check_nanbox_s(env, rs1);
94
set_misa(env, RVXLEN | RVI | RVM | RVA | RVC | RVU);
579
+ float32 frs2 = check_nanbox_s(env, rs2);
95
set_priv_version(env, PRIV_VERSION_1_10_0);
580
+ return float32_le_quiet(frs1, frs2, &env->fp_status);
96
- set_resetvec(env, 0x1004);
581
+}
97
qdev_prop_set_bit(DEVICE(obj), "mmu", false);
582
+
583
target_ulong helper_flt_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
584
{
585
float32 frs1 = check_nanbox_s(env, rs1);
586
@@ -XXX,XX +XXX,XX @@ target_ulong helper_flt_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
587
return float32_lt(frs1, frs2, &env->fp_status);
98
}
588
}
99
589
100
@@ -XXX,XX +XXX,XX @@ static void rv32_ibex_cpu_init(Object *obj)
590
+target_ulong helper_fltq_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
101
CPURISCVState *env = &RISCV_CPU(obj)->env;
591
+{
102
set_misa(env, RV32 | RVI | RVM | RVC | RVU);
592
+ float32 frs1 = check_nanbox_s(env, rs1);
103
set_priv_version(env, PRIV_VERSION_1_10_0);
593
+ float32 frs2 = check_nanbox_s(env, rs2);
104
- set_resetvec(env, 0x8090);
594
+ return float32_lt_quiet(frs1, frs2, &env->fp_status);
105
qdev_prop_set_bit(DEVICE(obj), "mmu", false);
595
+}
596
+
597
target_ulong helper_feq_s(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
598
{
599
float32 frs1 = check_nanbox_s(env, rs1);
600
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fclass_s(CPURISCVState *env, uint64_t rs1)
601
return fclass_s(frs1);
106
}
602
}
107
603
108
@@ -XXX,XX +XXX,XX @@ static void riscv_cpu_realize(DeviceState *dev, Error **errp)
604
+uint64_t helper_fround_s(CPURISCVState *env, uint64_t rs1)
109
set_feature(env, RISCV_FEATURE_PMP);
605
+{
110
}
606
+ float_status *fs = &env->fp_status;
111
607
+ uint16_t nx_old = get_float_exception_flags(fs) & float_flag_inexact;
112
+ set_resetvec(env, cpu->cfg.resetvec);
608
+ float32 frs1 = check_nanbox_s(env, rs1);
113
+
609
+
114
/* If misa isn't set (rv32 and rv64 machines) set it here */
610
+ frs1 = float32_round_to_int(frs1, fs);
115
if (!env->misa) {
611
+
116
/* Do some ISA extension error checking */
612
+ /* Restore the original NX flag. */
613
+ uint16_t flags = get_float_exception_flags(fs);
614
+ flags &= ~float_flag_inexact;
615
+ flags |= nx_old;
616
+ set_float_exception_flags(flags, fs);
617
+
618
+ return nanbox_s(env, frs1);
619
+}
620
+
621
+uint64_t helper_froundnx_s(CPURISCVState *env, uint64_t rs1)
622
+{
623
+ float32 frs1 = check_nanbox_s(env, rs1);
624
+ frs1 = float32_round_to_int(frs1, &env->fp_status);
625
+ return nanbox_s(env, frs1);
626
+}
627
+
628
uint64_t helper_fadd_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
629
{
630
return float64_add(frs1, frs2, &env->fp_status);
631
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmin_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
632
float64_minimum_number(frs1, frs2, &env->fp_status);
633
}
634
635
+uint64_t helper_fminm_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
636
+{
637
+ return float64_min(frs1, frs2, &env->fp_status);
638
+}
639
+
640
uint64_t helper_fmax_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
641
{
642
return env->priv_ver < PRIV_VERSION_1_11_0 ?
643
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmax_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
644
float64_maximum_number(frs1, frs2, &env->fp_status);
645
}
646
647
+uint64_t helper_fmaxm_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
648
+{
649
+ return float64_max(frs1, frs2, &env->fp_status);
650
+}
651
+
652
uint64_t helper_fcvt_s_d(CPURISCVState *env, uint64_t rs1)
653
{
654
return nanbox_s(env, float64_to_float32(rs1, &env->fp_status));
655
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fle_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
656
return float64_le(frs1, frs2, &env->fp_status);
657
}
658
659
+target_ulong helper_fleq_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
660
+{
661
+ return float64_le_quiet(frs1, frs2, &env->fp_status);
662
+}
663
+
664
target_ulong helper_flt_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
665
{
666
return float64_lt(frs1, frs2, &env->fp_status);
667
}
668
669
+target_ulong helper_fltq_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
670
+{
671
+ return float64_lt_quiet(frs1, frs2, &env->fp_status);
672
+}
673
+
674
target_ulong helper_feq_d(CPURISCVState *env, uint64_t frs1, uint64_t frs2)
675
{
676
return float64_eq_quiet(frs1, frs2, &env->fp_status);
677
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fcvt_w_d(CPURISCVState *env, uint64_t frs1)
678
return float64_to_int32(frs1, &env->fp_status);
679
}
680
681
+uint64_t helper_fcvtmod_w_d(CPURISCVState *env, uint64_t value)
682
+{
683
+ return float64_to_int32_modulo(value, float_round_to_zero, &env->fp_status);
684
+}
685
+
686
target_ulong helper_fcvt_wu_d(CPURISCVState *env, uint64_t frs1)
687
{
688
return (int32_t)float64_to_uint32(frs1, &env->fp_status);
689
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fclass_d(uint64_t frs1)
690
return fclass_d(frs1);
691
}
692
693
+uint64_t helper_fround_d(CPURISCVState *env, uint64_t frs1)
694
+{
695
+ float_status *fs = &env->fp_status;
696
+ uint16_t nx_old = get_float_exception_flags(fs) & float_flag_inexact;
697
+
698
+ frs1 = float64_round_to_int(frs1, fs);
699
+
700
+ /* Restore the original NX flag. */
701
+ uint16_t flags = get_float_exception_flags(fs);
702
+ flags &= ~float_flag_inexact;
703
+ flags |= nx_old;
704
+ set_float_exception_flags(flags, fs);
705
+
706
+ return frs1;
707
+}
708
+
709
+uint64_t helper_froundnx_d(CPURISCVState *env, uint64_t frs1)
710
+{
711
+ return float64_round_to_int(frs1, &env->fp_status);
712
+}
713
+
714
uint64_t helper_fadd_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
715
{
716
float16 frs1 = check_nanbox_h(env, rs1);
717
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmin_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
718
float16_minimum_number(frs1, frs2, &env->fp_status));
719
}
720
721
+uint64_t helper_fminm_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
722
+{
723
+ float16 frs1 = check_nanbox_h(env, rs1);
724
+ float16 frs2 = check_nanbox_h(env, rs2);
725
+ float16 ret = float16_min(frs1, frs2, &env->fp_status);
726
+ return nanbox_h(env, ret);
727
+}
728
+
729
uint64_t helper_fmax_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
730
{
731
float16 frs1 = check_nanbox_h(env, rs1);
732
@@ -XXX,XX +XXX,XX @@ uint64_t helper_fmax_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
733
float16_maximum_number(frs1, frs2, &env->fp_status));
734
}
735
736
+uint64_t helper_fmaxm_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
737
+{
738
+ float16 frs1 = check_nanbox_h(env, rs1);
739
+ float16 frs2 = check_nanbox_h(env, rs2);
740
+ float16 ret = float16_max(frs1, frs2, &env->fp_status);
741
+ return nanbox_h(env, ret);
742
+}
743
+
744
uint64_t helper_fsqrt_h(CPURISCVState *env, uint64_t rs1)
745
{
746
float16 frs1 = check_nanbox_h(env, rs1);
747
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fle_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
748
return float16_le(frs1, frs2, &env->fp_status);
749
}
750
751
+target_ulong helper_fleq_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
752
+{
753
+ float16 frs1 = check_nanbox_h(env, rs1);
754
+ float16 frs2 = check_nanbox_h(env, rs2);
755
+ return float16_le_quiet(frs1, frs2, &env->fp_status);
756
+}
757
+
758
target_ulong helper_flt_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
759
{
760
float16 frs1 = check_nanbox_h(env, rs1);
761
@@ -XXX,XX +XXX,XX @@ target_ulong helper_flt_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
762
return float16_lt(frs1, frs2, &env->fp_status);
763
}
764
765
+target_ulong helper_fltq_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
766
+{
767
+ float16 frs1 = check_nanbox_h(env, rs1);
768
+ float16 frs2 = check_nanbox_h(env, rs2);
769
+ return float16_lt_quiet(frs1, frs2, &env->fp_status);
770
+}
771
+
772
target_ulong helper_feq_h(CPURISCVState *env, uint64_t rs1, uint64_t rs2)
773
{
774
float16 frs1 = check_nanbox_h(env, rs1);
775
@@ -XXX,XX +XXX,XX @@ target_ulong helper_fclass_h(CPURISCVState *env, uint64_t rs1)
776
return fclass_h(frs1);
777
}
778
779
+uint64_t helper_fround_h(CPURISCVState *env, uint64_t rs1)
780
+{
781
+ float_status *fs = &env->fp_status;
782
+ uint16_t nx_old = get_float_exception_flags(fs) & float_flag_inexact;
783
+ float16 frs1 = check_nanbox_h(env, rs1);
784
+
785
+ frs1 = float16_round_to_int(frs1, fs);
786
+
787
+ /* Restore the original NX flag. */
788
+ uint16_t flags = get_float_exception_flags(fs);
789
+ flags &= ~float_flag_inexact;
790
+ flags |= nx_old;
791
+ set_float_exception_flags(flags, fs);
792
+
793
+ return nanbox_h(env, frs1);
794
+}
795
+
796
+uint64_t helper_froundnx_h(CPURISCVState *env, uint64_t rs1)
797
+{
798
+ float16 frs1 = check_nanbox_s(env, rs1);
799
+ frs1 = float16_round_to_int(frs1, &env->fp_status);
800
+ return nanbox_h(env, frs1);
801
+}
802
+
803
target_ulong helper_fcvt_w_h(CPURISCVState *env, uint64_t rs1)
804
{
805
float16 frs1 = check_nanbox_h(env, rs1);
806
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
807
index XXXXXXX..XXXXXXX 100644
808
--- a/target/riscv/translate.c
809
+++ b/target/riscv/translate.c
810
@@ -XXX,XX +XXX,XX @@ static uint32_t opcode_at(DisasContextBase *dcbase, target_ulong pc)
811
#include "insn_trans/trans_rvzicond.c.inc"
812
#include "insn_trans/trans_rvzawrs.c.inc"
813
#include "insn_trans/trans_rvzicbo.c.inc"
814
+#include "insn_trans/trans_rvzfa.c.inc"
815
#include "insn_trans/trans_rvzfh.c.inc"
816
#include "insn_trans/trans_rvk.c.inc"
817
#include "insn_trans/trans_privileged.c.inc"
818
diff --git a/tests/tcg/riscv64/test-fcvtmod.c b/tests/tcg/riscv64/test-fcvtmod.c
819
new file mode 100644
820
index XXXXXXX..XXXXXXX
821
--- /dev/null
822
+++ b/tests/tcg/riscv64/test-fcvtmod.c
823
@@ -XXX,XX +XXX,XX @@
824
+#include <stdio.h>
825
+#include <stddef.h>
826
+#include <stdint.h>
827
+
828
+#define FFLAG_NX_SHIFT 0 /* inexact */
829
+#define FFLAG_UF_SHIFT 1 /* underflow */
830
+#define FFLAG_OF_SHIFT 2 /* overflow */
831
+#define FFLAG_DZ_SHIFT 3 /* divide by zero */
832
+#define FFLAG_NV_SHIFT 4 /* invalid operation */
833
+
834
+#define FFLAG_NV (1UL << FFLAG_NV_SHIFT)
835
+#define FFLAG_DZ (1UL << FFLAG_DZ_SHIFT)
836
+#define FFLAG_OF (1UL << FFLAG_OF_SHIFT)
837
+#define FFLAG_UF (1UL << FFLAG_UF_SHIFT)
838
+#define FFLAG_NX (1UL << FFLAG_NX_SHIFT)
839
+
840
+typedef struct fp64_fcvt_fcvtmod_testcase {
841
+ const char* name;
842
+ union {
843
+ uint64_t inp_lu;
844
+ double inp_lf;
845
+ };
846
+ uint64_t exp_fcvt;
847
+ uint8_t exp_fcvt_fflags;
848
+ uint64_t exp_fcvtmod;
849
+ uint8_t exp_fcvtmod_fflags;
850
+} fp64_fcvt_fcvtmod_testcase_t;
851
+
852
+void print_fflags(uint8_t fflags)
853
+{
854
+ int set = 0;
855
+
856
+ if (fflags == 0) {
857
+ printf("-");
858
+ return;
859
+ }
860
+
861
+ if (fflags & FFLAG_NV) {
862
+ printf("%sFFLAG_NV", set ? " | " : "");
863
+ set = 1;
864
+ }
865
+ if (fflags & FFLAG_DZ) {
866
+ printf("%sFFLAG_DZ", set ? " | " : "");
867
+ set = 1;
868
+ }
869
+ if (fflags & FFLAG_OF) {
870
+ printf("%sFFLAG_OF", set ? " | " : "");
871
+ set = 1;
872
+ }
873
+ if (fflags & FFLAG_UF) {
874
+ printf("%sFFLAG_UF", set ? " | " : "");
875
+ set = 1;
876
+ }
877
+ if (fflags & FFLAG_NX) {
878
+ printf("%sFFLAG_NX", set ? " | " : "");
879
+ set = 1;
880
+ }
881
+}
882
+
883
+/* Clear all FP flags. */
884
+static inline void clear_fflags()
885
+{
886
+ __asm__ __volatile__("fsflags zero");
887
+}
888
+
889
+/* Read all FP flags. */
890
+static inline uint8_t get_fflags()
891
+{
892
+ uint64_t v;
893
+ __asm__ __volatile__("frflags %0" : "=r"(v));
894
+ return (uint8_t)v;
895
+}
896
+
897
+/* Move input value (without conversations) into an FP register. */
898
+static inline double do_fmv_d_x(uint64_t inp)
899
+{
900
+ double fpr;
901
+ __asm__ __volatile__("fmv.d.x %0, %1" : "=f"(fpr) : "r"(inp));
902
+ return fpr;
903
+}
904
+
905
+static inline uint64_t do_fcvt_w_d(uint64_t inp, uint8_t *fflags)
906
+{
907
+ uint64_t ret;
908
+ double fpr = do_fmv_d_x(inp);
909
+
910
+ clear_fflags();
911
+
912
+ __asm__ __volatile__("fcvt.w.d %0, %1, rtz" : "=r"(ret) : "f"(fpr));
913
+
914
+ *fflags = get_fflags();
915
+
916
+ return ret;
917
+}
918
+
919
+static inline uint64_t do_fcvtmod_w_d(uint64_t inp, uint8_t *fflags)
920
+{
921
+ uint64_t ret;
922
+ double fpr = do_fmv_d_x(inp);
923
+
924
+ clear_fflags();
925
+
926
+ /* fcvtmod.w.d rd, rs1, rtz = 1100001 01000 rs1 001 rd 1010011 */
927
+ asm(".insn r 0x53, 0x1, 0x61, %0, %1, f8" : "=r"(ret) : "f"(fpr));
928
+
929
+ *fflags = get_fflags();
930
+
931
+ return ret;
932
+}
933
+
934
+static const fp64_fcvt_fcvtmod_testcase_t tests[] = {
935
+ /* Zero (exp=0, frac=0) */
936
+ { .name = "+0.0",
937
+ .inp_lf = 0x0p0,
938
+ .exp_fcvt = 0x0000000000000000,
939
+ .exp_fcvt_fflags = 0,
940
+ .exp_fcvtmod = 0x0000000000000000,
941
+ .exp_fcvtmod_fflags = 0 },
942
+ { .name = "-0.0",
943
+ .inp_lf = -0x0p0,
944
+ .exp_fcvt = 0x0000000000000000,
945
+ .exp_fcvt_fflags = 0,
946
+ .exp_fcvtmod = 0x0000000000000000,
947
+ .exp_fcvtmod_fflags = 0 },
948
+
949
+ /* Subnormal: exp=0 frac!=0 */
950
+ { .name = "Subnormal frac=1",
951
+ .inp_lu = 0x0000000000000001,
952
+ .exp_fcvt = 0x0000000000000000,
953
+ .exp_fcvt_fflags = FFLAG_NX,
954
+ .exp_fcvtmod = 0,
955
+ .exp_fcvtmod_fflags = FFLAG_NX },
956
+ { .name = "Subnormal frac=0xf..f",
957
+ .inp_lu = 0x0000ffffffffffff,
958
+ .exp_fcvt = 0x0000000000000000,
959
+ .exp_fcvt_fflags = FFLAG_NX,
960
+ .exp_fcvtmod = 0,
961
+ .exp_fcvtmod_fflags = FFLAG_NX },
962
+ { .name = "Neg subnormal frac=1",
963
+ .inp_lu = 0x0000000000000001,
964
+ .exp_fcvt = 0x0000000000000000,
965
+ .exp_fcvt_fflags = FFLAG_NX,
966
+ .exp_fcvtmod = 0,
967
+ .exp_fcvtmod_fflags = FFLAG_NX },
968
+ { .name = "Neg subnormal frac=0xf..f",
969
+ .inp_lu = 0x8000ffffffffffff,
970
+ .exp_fcvt = 0x0000000000000000,
971
+ .exp_fcvt_fflags = FFLAG_NX,
972
+ .exp_fcvtmod = 0,
973
+ .exp_fcvtmod_fflags = FFLAG_NX },
974
+
975
+ /* Infinity: exp=0x7ff, frac=0 */
976
+ { .name = "+INF",
977
+ .inp_lu = 0x7ff0000000000000,
978
+ .exp_fcvt = 0x000000007fffffff, /* int32 max */
979
+ .exp_fcvt_fflags = FFLAG_NV,
980
+ .exp_fcvtmod = 0,
981
+ .exp_fcvtmod_fflags = FFLAG_NV },
982
+ { .name = "-INF",
983
+ .inp_lu = 0xfff0000000000000,
984
+ .exp_fcvt = 0xffffffff80000000, /* int32 min */
985
+ .exp_fcvt_fflags = FFLAG_NV,
986
+ .exp_fcvtmod = 0,
987
+ .exp_fcvtmod_fflags = FFLAG_NV },
988
+
989
+ /* NaN: exp=7ff, frac!=0 */
990
+ { .name = "canonical NaN",
991
+ .inp_lu = 0x7ff8000000000000,
992
+ .exp_fcvt = 0x000000007fffffff, /* int32 max */
993
+ .exp_fcvt_fflags = FFLAG_NV,
994
+ .exp_fcvtmod = 0,
995
+ .exp_fcvtmod_fflags = FFLAG_NV },
996
+ { .name = "non-canonical NaN",
997
+ .inp_lu = 0x7ff8000000100000,
998
+ .exp_fcvt = 0x000000007fffffff, /* int32 min */
999
+ .exp_fcvt_fflags = FFLAG_NV,
1000
+ .exp_fcvtmod = 0,
1001
+ .exp_fcvtmod_fflags = FFLAG_NV },
1002
+
1003
+ /* Normal numbers: exp!=0, exp!=7ff */
1004
+ { .name = "+smallest normal value",
1005
+ .inp_lu = 0x0010000000000000,
1006
+ .exp_fcvt = 0,
1007
+ .exp_fcvt_fflags = FFLAG_NX,
1008
+ .exp_fcvtmod = 0,
1009
+ .exp_fcvtmod_fflags = FFLAG_NX },
1010
+ { .name = "-smallest normal value",
1011
+ .inp_lu = 0x8010000000000000,
1012
+ .exp_fcvt = 0,
1013
+ .exp_fcvt_fflags = FFLAG_NX,
1014
+ .exp_fcvtmod = 0,
1015
+ .exp_fcvtmod_fflags = FFLAG_NX },
1016
+
1017
+ { .name = "+0.5",
1018
+ .inp_lf = 0x1p-1,
1019
+ .exp_fcvt = 0,
1020
+ .exp_fcvt_fflags = FFLAG_NX,
1021
+ .exp_fcvtmod = 0,
1022
+ .exp_fcvtmod_fflags = FFLAG_NX },
1023
+ { .name = "-0.5",
1024
+ .inp_lf = -0x1p-1,
1025
+ .exp_fcvt = 0,
1026
+ .exp_fcvt_fflags = FFLAG_NX,
1027
+ .exp_fcvtmod = 0,
1028
+ .exp_fcvtmod_fflags = FFLAG_NX },
1029
+
1030
+ { .name = "+value just below 1.0",
1031
+ .inp_lu = 0x3fefffffffffffff,
1032
+ .exp_fcvt = 0,
1033
+ .exp_fcvt_fflags = FFLAG_NX,
1034
+ .exp_fcvtmod = 0,
1035
+ .exp_fcvtmod_fflags = FFLAG_NX },
1036
+ { .name = "-value just above -1.0",
1037
+ .inp_lu = 0xbfefffffffffffff,
1038
+ .exp_fcvt = 0,
1039
+ .exp_fcvt_fflags = FFLAG_NX,
1040
+ .exp_fcvtmod = 0,
1041
+ .exp_fcvtmod_fflags = FFLAG_NX },
1042
+
1043
+ { .name = "+1.0",
1044
+ .inp_lf = 0x1p0,
1045
+ .exp_fcvt = 0x0000000000000001,
1046
+ .exp_fcvt_fflags = 0,
1047
+ .exp_fcvtmod = 0x0000000000000001,
1048
+ .exp_fcvtmod_fflags = 0 },
1049
+ { .name = "-1.0",
1050
+ .inp_lf = -0x1p0,
1051
+ .exp_fcvt = 0xffffffffffffffff,
1052
+ .exp_fcvt_fflags = 0,
1053
+ .exp_fcvtmod = 0xffffffffffffffff,
1054
+ .exp_fcvtmod_fflags = 0 },
1055
+
1056
+ { .name = "+1.5",
1057
+ .inp_lu = 0x3ff8000000000000,
1058
+ .exp_fcvt = 1,
1059
+ .exp_fcvt_fflags = FFLAG_NX,
1060
+ .exp_fcvtmod = 1,
1061
+ .exp_fcvtmod_fflags = FFLAG_NX },
1062
+ { .name = "-1.5",
1063
+ .inp_lu = 0xbff8000000000000,
1064
+ .exp_fcvt = 0xffffffffffffffff,
1065
+ .exp_fcvt_fflags = FFLAG_NX,
1066
+ .exp_fcvtmod = 0xffffffffffffffff,
1067
+ .exp_fcvtmod_fflags = FFLAG_NX },
1068
+
1069
+ { .name = "+max int32 (2147483647)",
1070
+ .inp_lu = 0x41dfffffffc00000,
1071
+ .exp_fcvt = 0x000000007fffffff,
1072
+ .exp_fcvt_fflags = 0,
1073
+ .exp_fcvtmod = 0x000000007fffffff,
1074
+ .exp_fcvtmod_fflags = 0 },
1075
+ { .name = "+max int32 +1 (2147483648)",
1076
+ .inp_lf = 0x1p31,
1077
+ .exp_fcvt = 0x000000007fffffff,
1078
+ .exp_fcvt_fflags = FFLAG_NV,
1079
+ .exp_fcvtmod = (uint64_t)-2147483648l, /* int32 min */
1080
+ .exp_fcvtmod_fflags = FFLAG_NV },
1081
+ { .name = "+max int32 +2 (2147483649)",
1082
+ .inp_lu = 0x41e0000000200000,
1083
+ .exp_fcvt = 0x000000007fffffff,
1084
+ .exp_fcvt_fflags = FFLAG_NV,
1085
+ .exp_fcvtmod = (uint64_t)-2147483647l, /* int32 min +1 */
1086
+ .exp_fcvtmod_fflags = FFLAG_NV },
1087
+
1088
+ { .name = "-max int32 (-2147483648)",
1089
+ .inp_lf = -0x1p31,
1090
+ .exp_fcvt = 0xffffffff80000000,
1091
+ .exp_fcvt_fflags = 0,
1092
+ .exp_fcvtmod = 0xffffffff80000000,
1093
+ .exp_fcvtmod_fflags = 0 },
1094
+ { .name = "-max int32 -1 (-2147483649)",
1095
+ .inp_lf = -0x1.00000002p+31,
1096
+ .exp_fcvt = 0xffffffff80000000,
1097
+ .exp_fcvt_fflags = FFLAG_NV,
1098
+ .exp_fcvtmod = 2147483647, /* int32 max */
1099
+ .exp_fcvtmod_fflags = FFLAG_NV },
1100
+ { .name = "-max int32 -2 (-2147483650)",
1101
+ .inp_lf = -0x1.00000004p+31,
1102
+ .exp_fcvt = 0xffffffff80000000,
1103
+ .exp_fcvt_fflags = FFLAG_NV,
1104
+ .exp_fcvtmod = 2147483646, /* int32 max -1 */
1105
+ .exp_fcvtmod_fflags = FFLAG_NV },
1106
+};
1107
+
1108
+int run_fcvtmod_tests()
1109
+{
1110
+ uint64_t act_fcvt;
1111
+ uint8_t act_fcvt_fflags;
1112
+ uint64_t act_fcvtmod;
1113
+ uint8_t act_fcvtmod_fflags;
1114
+
1115
+ for (size_t i = 0; i < sizeof(tests)/sizeof(tests[0]); i++) {
1116
+ const fp64_fcvt_fcvtmod_testcase_t *t = &tests[i];
1117
+
1118
+ act_fcvt = do_fcvt_w_d(t->inp_lu, &act_fcvt_fflags);
1119
+ int fcvt_correct = act_fcvt == t->exp_fcvt &&
1120
+ act_fcvt_fflags == t->exp_fcvt_fflags;
1121
+ act_fcvtmod = do_fcvtmod_w_d(t->inp_lu, &act_fcvtmod_fflags);
1122
+ int fcvtmod_correct = act_fcvtmod == t->exp_fcvtmod &&
1123
+ act_fcvtmod_fflags == t->exp_fcvtmod_fflags;
1124
+
1125
+ if (fcvt_correct && fcvtmod_correct) {
1126
+ continue;
1127
+ }
1128
+
1129
+ printf("Test %zu (%s) failed!\n", i, t->name);
1130
+
1131
+ double fpr = do_fmv_d_x(t->inp_lu);
1132
+ printf("inp_lu: 0x%016lx == %lf\n", t->inp_lu, fpr);
1133
+ printf("inp_lf: %lf\n", t->inp_lf);
1134
+
1135
+ uint32_t sign = (t->inp_lu >> 63);
1136
+ uint32_t exp = (uint32_t)(t->inp_lu >> 52) & 0x7ff;
1137
+ uint64_t frac = t->inp_lu & 0xfffffffffffffull; /* significand */
1138
+ int true_exp = exp - 1023;
1139
+ int shift = true_exp - 52;
1140
+ uint64_t true_frac = frac | 1ull << 52;
1141
+
1142
+ printf("sign=%d, exp=0x%03x, frac=0x%012lx\n", sign, exp, frac);
1143
+ printf("true_exp=%d, shift=%d, true_frac=0x%016lx\n", true_exp, shift, true_frac);
1144
+
1145
+ if (!fcvt_correct) {
1146
+ printf("act_fcvt: 0x%016lx == %li\n", act_fcvt, act_fcvt);
1147
+ printf("exp_fcvt: 0x%016lx == %li\n", t->exp_fcvt, t->exp_fcvt);
1148
+ printf("act_fcvt_fflags: "); print_fflags(act_fcvt_fflags); printf("\n");
1149
+ printf("exp_fcvt_fflags: "); print_fflags(t->exp_fcvt_fflags); printf("\n");
1150
+ }
1151
+
1152
+ if (!fcvtmod_correct) {
1153
+ printf("act_fcvtmod: 0x%016lx == %li\n", act_fcvtmod, act_fcvtmod);
1154
+ printf("exp_fcvtmod: 0x%016lx == %li\n", t->exp_fcvtmod, t->exp_fcvtmod);
1155
+ printf("act_fcvtmod_fflags: "); print_fflags(act_fcvtmod_fflags); printf("\n");
1156
+ printf("exp_fcvtmod_fflags: "); print_fflags(t->exp_fcvtmod_fflags); printf("\n");
1157
+ }
1158
+
1159
+ return 1;
1160
+ }
1161
+
1162
+ return 0;
1163
+}
1164
+
1165
+int main()
1166
+{
1167
+ return run_fcvtmod_tests();
1168
+}
1169
diff --git a/target/riscv/insn_trans/trans_rvzfa.c.inc b/target/riscv/insn_trans/trans_rvzfa.c.inc
1170
new file mode 100644
1171
index XXXXXXX..XXXXXXX
1172
--- /dev/null
1173
+++ b/target/riscv/insn_trans/trans_rvzfa.c.inc
1174
@@ -XXX,XX +XXX,XX @@
1175
+/*
1176
+ * RISC-V translation routines for the Zfa Standard Extension.
1177
+ *
1178
+ * Copyright (c) 2023 Christoph Müllner, christoph.muellner@vrull.eu
1179
+ *
1180
+ * This program is free software; you can redistribute it and/or modify it
1181
+ * under the terms and conditions of the GNU General Public License,
1182
+ * version 2 or later, as published by the Free Software Foundation.
1183
+ *
1184
+ * This program is distributed in the hope it will be useful, but WITHOUT
1185
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1186
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
1187
+ * more details.
1188
+ *
1189
+ * You should have received a copy of the GNU General Public License along with
1190
+ * this program. If not, see <http://www.gnu.org/licenses/>.
1191
+ */
1192
+
1193
+#define REQUIRE_ZFA(ctx) do { \
1194
+ if (!ctx->cfg_ptr->ext_zfa) { \
1195
+ return false; \
1196
+ } \
1197
+} while (0)
1198
+
1199
+#define REQUIRE_ZFH(ctx) do { \
1200
+ if (!ctx->cfg_ptr->ext_zfh) { \
1201
+ return false; \
1202
+ } \
1203
+} while (0)
1204
+
1205
+static bool trans_fli_s(DisasContext *ctx, arg_fli_s *a)
1206
+{
1207
+ REQUIRE_FPU;
1208
+ REQUIRE_ZFA(ctx);
1209
+ REQUIRE_EXT(ctx, RVF);
1210
+
1211
+ /* Values below are NaN-boxed to avoid a gen_nanbox_s(). */
1212
+ static const uint64_t fli_s_table[] = {
1213
+ 0xffffffffbf800000, /* -1.0 */
1214
+ 0xffffffff00800000, /* minimum positive normal */
1215
+ 0xffffffff37800000, /* 1.0 * 2^-16 */
1216
+ 0xffffffff38000000, /* 1.0 * 2^-15 */
1217
+ 0xffffffff3b800000, /* 1.0 * 2^-8 */
1218
+ 0xffffffff3c000000, /* 1.0 * 2^-7 */
1219
+ 0xffffffff3d800000, /* 1.0 * 2^-4 */
1220
+ 0xffffffff3e000000, /* 1.0 * 2^-3 */
1221
+ 0xffffffff3e800000, /* 0.25 */
1222
+ 0xffffffff3ea00000, /* 0.3125 */
1223
+ 0xffffffff3ec00000, /* 0.375 */
1224
+ 0xffffffff3ee00000, /* 0.4375 */
1225
+ 0xffffffff3f000000, /* 0.5 */
1226
+ 0xffffffff3f200000, /* 0.625 */
1227
+ 0xffffffff3f400000, /* 0.75 */
1228
+ 0xffffffff3f600000, /* 0.875 */
1229
+ 0xffffffff3f800000, /* 1.0 */
1230
+ 0xffffffff3fa00000, /* 1.25 */
1231
+ 0xffffffff3fc00000, /* 1.5 */
1232
+ 0xffffffff3fe00000, /* 1.75 */
1233
+ 0xffffffff40000000, /* 2.0 */
1234
+ 0xffffffff40200000, /* 2.5 */
1235
+ 0xffffffff40400000, /* 3 */
1236
+ 0xffffffff40800000, /* 4 */
1237
+ 0xffffffff41000000, /* 8 */
1238
+ 0xffffffff41800000, /* 16 */
1239
+ 0xffffffff43000000, /* 2^7 */
1240
+ 0xffffffff43800000, /* 2^8 */
1241
+ 0xffffffff47000000, /* 2^15 */
1242
+ 0xffffffff47800000, /* 2^16 */
1243
+ 0xffffffff7f800000, /* +inf */
1244
+ 0xffffffff7fc00000, /* Canonical NaN */
1245
+ };
1246
+
1247
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1248
+ tcg_gen_movi_i64(dest, fli_s_table[a->rs1]);
1249
+ gen_set_fpr_hs(ctx, a->rd, dest);
1250
+
1251
+ mark_fs_dirty(ctx);
1252
+ return true;
1253
+}
1254
+
1255
+static bool trans_fli_d(DisasContext *ctx, arg_fli_d *a)
1256
+{
1257
+ REQUIRE_FPU;
1258
+ REQUIRE_ZFA(ctx);
1259
+ REQUIRE_EXT(ctx, RVD);
1260
+
1261
+ static const uint64_t fli_d_table[] = {
1262
+ 0xbff0000000000000, /* -1.0 */
1263
+ 0x0010000000000000, /* minimum positive normal */
1264
+ 0x3ef0000000000000, /* 1.0 * 2^-16 */
1265
+ 0x3f00000000000000, /* 1.0 * 2^-15 */
1266
+ 0x3f70000000000000, /* 1.0 * 2^-8 */
1267
+ 0x3f80000000000000, /* 1.0 * 2^-7 */
1268
+ 0x3fb0000000000000, /* 1.0 * 2^-4 */
1269
+ 0x3fc0000000000000, /* 1.0 * 2^-3 */
1270
+ 0x3fd0000000000000, /* 0.25 */
1271
+ 0x3fd4000000000000, /* 0.3125 */
1272
+ 0x3fd8000000000000, /* 0.375 */
1273
+ 0x3fdc000000000000, /* 0.4375 */
1274
+ 0x3fe0000000000000, /* 0.5 */
1275
+ 0x3fe4000000000000, /* 0.625 */
1276
+ 0x3fe8000000000000, /* 0.75 */
1277
+ 0x3fec000000000000, /* 0.875 */
1278
+ 0x3ff0000000000000, /* 1.0 */
1279
+ 0x3ff4000000000000, /* 1.25 */
1280
+ 0x3ff8000000000000, /* 1.5 */
1281
+ 0x3ffc000000000000, /* 1.75 */
1282
+ 0x4000000000000000, /* 2.0 */
1283
+ 0x4004000000000000, /* 2.5 */
1284
+ 0x4008000000000000, /* 3 */
1285
+ 0x4010000000000000, /* 4 */
1286
+ 0x4020000000000000, /* 8 */
1287
+ 0x4030000000000000, /* 16 */
1288
+ 0x4060000000000000, /* 2^7 */
1289
+ 0x4070000000000000, /* 2^8 */
1290
+ 0x40e0000000000000, /* 2^15 */
1291
+ 0x40f0000000000000, /* 2^16 */
1292
+ 0x7ff0000000000000, /* +inf */
1293
+ 0x7ff8000000000000, /* Canonical NaN */
1294
+ };
1295
+
1296
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1297
+ tcg_gen_movi_i64(dest, fli_d_table[a->rs1]);
1298
+ gen_set_fpr_d(ctx, a->rd, dest);
1299
+
1300
+ mark_fs_dirty(ctx);
1301
+ return true;
1302
+}
1303
+
1304
+static bool trans_fli_h(DisasContext *ctx, arg_fli_h *a)
1305
+{
1306
+ REQUIRE_FPU;
1307
+ REQUIRE_ZFA(ctx);
1308
+ REQUIRE_ZFH(ctx);
1309
+
1310
+ /* Values below are NaN-boxed to avoid a gen_nanbox_h(). */
1311
+ static const uint64_t fli_h_table[] = {
1312
+ 0xffffffffffffbc00, /* -1.0 */
1313
+ 0xffffffffffff0400, /* minimum positive normal */
1314
+ 0xffffffffffff0100, /* 1.0 * 2^-16 */
1315
+ 0xffffffffffff0200, /* 1.0 * 2^-15 */
1316
+ 0xffffffffffff1c00, /* 1.0 * 2^-8 */
1317
+ 0xffffffffffff2000, /* 1.0 * 2^-7 */
1318
+ 0xffffffffffff2c00, /* 1.0 * 2^-4 */
1319
+ 0xffffffffffff3000, /* 1.0 * 2^-3 */
1320
+ 0xffffffffffff3400, /* 0.25 */
1321
+ 0xffffffffffff3500, /* 0.3125 */
1322
+ 0xffffffffffff3600, /* 0.375 */
1323
+ 0xffffffffffff3700, /* 0.4375 */
1324
+ 0xffffffffffff3800, /* 0.5 */
1325
+ 0xffffffffffff3900, /* 0.625 */
1326
+ 0xffffffffffff3a00, /* 0.75 */
1327
+ 0xffffffffffff3b00, /* 0.875 */
1328
+ 0xffffffffffff3c00, /* 1.0 */
1329
+ 0xffffffffffff3d00, /* 1.25 */
1330
+ 0xffffffffffff3e00, /* 1.5 */
1331
+ 0xffffffffffff3f00, /* 1.75 */
1332
+ 0xffffffffffff4000, /* 2.0 */
1333
+ 0xffffffffffff4100, /* 2.5 */
1334
+ 0xffffffffffff4200, /* 3 */
1335
+ 0xffffffffffff4400, /* 4 */
1336
+ 0xffffffffffff4800, /* 8 */
1337
+ 0xffffffffffff4c00, /* 16 */
1338
+ 0xffffffffffff5800, /* 2^7 */
1339
+ 0xffffffffffff5c00, /* 2^8 */
1340
+ 0xffffffffffff7800, /* 2^15 */
1341
+ 0xffffffffffff7c00, /* 2^16 */
1342
+ 0xffffffffffff7c00, /* +inf */
1343
+ 0xffffffffffff7e00, /* Canonical NaN */
1344
+ };
1345
+
1346
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1347
+ tcg_gen_movi_i64(dest, fli_h_table[a->rs1]);
1348
+ gen_set_fpr_hs(ctx, a->rd, dest);
1349
+
1350
+ mark_fs_dirty(ctx);
1351
+ return true;
1352
+}
1353
+
1354
+static bool trans_fminm_s(DisasContext *ctx, arg_fminm_s *a)
1355
+{
1356
+ REQUIRE_FPU;
1357
+ REQUIRE_ZFA(ctx);
1358
+ REQUIRE_EXT(ctx, RVF);
1359
+
1360
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1361
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1362
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1363
+
1364
+ gen_helper_fminm_s(dest, cpu_env, src1, src2);
1365
+ gen_set_fpr_hs(ctx, a->rd, dest);
1366
+
1367
+ mark_fs_dirty(ctx);
1368
+ return true;
1369
+}
1370
+
1371
+static bool trans_fmaxm_s(DisasContext *ctx, arg_fmaxm_s *a)
1372
+{
1373
+ REQUIRE_FPU;
1374
+ REQUIRE_ZFA(ctx);
1375
+ REQUIRE_EXT(ctx, RVF);
1376
+
1377
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1378
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1379
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1380
+
1381
+ gen_helper_fmaxm_s(dest, cpu_env, src1, src2);
1382
+ gen_set_fpr_hs(ctx, a->rd, dest);
1383
+
1384
+ mark_fs_dirty(ctx);
1385
+ return true;
1386
+}
1387
+
1388
+static bool trans_fminm_d(DisasContext *ctx, arg_fminm_d *a)
1389
+{
1390
+ REQUIRE_FPU;
1391
+ REQUIRE_ZFA(ctx);
1392
+ REQUIRE_EXT(ctx, RVD);
1393
+
1394
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1395
+ TCGv_i64 src1 = get_fpr_d(ctx, a->rs1);
1396
+ TCGv_i64 src2 = get_fpr_d(ctx, a->rs2);
1397
+
1398
+ gen_helper_fminm_d(dest, cpu_env, src1, src2);
1399
+ gen_set_fpr_d(ctx, a->rd, dest);
1400
+
1401
+ mark_fs_dirty(ctx);
1402
+ return true;
1403
+}
1404
+
1405
+static bool trans_fmaxm_d(DisasContext *ctx, arg_fmaxm_d *a)
1406
+{
1407
+ REQUIRE_FPU;
1408
+ REQUIRE_ZFA(ctx);
1409
+ REQUIRE_EXT(ctx, RVD);
1410
+
1411
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1412
+ TCGv_i64 src1 = get_fpr_d(ctx, a->rs1);
1413
+ TCGv_i64 src2 = get_fpr_d(ctx, a->rs2);
1414
+
1415
+ gen_helper_fmaxm_d(dest, cpu_env, src1, src2);
1416
+ gen_set_fpr_d(ctx, a->rd, dest);
1417
+
1418
+ mark_fs_dirty(ctx);
1419
+ return true;
1420
+}
1421
+
1422
+static bool trans_fminm_h(DisasContext *ctx, arg_fminm_h *a)
1423
+{
1424
+ REQUIRE_FPU;
1425
+ REQUIRE_ZFA(ctx);
1426
+ REQUIRE_ZFH(ctx);
1427
+
1428
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1429
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1430
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1431
+
1432
+ gen_helper_fminm_h(dest, cpu_env, src1, src2);
1433
+ gen_set_fpr_hs(ctx, a->rd, dest);
1434
+
1435
+ mark_fs_dirty(ctx);
1436
+ return true;
1437
+}
1438
+
1439
+static bool trans_fmaxm_h(DisasContext *ctx, arg_fmaxm_h *a)
1440
+{
1441
+ REQUIRE_FPU;
1442
+ REQUIRE_ZFA(ctx);
1443
+ REQUIRE_ZFH(ctx);
1444
+
1445
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1446
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1447
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1448
+
1449
+ gen_helper_fmaxm_h(dest, cpu_env, src1, src2);
1450
+ gen_set_fpr_hs(ctx, a->rd, dest);
1451
+
1452
+ mark_fs_dirty(ctx);
1453
+ return true;
1454
+}
1455
+
1456
+static bool trans_fround_s(DisasContext *ctx, arg_fround_s *a)
1457
+{
1458
+ REQUIRE_FPU;
1459
+ REQUIRE_ZFA(ctx);
1460
+ REQUIRE_EXT(ctx, RVF);
1461
+
1462
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1463
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1464
+
1465
+ gen_set_rm(ctx, a->rm);
1466
+ gen_helper_fround_s(dest, cpu_env, src1);
1467
+ gen_set_fpr_hs(ctx, a->rd, dest);
1468
+
1469
+ mark_fs_dirty(ctx);
1470
+ return true;
1471
+}
1472
+
1473
+static bool trans_froundnx_s(DisasContext *ctx, arg_froundnx_s *a)
1474
+{
1475
+ REQUIRE_FPU;
1476
+ REQUIRE_ZFA(ctx);
1477
+ REQUIRE_EXT(ctx, RVF);
1478
+
1479
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1480
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1481
+
1482
+ gen_set_rm(ctx, a->rm);
1483
+ gen_helper_froundnx_s(dest, cpu_env, src1);
1484
+ gen_set_fpr_hs(ctx, a->rd, dest);
1485
+
1486
+ mark_fs_dirty(ctx);
1487
+ return true;
1488
+}
1489
+
1490
+static bool trans_fround_d(DisasContext *ctx, arg_fround_d *a)
1491
+{
1492
+ REQUIRE_FPU;
1493
+ REQUIRE_ZFA(ctx);
1494
+ REQUIRE_EXT(ctx, RVD);
1495
+
1496
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1497
+ TCGv_i64 src1 = get_fpr_d(ctx, a->rs1);
1498
+
1499
+ gen_set_rm(ctx, a->rm);
1500
+ gen_helper_fround_d(dest, cpu_env, src1);
1501
+ gen_set_fpr_hs(ctx, a->rd, dest);
1502
+
1503
+ mark_fs_dirty(ctx);
1504
+ return true;
1505
+}
1506
+
1507
+static bool trans_froundnx_d(DisasContext *ctx, arg_froundnx_d *a)
1508
+{
1509
+ REQUIRE_FPU;
1510
+ REQUIRE_ZFA(ctx);
1511
+ REQUIRE_EXT(ctx, RVD);
1512
+
1513
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1514
+ TCGv_i64 src1 = get_fpr_d(ctx, a->rs1);
1515
+
1516
+ gen_set_rm(ctx, a->rm);
1517
+ gen_helper_froundnx_d(dest, cpu_env, src1);
1518
+ gen_set_fpr_hs(ctx, a->rd, dest);
1519
+
1520
+ mark_fs_dirty(ctx);
1521
+ return true;
1522
+}
1523
+
1524
+static bool trans_fround_h(DisasContext *ctx, arg_fround_h *a)
1525
+{
1526
+ REQUIRE_FPU;
1527
+ REQUIRE_ZFA(ctx);
1528
+ REQUIRE_ZFH(ctx);
1529
+
1530
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1531
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1532
+
1533
+ gen_set_rm(ctx, a->rm);
1534
+ gen_helper_fround_h(dest, cpu_env, src1);
1535
+ gen_set_fpr_hs(ctx, a->rd, dest);
1536
+
1537
+ mark_fs_dirty(ctx);
1538
+ return true;
1539
+}
1540
+
1541
+static bool trans_froundnx_h(DisasContext *ctx, arg_froundnx_h *a)
1542
+{
1543
+ REQUIRE_FPU;
1544
+ REQUIRE_ZFA(ctx);
1545
+ REQUIRE_ZFH(ctx);
1546
+
1547
+ TCGv_i64 dest = dest_fpr(ctx, a->rd);
1548
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1549
+
1550
+ gen_set_rm(ctx, a->rm);
1551
+ gen_helper_froundnx_h(dest, cpu_env, src1);
1552
+ gen_set_fpr_hs(ctx, a->rd, dest);
1553
+
1554
+ mark_fs_dirty(ctx);
1555
+ return true;
1556
+}
1557
+
1558
+bool trans_fcvtmod_w_d(DisasContext *ctx, arg_fcvtmod_w_d *a)
1559
+{
1560
+ REQUIRE_FPU;
1561
+ REQUIRE_ZFA(ctx);
1562
+ REQUIRE_EXT(ctx, RVD);
1563
+
1564
+ TCGv dst = dest_gpr(ctx, a->rd);
1565
+ TCGv_i64 src1 = get_fpr_d(ctx, a->rs1);
1566
+ TCGv_i64 t1 = tcg_temp_new_i64();
1567
+
1568
+ /* Rounding mode is RTZ. */
1569
+ gen_set_rm(ctx, RISCV_FRM_RTZ);
1570
+ gen_helper_fcvtmod_w_d(t1, cpu_env, src1);
1571
+ tcg_gen_trunc_i64_tl(dst, t1);
1572
+ gen_set_gpr(ctx, a->rd, dst);
1573
+
1574
+ return true;
1575
+}
1576
+
1577
+bool trans_fmvh_x_d(DisasContext *ctx, arg_fmvh_x_d *a)
1578
+{
1579
+ REQUIRE_FPU;
1580
+ REQUIRE_ZFA(ctx);
1581
+ REQUIRE_EXT(ctx, RVD);
1582
+ REQUIRE_32BIT(ctx);
1583
+
1584
+ TCGv dst = dest_gpr(ctx, a->rd);
1585
+ TCGv_i64 t1 = tcg_temp_new_i64();
1586
+ tcg_gen_sari_i64(t1, cpu_fpr[a->rs1], 32);
1587
+ tcg_gen_trunc_i64_tl(dst, t1);
1588
+ gen_set_gpr(ctx, a->rd, dst);
1589
+ return true;
1590
+}
1591
+
1592
+bool trans_fmvp_d_x(DisasContext *ctx, arg_fmvp_d_x *a)
1593
+{
1594
+ REQUIRE_FPU;
1595
+ REQUIRE_ZFA(ctx);
1596
+ REQUIRE_EXT(ctx, RVD);
1597
+ REQUIRE_32BIT(ctx);
1598
+
1599
+ TCGv src1 = get_gpr(ctx, a->rs1, EXT_NONE);
1600
+ TCGv src2 = get_gpr(ctx, a->rs2, EXT_NONE);
1601
+ tcg_gen_concat_tl_i64(cpu_fpr[a->rd], src1, src2);
1602
+
1603
+ mark_fs_dirty(ctx);
1604
+ return true;
1605
+}
1606
+
1607
+bool trans_fleq_s(DisasContext *ctx, arg_fleq_s *a)
1608
+{
1609
+ REQUIRE_FPU;
1610
+ REQUIRE_ZFA(ctx);
1611
+ REQUIRE_EXT(ctx, RVF);
1612
+
1613
+ TCGv dest = dest_gpr(ctx, a->rd);
1614
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1615
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1616
+
1617
+ gen_helper_fleq_s(dest, cpu_env, src1, src2);
1618
+ gen_set_gpr(ctx, a->rd, dest);
1619
+ return true;
1620
+}
1621
+
1622
+bool trans_fltq_s(DisasContext *ctx, arg_fltq_s *a)
1623
+{
1624
+ REQUIRE_FPU;
1625
+ REQUIRE_ZFA(ctx);
1626
+ REQUIRE_EXT(ctx, RVF);
1627
+
1628
+ TCGv dest = dest_gpr(ctx, a->rd);
1629
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1630
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1631
+
1632
+ gen_helper_fltq_s(dest, cpu_env, src1, src2);
1633
+ gen_set_gpr(ctx, a->rd, dest);
1634
+ return true;
1635
+}
1636
+
1637
+bool trans_fleq_d(DisasContext *ctx, arg_fleq_d *a)
1638
+{
1639
+ REQUIRE_FPU;
1640
+ REQUIRE_ZFA(ctx);
1641
+ REQUIRE_EXT(ctx, RVD);
1642
+
1643
+ TCGv dest = dest_gpr(ctx, a->rd);
1644
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1645
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1646
+
1647
+ gen_helper_fltq_s(dest, cpu_env, src1, src2);
1648
+ gen_set_gpr(ctx, a->rd, dest);
1649
+ return true;
1650
+}
1651
+
1652
+bool trans_fltq_d(DisasContext *ctx, arg_fltq_d *a)
1653
+{
1654
+ REQUIRE_FPU;
1655
+ REQUIRE_ZFA(ctx);
1656
+ REQUIRE_EXT(ctx, RVD);
1657
+
1658
+ TCGv dest = dest_gpr(ctx, a->rd);
1659
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1660
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1661
+
1662
+ gen_helper_fltq_s(dest, cpu_env, src1, src2);
1663
+ gen_set_gpr(ctx, a->rd, dest);
1664
+ return true;
1665
+}
1666
+
1667
+bool trans_fleq_h(DisasContext *ctx, arg_fleq_h *a)
1668
+{
1669
+ REQUIRE_FPU;
1670
+ REQUIRE_ZFA(ctx);
1671
+ REQUIRE_ZFH(ctx);
1672
+
1673
+ TCGv dest = dest_gpr(ctx, a->rd);
1674
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1675
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1676
+
1677
+ gen_helper_fleq_h(dest, cpu_env, src1, src2);
1678
+ gen_set_gpr(ctx, a->rd, dest);
1679
+ return true;
1680
+}
1681
+
1682
+bool trans_fltq_h(DisasContext *ctx, arg_fltq_h *a)
1683
+{
1684
+ REQUIRE_FPU;
1685
+ REQUIRE_ZFA(ctx);
1686
+ REQUIRE_ZFH(ctx);
1687
+
1688
+ TCGv dest = dest_gpr(ctx, a->rd);
1689
+ TCGv_i64 src1 = get_fpr_hs(ctx, a->rs1);
1690
+ TCGv_i64 src2 = get_fpr_hs(ctx, a->rs2);
1691
+
1692
+ gen_helper_fltq_h(dest, cpu_env, src1, src2);
1693
+ gen_set_gpr(ctx, a->rd, dest);
1694
+ return true;
1695
+}
1696
diff --git a/tests/tcg/riscv64/Makefile.target b/tests/tcg/riscv64/Makefile.target
1697
index XXXXXXX..XXXXXXX 100644
1698
--- a/tests/tcg/riscv64/Makefile.target
1699
+++ b/tests/tcg/riscv64/Makefile.target
1700
@@ -XXX,XX +XXX,XX @@ run-test-noc: QEMU_OPTS += -cpu rv64,c=false
1701
1702
TESTS += test-aes
1703
run-test-aes: QEMU_OPTS += -cpu rv64,zk=on
1704
+
1705
+# Test for fcvtmod
1706
+TESTS += test-fcvtmod
1707
+test-fcvtmod: CFLAGS += -march=rv64imafdc
1708
+test-fcvtmod: LDFLAGS += -static
1709
+run-test-fcvtmod: QEMU_OPTS += -cpu rv64,d=true,Zfa=true
117
--
1710
--
118
2.28.0
1711
2.40.1
119
1712
120
1713
diff view generated by jsdifflib