]> git.proxmox.com Git - mirror_qemu.git/blame - target/riscv/cpu.h
target/riscv: add satp_mode profile support
[mirror_qemu.git] / target / riscv / cpu.h
CommitLineData
dc5bd18f
MC
1/*
2 * QEMU RISC-V CPU
3 *
4 * Copyright (c) 2016-2017 Sagar Karandikar, sagark@eecs.berkeley.edu
5 * Copyright (c) 2017-2018 SiFive, Inc.
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms and conditions of the GNU General Public License,
9 * version 2 or later, as published by the Free Software Foundation.
10 *
11 * This program is distributed in the hope it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19
20#ifndef RISCV_CPU_H
21#define RISCV_CPU_H
22
2e5b09fd 23#include "hw/core/cpu.h"
2b7168fc 24#include "hw/registerfields.h"
32fa1776 25#include "hw/qdev-properties.h"
dc5bd18f 26#include "exec/cpu-defs.h"
69242e7e 27#include "qemu/cpu-float.h"
db1015e9 28#include "qom/object.h"
961738ff 29#include "qemu/int128.h"
e91a7227 30#include "cpu_bits.h"
b902ff29 31#include "cpu_cfg.h"
6f23aaeb 32#include "qapi/qapi-types-common.h"
85840bd2 33#include "cpu-qom.h"
dc5bd18f 34
9348028e
PMD
35typedef struct CPUArchState CPURISCVState;
36
66125f93
PMD
37#define CPU_RESOLVING_TYPE TYPE_RISCV_CPU
38
27a6e78e
PMD
39#if defined(TARGET_RISCV32)
40# define TYPE_RISCV_CPU_BASE TYPE_RISCV_CPU_BASE32
41#elif defined(TARGET_RISCV64)
42# define TYPE_RISCV_CPU_BASE TYPE_RISCV_CPU_BASE64
43#endif
44
74433bf0
RH
45#define TCG_GUEST_DEFAULT_MO 0
46
62cf0245
AP
47/*
48 * RISC-V-specific extra insn start words:
49 * 1: Original instruction opcode
50 */
51#define TARGET_INSN_START_EXTRA_WORDS 1
52
dc5bd18f
MC
53#define RV(x) ((target_ulong)1 << (x - 'A'))
54
ed7e6182 55/*
efa365b7 56 * Update misa_bits[], misa_ext_info_arr[] and misa_ext_cfgs[]
ed7e6182
DHB
57 * when adding new MISA bits here.
58 */
dc5bd18f 59#define RVI RV('I')
79f86934 60#define RVE RV('E') /* E and I are mutually exclusive */
dc5bd18f
MC
61#define RVM RV('M')
62#define RVA RV('A')
63#define RVF RV('F')
64#define RVD RV('D')
ad9e5aa2 65#define RVV RV('V')
dc5bd18f
MC
66#define RVC RV('C')
67#define RVS RV('S')
68#define RVU RV('U')
af1fa003 69#define RVH RV('H')
53dcea58 70#define RVJ RV('J')
4f13abcb 71#define RVG RV('G')
dc5bd18f 72
efa365b7 73extern const uint32_t misa_bits[];
ed7e6182
DHB
74const char *riscv_get_misa_ext_name(uint32_t bit);
75const char *riscv_get_misa_ext_description(uint32_t bit);
dc5bd18f 76
238fd586
DHB
77#define CPU_CFG_OFFSET(_prop) offsetof(struct RISCVCPUConfig, _prop)
78
3f361847
DHB
79typedef struct riscv_cpu_profile {
80 const char *name;
81 uint32_t misa_ext;
82 bool enabled;
83 bool user_set;
1a7d4fcb 84 int priv_spec;
55398025 85 int satp_mode;
3f361847
DHB
86 const int32_t ext_offsets[];
87} RISCVCPUProfile;
88
89#define RISCV_PROFILE_EXT_LIST_END -1
1a7d4fcb 90#define RISCV_PROFILE_ATTR_UNUSED -1
3f361847
DHB
91
92extern RISCVCPUProfile *riscv_profiles[];
93
a46d410c
AP
94/* Privileged specification version */
95enum {
96 PRIV_VERSION_1_10_0 = 0,
97 PRIV_VERSION_1_11_0,
3a4af26d 98 PRIV_VERSION_1_12_0,
b9a2b98e
DHB
99
100 PRIV_VERSION_LATEST = PRIV_VERSION_1_12_0,
a46d410c 101};
dc5bd18f 102
9ec6622d 103#define VEXT_VERSION_1_00_0 0x00010000
32931383 104
33a9a57d
YJ
105enum {
106 TRANSLATE_SUCCESS,
107 TRANSLATE_FAIL,
108 TRANSLATE_PMP_FAIL,
109 TRANSLATE_G_STAGE_FAIL
110};
111
42967f40
LZ
112/* Extension context status */
113typedef enum {
114 EXT_STATUS_DISABLED = 0,
115 EXT_STATUS_INITIAL,
116 EXT_STATUS_CLEAN,
117 EXT_STATUS_DIRTY,
118} RISCVExtStatus;
119
dc5bd18f
MC
120#define MMU_USER_IDX 3
121
122#define MAX_RISCV_PMPS (16)
123
bbf3d1b4 124#if !defined(CONFIG_USER_ONLY)
dc5bd18f 125#include "pmp.h"
95799e36 126#include "debug.h"
bbf3d1b4 127#endif
dc5bd18f 128
8a4b5257 129#define RV_VLEN_MAX 1024
3780e337 130#define RV_MAX_MHPMEVENTS 32
621f35bb 131#define RV_MAX_MHPMCOUNTERS 32
ad9e5aa2 132
33f1beaf
FC
133FIELD(VTYPE, VLMUL, 0, 3)
134FIELD(VTYPE, VSEW, 3, 3)
3479a814
FC
135FIELD(VTYPE, VTA, 6, 1)
136FIELD(VTYPE, VMA, 7, 1)
33f1beaf
FC
137FIELD(VTYPE, VEDIV, 8, 2)
138FIELD(VTYPE, RESERVED, 10, sizeof(target_ulong) * 8 - 11)
2b7168fc 139
3780e337
AP
140typedef struct PMUCTRState {
141 /* Current value of a counter */
142 target_ulong mhpmcounter_val;
3b57254d 143 /* Current value of a counter in RV32 */
3780e337
AP
144 target_ulong mhpmcounterh_val;
145 /* Snapshot values of counter */
146 target_ulong mhpmcounter_prev;
147 /* Snapshort value of a counter in RV32 */
148 target_ulong mhpmcounterh_prev;
149 bool started;
14664483
AP
150 /* Value beyond UINT32_MAX/UINT64_MAX before overflow interrupt trigger */
151 target_ulong irq_overflow_left;
3780e337
AP
152} PMUCTRState;
153
1ea4a06a 154struct CPUArchState {
dc5bd18f 155 target_ulong gpr[32];
2b547084 156 target_ulong gprh[32]; /* 64 top bits of the 128-bit registers */
ad9e5aa2
LZ
157
158 /* vector coprocessor state. */
159 uint64_t vreg[32 * RV_VLEN_MAX / 64] QEMU_ALIGNED(16);
160 target_ulong vxrm;
161 target_ulong vxsat;
162 target_ulong vl;
163 target_ulong vstart;
164 target_ulong vtype;
d96a271a 165 bool vill;
ad9e5aa2 166
dc5bd18f
MC
167 target_ulong pc;
168 target_ulong load_res;
169 target_ulong load_val;
170
04bc3027
PMD
171 /* Floating-Point state */
172 uint64_t fpr[32]; /* assume both F and D extensions */
dc5bd18f 173 target_ulong frm;
04bc3027 174 float_status fp_status;
dc5bd18f
MC
175
176 target_ulong badaddr;
62cf0245 177 target_ulong bins;
48eaeb56 178
36a18664 179 target_ulong guest_phys_fault_addr;
dc5bd18f 180
dc5bd18f 181 target_ulong priv_ver;
d2c1a177 182 target_ulong bext_ver;
32931383 183 target_ulong vext_ver;
e91a7227
RH
184
185 /* RISCVMXL, but uint32_t for vmstate migration */
186 uint32_t misa_mxl; /* current mxl */
187 uint32_t misa_mxl_max; /* max mxl for this cpu */
188 uint32_t misa_ext; /* current extensions */
189 uint32_t misa_ext_mask; /* max ext for this cpu */
440544e1 190 uint32_t xl; /* current xlen */
dc5bd18f 191
b3a5d1fb
FP
192 /* 128-bit helpers upper part return value */
193 target_ulong retxh;
194
ce3af0bb
WL
195 target_ulong jvt;
196
5836c3ec
KC
197#ifdef CONFIG_USER_ONLY
198 uint32_t elf_flags;
199#endif
200
dc5bd18f
MC
201#ifndef CONFIG_USER_ONLY
202 target_ulong priv;
ef6bb7b6 203 /* This contains QEMU specific information about the virt state. */
b3c5077b 204 bool virt_enabled;
cd032fe7 205 target_ulong geilen;
277b210d 206 uint64_t resetvec;
dc5bd18f
MC
207
208 target_ulong mhartid;
284d697c
YJ
209 /*
210 * For RV32 this is 32-bit mstatus and 32-bit mstatush.
211 * For RV64 this is a 64-bit mstatus.
212 */
213 uint64_t mstatus;
85ba724f 214
d028ac75 215 uint64_t mip;
33fe584f
AF
216 /*
217 * MIP contains the software writable version of SEIP ORed with the
218 * external interrupt value. The MIP register is always up-to-date.
219 * To keep track of the current source, we also save booleans of the values
220 * here.
221 */
222 bool external_seip;
223 bool software_seip;
66e594f2 224
d028ac75 225 uint64_t miclaim;
85ba724f 226
d028ac75
AP
227 uint64_t mie;
228 uint64_t mideleg;
dc5bd18f 229
1697837e
RK
230 /*
231 * When mideleg[i]=0 and mvien[i]=1, sie[i] is no more
3a4e5601 232 * alias of mie[i] and needs to be maintained separately.
1697837e
RK
233 */
234 uint64_t sie;
235
40336d5b
RK
236 /*
237 * When hideleg[i]=0 and hvien[i]=1, vsie[i] is no more
3a4e5601 238 * alias of sie[i] (mie[i]) and needs to be maintained separately.
40336d5b
RK
239 */
240 uint64_t vsie;
241
dc5bd18f 242 target_ulong satp; /* since: priv-1.10.0 */
ac12b601 243 target_ulong stval;
dc5bd18f
MC
244 target_ulong medeleg;
245
246 target_ulong stvec;
247 target_ulong sepc;
248 target_ulong scause;
249
250 target_ulong mtvec;
251 target_ulong mepc;
252 target_ulong mcause;
253 target_ulong mtval; /* since: priv-1.10.0 */
254
43dc93af
AP
255 /* Machine and Supervisor interrupt priorities */
256 uint8_t miprio[64];
257 uint8_t siprio[64];
258
d1ceff40
AP
259 /* AIA CSRs */
260 target_ulong miselect;
261 target_ulong siselect;
1697837e
RK
262 uint64_t mvien;
263 uint64_t mvip;
d1ceff40 264
bd023ce3
AF
265 /* Hypervisor CSRs */
266 target_ulong hstatus;
267 target_ulong hedeleg;
d028ac75 268 uint64_t hideleg;
bd023ce3
AF
269 target_ulong hcounteren;
270 target_ulong htval;
271 target_ulong htinst;
272 target_ulong hgatp;
cd032fe7
AP
273 target_ulong hgeie;
274 target_ulong hgeip;
c6957248 275 uint64_t htimedelta;
40336d5b
RK
276 uint64_t hvien;
277
278 /*
279 * Bits VSSIP, VSTIP and VSEIP in hvip are maintained in mip. Other bits
280 * from 0:12 are reserved. Bits 13:63 are not aliased and must be separately
281 * maintain in hvip.
282 */
283 uint64_t hvip;
bd023ce3 284
43dc93af 285 /* Hypervisor controlled virtual interrupt priorities */
2b602398 286 target_ulong hvictl;
43dc93af
AP
287 uint8_t hviprio[64];
288
2c64ab66
FP
289 /* Upper 64-bits of 128-bit CSRs */
290 uint64_t mscratchh;
291 uint64_t sscratchh;
292
bd023ce3 293 /* Virtual CSRs */
284d697c
YJ
294 /*
295 * For RV32 this is 32-bit vsstatus and 32-bit vsstatush.
296 * For RV64 this is a 64-bit vsstatus.
297 */
298 uint64_t vsstatus;
bd023ce3
AF
299 target_ulong vstvec;
300 target_ulong vsscratch;
301 target_ulong vsepc;
302 target_ulong vscause;
303 target_ulong vstval;
304 target_ulong vsatp;
305
d1ceff40
AP
306 /* AIA VS-mode CSRs */
307 target_ulong vsiselect;
308
bd023ce3
AF
309 target_ulong mtval2;
310 target_ulong mtinst;
311
66e594f2
AF
312 /* HS Backup CSRs */
313 target_ulong stvec_hs;
314 target_ulong sscratch_hs;
315 target_ulong sepc_hs;
316 target_ulong scause_hs;
317 target_ulong stval_hs;
318 target_ulong satp_hs;
284d697c 319 uint64_t mstatus_hs;
66e594f2 320
3b57254d
WL
321 /*
322 * Signals whether the current exception occurred with two-stage address
323 * translation active.
324 */
ec352d0c 325 bool two_stage_lookup;
8e2aa21b
AP
326 /*
327 * Signals whether the current exception occurred while doing two-stage
328 * address translation for the VS-stage page table walk.
329 */
330 bool two_stage_indirect_lookup;
ec352d0c 331
8c59f5c1
MC
332 target_ulong scounteren;
333 target_ulong mcounteren;
dc5bd18f 334
b1675eeb
AP
335 target_ulong mcountinhibit;
336
3780e337
AP
337 /* PMU counter state */
338 PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
621f35bb 339
3b57254d 340 /* PMU event selector configured values. First three are unused */
621f35bb
AP
341 target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
342
3b57254d 343 /* PMU event selector configured values for RV32 */
14664483
AP
344 target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
345
dc5bd18f
MC
346 target_ulong sscratch;
347 target_ulong mscratch;
348
43888c2f
AP
349 /* Sstc CSRs */
350 uint64_t stimecmp;
351
3ec0fe18
AP
352 uint64_t vstimecmp;
353
dc5bd18f
MC
354 /* physical memory protection */
355 pmp_table_t pmp_state;
2582a95c 356 target_ulong mseccfg;
753e3fe2 357
95799e36
BM
358 /* trigger module */
359 target_ulong trigger_cur;
9495c488
FC
360 target_ulong tdata1[RV_MAX_TRIGGERS];
361 target_ulong tdata2[RV_MAX_TRIGGERS];
362 target_ulong tdata3[RV_MAX_TRIGGERS];
363 struct CPUBreakpoint *cpu_breakpoint[RV_MAX_TRIGGERS];
364 struct CPUWatchpoint *cpu_watchpoint[RV_MAX_TRIGGERS];
5a4ae64c
LZ
365 QEMUTimer *itrigger_timer[RV_MAX_TRIGGERS];
366 int64_t last_icount;
577f0286 367 bool itrigger_enabled;
95799e36 368
c6957248 369 /* machine specific rdtime callback */
e2f01f3c
FC
370 uint64_t (*rdtime_fn)(void *);
371 void *rdtime_fn_arg;
c6957248 372
69077dd6
AP
373 /* machine specific AIA ireg read-modify-write callback */
374#define AIA_MAKE_IREG(__isel, __priv, __virt, __vgein, __xlen) \
375 ((((__xlen) & 0xff) << 24) | \
376 (((__vgein) & 0x3f) << 20) | \
377 (((__virt) & 0x1) << 18) | \
378 (((__priv) & 0x3) << 16) | \
379 (__isel & 0xffff))
380#define AIA_IREG_ISEL(__ireg) ((__ireg) & 0xffff)
381#define AIA_IREG_PRIV(__ireg) (((__ireg) >> 16) & 0x3)
382#define AIA_IREG_VIRT(__ireg) (((__ireg) >> 18) & 0x1)
383#define AIA_IREG_VGEIN(__ireg) (((__ireg) >> 20) & 0x3f)
384#define AIA_IREG_XLEN(__ireg) (((__ireg) >> 24) & 0xff)
385 int (*aia_ireg_rmw_fn[4])(void *arg, target_ulong reg,
386 target_ulong *val, target_ulong new_val, target_ulong write_mask);
387 void *aia_ireg_rmw_fn_arg[4];
388
753e3fe2
JW
389 /* True if in debugger mode. */
390 bool debugger;
4bbe8033
AB
391
392 /*
393 * CSRs for PointerMasking extension
394 */
395 target_ulong mmte;
396 target_ulong mpmmask;
397 target_ulong mpmbase;
398 target_ulong spmmask;
399 target_ulong spmbase;
400 target_ulong upmmask;
401 target_ulong upmbase;
29a9ec9b 402
42fe7499 403 /* CSRs for execution environment configuration */
29a9ec9b 404 uint64_t menvcfg;
3bee0e40
MC
405 uint64_t mstateen[SMSTATEEN_MAX_COUNT];
406 uint64_t hstateen[SMSTATEEN_MAX_COUNT];
407 uint64_t sstateen[SMSTATEEN_MAX_COUNT];
29a9ec9b
AP
408 target_ulong senvcfg;
409 uint64_t henvcfg;
dc5bd18f 410#endif
40bfa5f6
LZ
411 target_ulong cur_pmmask;
412 target_ulong cur_pmbase;
dc5bd18f 413
dc5bd18f 414 /* Fields from here on are preserved across CPU reset. */
43888c2f 415 QEMUTimer *stimer; /* Internal timer for S-mode interrupt */
3ec0fe18
AP
416 QEMUTimer *vstimer; /* Internal timer for VS-mode interrupt */
417 bool vstime_irq;
ad40be27
YJ
418
419 hwaddr kernel_addr;
420 hwaddr fdt_addr;
27abe66f 421
9638cbde 422#ifdef CONFIG_KVM
27abe66f
YJ
423 /* kvm timer */
424 bool kvm_timer_dirty;
425 uint64_t kvm_timer_time;
426 uint64_t kvm_timer_compare;
427 uint64_t kvm_timer_state;
428 uint64_t kvm_timer_frequency;
9638cbde 429#endif /* CONFIG_KVM */
dc5bd18f
MC
430};
431
3b57254d 432/*
dc5bd18f
MC
433 * RISCVCPU:
434 * @env: #CPURISCVState
435 *
436 * A RISCV CPU.
437 */
b36e239e 438struct ArchCPU {
dc5bd18f 439 CPUState parent_obj;
3b3d7df5 440
dc5bd18f 441 CPURISCVState env;
c4e95030 442
b93777e1 443 char *dyn_csr_xml;
719d3561 444 char *dyn_vreg_xml;
b93777e1 445
c4e95030 446 /* Configuration Settings */
466292bd 447 RISCVCPUConfig cfg;
14664483
AP
448
449 QEMUTimer *pmu_timer;
450 /* A bitmask of Available programmable counters */
451 uint32_t pmu_avail_ctrs;
452 /* Mapping of events to counters */
453 GHashTable *pmu_event_ctr_map;
db1015e9 454};
dc5bd18f 455
9348028e
PMD
456/**
457 * RISCVCPUClass:
458 * @parent_realize: The parent class' realize handler.
459 * @parent_phases: The parent class' reset phase handlers.
460 *
461 * A RISCV CPU model.
462 */
463struct RISCVCPUClass {
464 CPUClass parent_class;
465
466 DeviceRealize parent_realize;
467 ResettablePhases parent_phases;
468};
469
dc5bd18f
MC
470static inline int riscv_has_ext(CPURISCVState *env, target_ulong ext)
471{
e91a7227 472 return (env->misa_ext & ext) != 0;
dc5bd18f
MC
473}
474
dc5bd18f 475#include "cpu_user.h"
dc5bd18f
MC
476
477extern const char * const riscv_int_regnames[];
2b547084 478extern const char * const riscv_int_regnamesh[];
dc5bd18f 479extern const char * const riscv_fpr_regnames[];
dc5bd18f 480
c51a3f5d 481const char *riscv_cpu_get_trap_name(target_ulong cause, bool async);
dc5bd18f 482void riscv_cpu_do_interrupt(CPUState *cpu);
43a96588 483int riscv_cpu_write_elf64_note(WriteCoreDumpFunction f, CPUState *cs,
1af0006a 484 int cpuid, DumpState *s);
43a96588 485int riscv_cpu_write_elf32_note(WriteCoreDumpFunction f, CPUState *cs,
1af0006a 486 int cpuid, DumpState *s);
a010bdbe 487int riscv_cpu_gdb_read_register(CPUState *cpu, GByteArray *buf, int reg);
dc5bd18f 488int riscv_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg);
43dc93af
AP
489int riscv_cpu_hviprio_index2irq(int index, int *out_irq, int *out_rdzero);
490uint8_t riscv_cpu_default_priority(int irq);
8f42415f 491uint64_t riscv_cpu_all_pending(CPURISCVState *env);
43dc93af
AP
492int riscv_cpu_mirq_pending(CPURISCVState *env);
493int riscv_cpu_sirq_pending(CPURISCVState *env);
494int riscv_cpu_vsirq_pending(CPURISCVState *env);
b345b480 495bool riscv_cpu_fp_enabled(CPURISCVState *env);
cd032fe7
AP
496target_ulong riscv_cpu_get_geilen(CPURISCVState *env);
497void riscv_cpu_set_geilen(CPURISCVState *env, target_ulong geilen);
61b4b69d 498bool riscv_cpu_vector_enabled(CPURISCVState *env);
ef6bb7b6 499void riscv_cpu_set_virt_enabled(CPURISCVState *env, bool enable);
dc5bd18f 500int riscv_cpu_mmu_index(CPURISCVState *env, bool ifetch);
8905770b 501G_NORETURN void riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
246f8796
WL
502 MMUAccessType access_type,
503 int mmu_idx, uintptr_t retaddr);
8a4ca3c1
RH
504bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
505 MMUAccessType access_type, int mmu_idx,
506 bool probe, uintptr_t retaddr);
dc5bd18f 507char *riscv_isa_string(RISCVCPU *cpu);
dc5bd18f 508
dc5bd18f
MC
509#define cpu_mmu_index riscv_cpu_mmu_index
510
85ba724f 511#ifndef CONFIG_USER_ONLY
d90ebc47
PMD
512void riscv_cpu_do_transaction_failed(CPUState *cs, hwaddr physaddr,
513 vaddr addr, unsigned size,
514 MMUAccessType access_type,
515 int mmu_idx, MemTxAttrs attrs,
516 MemTxResult response, uintptr_t retaddr);
6d2d454a 517hwaddr riscv_cpu_get_phys_page_debug(CPUState *cpu, vaddr addr);
17b3c353 518bool riscv_cpu_exec_interrupt(CPUState *cs, int interrupt_request);
66e594f2 519void riscv_cpu_swap_hypervisor_regs(CPURISCVState *env);
d028ac75 520int riscv_cpu_claim_interrupts(RISCVCPU *cpu, uint64_t interrupts);
bbb9fc25
WL
521uint64_t riscv_cpu_update_mip(CPURISCVState *env, uint64_t mask,
522 uint64_t value);
1ebad505 523void riscv_cpu_interrupt(CPURISCVState *env);
85ba724f 524#define BOOL_TO_MASK(x) (-!!(x)) /* helper for riscv_cpu_update_mip value */
e2f01f3c
FC
525void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(void *),
526 void *arg);
69077dd6
AP
527void riscv_cpu_set_aia_ireg_rmw_fn(CPURISCVState *env, uint32_t priv,
528 int (*rmw_fn)(void *arg,
529 target_ulong reg,
530 target_ulong *val,
531 target_ulong new_val,
532 target_ulong write_mask),
533 void *rmw_fn_arg);
ce3af0bb
WL
534
535RISCVException smstateen_acc_ok(CPURISCVState *env, int index, uint64_t bit);
85ba724f 536#endif
fb738839 537void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv);
dc5bd18f
MC
538
539void riscv_translate_init(void);
8905770b
MAL
540G_NORETURN void riscv_raise_exception(CPURISCVState *env,
541 uint32_t exception, uintptr_t pc);
dc5bd18f 542
fb738839
MC
543target_ulong riscv_cpu_get_fflags(CPURISCVState *env);
544void riscv_cpu_set_fflags(CPURISCVState *env, target_ulong);
dc5bd18f 545
2b7168fc
LZ
546#include "exec/cpu-all.h"
547
61d56494 548FIELD(TB_FLAGS, MEM_IDX, 0, 3)
ebd47648
LZ
549FIELD(TB_FLAGS, FS, 3, 2)
550/* Vector flags */
551FIELD(TB_FLAGS, VS, 5, 2)
552FIELD(TB_FLAGS, LMUL, 7, 3)
553FIELD(TB_FLAGS, SEW, 10, 3)
554FIELD(TB_FLAGS, VL_EQ_VLMAX, 13, 1)
555FIELD(TB_FLAGS, VILL, 14, 1)
0f58cbbe 556FIELD(TB_FLAGS, VSTART_EQ_ZERO, 15, 1)
92371bd9 557/* The combination of MXL/SXL/UXL that applies to the current cpu mode. */
25f3ddff 558FIELD(TB_FLAGS, XL, 16, 2)
0774a7a1 559/* If PointerMasking should be applied */
25f3ddff
RH
560FIELD(TB_FLAGS, PM_MASK_ENABLED, 18, 1)
561FIELD(TB_FLAGS, PM_BASE_ENABLED, 19, 1)
562FIELD(TB_FLAGS, VTA, 20, 1)
563FIELD(TB_FLAGS, VMA, 21, 1)
2c9d7471 564/* Native debug itrigger */
25f3ddff 565FIELD(TB_FLAGS, ITRIGGER, 22, 1)
f1966390 566/* Virtual mode enabled */
25f3ddff 567FIELD(TB_FLAGS, VIRT_ENABLED, 23, 1)
0f58cbbe 568FIELD(TB_FLAGS, PRIV, 24, 2)
3a610f54 569FIELD(TB_FLAGS, AXL, 26, 2)
2b7168fc 570
db23e5d9
RH
571#ifdef TARGET_RISCV32
572#define riscv_cpu_mxl(env) ((void)(env), MXL_RV32)
573#else
574static inline RISCVMXL riscv_cpu_mxl(CPURISCVState *env)
575{
576 return env->misa_mxl;
577}
578#endif
2b602398 579#define riscv_cpu_mxl_bits(env) (1UL << (4 + riscv_cpu_mxl(env)))
51ae0cab 580
d4ea7117
DHB
581static inline const RISCVCPUConfig *riscv_cpu_cfg(CPURISCVState *env)
582{
583 return &env_archcpu(env)->cfg;
584}
585
3a610f54
WL
586#if !defined(CONFIG_USER_ONLY)
587static inline int cpu_address_mode(CPURISCVState *env)
588{
589 int mode = env->priv;
590
591 if (mode == PRV_M && get_field(env->mstatus, MSTATUS_MPRV)) {
592 mode = get_field(env->mstatus, MSTATUS_MPP);
593 }
594 return mode;
595}
596
597static inline RISCVMXL cpu_get_xl(CPURISCVState *env, target_ulong mode)
440544e1
LZ
598{
599 RISCVMXL xl = env->misa_mxl;
440544e1
LZ
600 /*
601 * When emulating a 32-bit-only cpu, use RV32.
602 * When emulating a 64-bit cpu, and MXL has been reduced to RV32,
603 * MSTATUSH doesn't have UXL/SXL, therefore XLEN cannot be widened
604 * back to RV64 for lower privs.
605 */
606 if (xl != MXL_RV32) {
3a610f54 607 switch (mode) {
440544e1
LZ
608 case PRV_M:
609 break;
610 case PRV_U:
611 xl = get_field(env->mstatus, MSTATUS64_UXL);
612 break;
44b8f74b 613 default: /* PRV_S */
440544e1
LZ
614 xl = get_field(env->mstatus, MSTATUS64_SXL);
615 break;
616 }
617 }
440544e1
LZ
618 return xl;
619}
620#endif
621
3a610f54
WL
622#if defined(TARGET_RISCV32)
623#define cpu_recompute_xl(env) ((void)(env), MXL_RV32)
624#else
625static inline RISCVMXL cpu_recompute_xl(CPURISCVState *env)
626{
627#if !defined(CONFIG_USER_ONLY)
628 return cpu_get_xl(env, env->priv);
629#else
630 return env->misa_mxl;
631#endif
632}
633#endif
634
635#if defined(TARGET_RISCV32)
636#define cpu_address_xl(env) ((void)(env), MXL_RV32)
637#else
638static inline RISCVMXL cpu_address_xl(CPURISCVState *env)
639{
640#ifdef CONFIG_USER_ONLY
641 return env->xl;
642#else
643 int mode = cpu_address_mode(env);
644
645 return cpu_get_xl(env, mode);
646#endif
647}
648#endif
649
31961cfe
LZ
650static inline int riscv_cpu_xlen(CPURISCVState *env)
651{
652 return 16 << env->xl;
653}
654
05e6ca5e
GR
655#ifdef TARGET_RISCV32
656#define riscv_cpu_sxl(env) ((void)(env), MXL_RV32)
657#else
658static inline RISCVMXL riscv_cpu_sxl(CPURISCVState *env)
659{
660#ifdef CONFIG_USER_ONLY
661 return env->misa_mxl;
662#else
663 return get_field(env->mstatus, MSTATUS64_SXL);
664#endif
665}
666#endif
667
2b7168fc 668/*
a689a82b
FC
669 * Encode LMUL to lmul as follows:
670 * LMUL vlmul lmul
671 * 1 000 0
672 * 2 001 1
673 * 4 010 2
674 * 8 011 3
675 * - 100 -
676 * 1/8 101 -3
677 * 1/4 110 -2
678 * 1/2 111 -1
679 *
680 * then, we can calculate VLMAX = vlen >> (vsew + 3 - lmul)
681 * e.g. vlen = 256 bits, SEW = 16, LMUL = 1/8
682 * => VLMAX = vlen >> (1 + 3 - (-3))
683 * = 256 >> 7
684 * = 2
2b7168fc
LZ
685 */
686static inline uint32_t vext_get_vlmax(RISCVCPU *cpu, target_ulong vtype)
687{
a689a82b
FC
688 uint8_t sew = FIELD_EX64(vtype, VTYPE, VSEW);
689 int8_t lmul = sextract32(FIELD_EX64(vtype, VTYPE, VLMUL), 0, 3);
2b7168fc
LZ
690 return cpu->cfg.vlen >> (sew + 3 - lmul);
691}
692
bb5de525
AJ
693void cpu_get_tb_cpu_state(CPURISCVState *env, vaddr *pc,
694 uint64_t *cs_base, uint32_t *pflags);
dc5bd18f 695
40bfa5f6 696void riscv_cpu_update_mask(CPURISCVState *env);
e7acc1cb 697bool riscv_cpu_is_32bit(RISCVCPU *cpu);
40bfa5f6 698
533c91e8
AF
699RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
700 target_ulong *ret_value,
701 target_ulong new_value, target_ulong write_mask);
702RISCVException riscv_csrrw_debug(CPURISCVState *env, int csrno,
703 target_ulong *ret_value,
704 target_ulong new_value,
705 target_ulong write_mask);
c7b95171 706
fb738839
MC
707static inline void riscv_csr_write(CPURISCVState *env, int csrno,
708 target_ulong val)
c7b95171
MC
709{
710 riscv_csrrw(env, csrno, NULL, val, MAKE_64BIT_MASK(0, TARGET_LONG_BITS));
711}
712
fb738839 713static inline target_ulong riscv_csr_read(CPURISCVState *env, int csrno)
c7b95171
MC
714{
715 target_ulong val = 0;
716 riscv_csrrw(env, csrno, &val, 0, 0);
717 return val;
718}
719
0e62f92e
AF
720typedef RISCVException (*riscv_csr_predicate_fn)(CPURISCVState *env,
721 int csrno);
605def6e
AF
722typedef RISCVException (*riscv_csr_read_fn)(CPURISCVState *env, int csrno,
723 target_ulong *ret_value);
724typedef RISCVException (*riscv_csr_write_fn)(CPURISCVState *env, int csrno,
725 target_ulong new_value);
726typedef RISCVException (*riscv_csr_op_fn)(CPURISCVState *env, int csrno,
727 target_ulong *ret_value,
728 target_ulong new_value,
729 target_ulong write_mask);
c7b95171 730
961738ff
FP
731RISCVException riscv_csrrw_i128(CPURISCVState *env, int csrno,
732 Int128 *ret_value,
733 Int128 new_value, Int128 write_mask);
734
457c360f
FP
735typedef RISCVException (*riscv_csr_read128_fn)(CPURISCVState *env, int csrno,
736 Int128 *ret_value);
737typedef RISCVException (*riscv_csr_write128_fn)(CPURISCVState *env, int csrno,
738 Int128 new_value);
739
c7b95171 740typedef struct {
8ceac5dc 741 const char *name;
a88365c1 742 riscv_csr_predicate_fn predicate;
c7b95171
MC
743 riscv_csr_read_fn read;
744 riscv_csr_write_fn write;
745 riscv_csr_op_fn op;
457c360f
FP
746 riscv_csr_read128_fn read128;
747 riscv_csr_write128_fn write128;
a4b2fa43
AP
748 /* The default priv spec version should be PRIV_VERSION_1_10_0 (i.e 0) */
749 uint32_t min_priv_ver;
c7b95171
MC
750} riscv_csr_operations;
751
56118ee8
BM
752/* CSR function table constants */
753enum {
754 CSR_TABLE_SIZE = 0x1000
755};
756
3b57254d 757/*
14664483
AP
758 * The event id are encoded based on the encoding specified in the
759 * SBI specification v0.3
760 */
761
762enum riscv_pmu_event_idx {
763 RISCV_PMU_EVENT_HW_CPU_CYCLES = 0x01,
764 RISCV_PMU_EVENT_HW_INSTRUCTIONS = 0x02,
765 RISCV_PMU_EVENT_CACHE_DTLB_READ_MISS = 0x10019,
766 RISCV_PMU_EVENT_CACHE_DTLB_WRITE_MISS = 0x1001B,
767 RISCV_PMU_EVENT_CACHE_ITLB_PREFETCH_MISS = 0x10021,
768};
769
36c1118d
DHB
770/* used by tcg/tcg-cpu.c*/
771void isa_ext_update_enabled(RISCVCPU *cpu, uint32_t ext_offset, bool en);
36c1118d 772bool isa_ext_is_enabled(RISCVCPU *cpu, uint32_t ext_offset);
f51d03b0 773void riscv_cpu_set_misa(CPURISCVState *env, RISCVMXL mxl, uint32_t ext);
36c1118d 774
32fa1776
DHB
775typedef struct RISCVCPUMultiExtConfig {
776 const char *name;
777 uint32_t offset;
778 bool enabled;
779} RISCVCPUMultiExtConfig;
780
781extern const RISCVCPUMultiExtConfig riscv_cpu_extensions[];
782extern const RISCVCPUMultiExtConfig riscv_cpu_vendor_exts[];
783extern const RISCVCPUMultiExtConfig riscv_cpu_experimental_exts[];
5fe2800b 784extern const RISCVCPUMultiExtConfig riscv_cpu_named_features[];
8043effd 785extern const RISCVCPUMultiExtConfig riscv_cpu_deprecated_exts[];
32fa1776
DHB
786extern Property riscv_cpu_options[];
787
7935e2c4
DHB
788typedef struct isa_ext_data {
789 const char *name;
790 int min_version;
791 int ext_enable_offset;
792} RISCVIsaExtData;
793extern const RISCVIsaExtData isa_edata_arr[];
b933720b 794char *riscv_cpu_get_name(RISCVCPU *cpu);
7935e2c4 795
a13a6082 796void riscv_cpu_finalize_features(RISCVCPU *cpu, Error **errp);
7d0c302c 797void riscv_add_satp_mode_properties(Object *obj);
ef58fad0 798bool riscv_cpu_accelerator_compatible(RISCVCPU *cpu);
32fa1776 799
56118ee8 800/* CSR function table */
6f03770d 801extern riscv_csr_operations csr_ops[CSR_TABLE_SIZE];
56118ee8 802
6f23aaeb
AG
803extern const bool valid_vm_1_10_32[], valid_vm_1_10_64[];
804
c7b95171
MC
805void riscv_get_csr_ops(int csrno, riscv_csr_operations *ops);
806void riscv_set_csr_ops(int csrno, riscv_csr_operations *ops);
dc5bd18f 807
5371f5cd
JW
808void riscv_cpu_register_gdb_regs_for_features(CPUState *cs);
809
6f23aaeb
AG
810uint8_t satp_mode_max_from_map(uint32_t map);
811const char *satp_mode_str(uint8_t satp_mode, bool is_32_bit);
812
dc5bd18f 813#endif /* RISCV_CPU_H */