summaryrefslogtreecommitdiff
path: root/riscv
diff options
context:
space:
mode:
authorPrashanth Mundkur2018-10-08 09:35:11 -0700
committerPrashanth Mundkur2018-10-23 15:32:15 -0700
commitd43b475507ed9144b26be124376c3e656005a416 (patch)
tree5d4bc4eba9b4993610ee9098abbd68c2cac01fe0 /riscv
parente3490924e6bce23d3d4b236fdc61c7345a17e814 (diff)
RISC-V: Add a platform knob to control mtval contents on illegal instruction faults.
Diffstat (limited to 'riscv')
-rw-r--r--riscv/platform.ml2
-rw-r--r--riscv/platform_main.ml3
-rw-r--r--riscv/riscv_extras.lem4
-rw-r--r--riscv/riscv_extras_sequential.lem4
-rw-r--r--riscv/riscv_platform.c3
-rw-r--r--riscv/riscv_platform.h1
-rw-r--r--riscv/riscv_platform.sail16
-rw-r--r--riscv/riscv_platform_impl.c5
-rw-r--r--riscv/riscv_platform_impl.h1
-rw-r--r--riscv/riscv_sim.c11
-rw-r--r--riscv/riscv_step.sail6
-rw-r--r--riscv/riscv_sys.sail12
-rw-r--r--riscv/riscv_types.sail7
13 files changed, 52 insertions, 23 deletions
diff --git a/riscv/platform.ml b/riscv/platform.ml
index 092df80f..06486ca2 100644
--- a/riscv/platform.ml
+++ b/riscv/platform.ml
@@ -56,6 +56,7 @@ module Elf = Elf_loader;;
let config_enable_dirty_update = ref false
let config_enable_misaligned_access = ref false
+let config_mtval_has_illegal_inst_bits = ref false
(* Mapping to Sail externs *)
@@ -82,6 +83,7 @@ let make_rom start_pc =
let enable_dirty_update () = !config_enable_dirty_update
let enable_misaligned_access () = !config_enable_misaligned_access
+let mtval_has_illegal_inst_bits () = !config_mtval_has_illegal_inst_bits
let rom_base () = bits_of_int64 P.rom_base
let rom_size () = bits_of_int !rom_size_ref
diff --git a/riscv/platform_main.ml b/riscv/platform_main.ml
index e204daee..b33247f1 100644
--- a/riscv/platform_main.ml
+++ b/riscv/platform_main.ml
@@ -73,6 +73,9 @@ let options = Arg.align ([("-dump-dts",
("-enable-misaligned-access",
Arg.Set P.config_enable_misaligned_access,
" enable misaligned accesses without M-mode traps");
+ ("-mtval-has-illegal-inst-bits",
+ Arg.Set P.config_mtval_has_illegal_inst_bits,
+ " mtval stores instruction bits on an illegal instruction exception");
("-with-dtc",
Arg.String PI.set_dtc,
" full path to dtc to use")
diff --git a/riscv/riscv_extras.lem b/riscv/riscv_extras.lem
index a6fa1298..7028d5b8 100644
--- a/riscv/riscv_extras.lem
+++ b/riscv/riscv_extras.lem
@@ -97,6 +97,10 @@ val plat_enable_misaligned_access : unit -> bool
let plat_enable_misaligned_access () = false
declare ocaml target_rep function plat_enable_misaligned_access = `Platform.enable_misaligned_access`
+val plat_mtval_has_illegal_inst_bits : unit -> bool
+let plat_mtval_has_illegal_inst_bits () = false
+declare ocaml target_rep function plat_mtval_has_illegal_inst_bits = `Platform.mtval_has_illegal_inst_bits`
+
val plat_insns_per_tick : unit -> integer
let plat_insns_per_tick () = 1
declare ocaml target_rep function plat_insns_per_tick = `Platform.insns_per_tick`
diff --git a/riscv/riscv_extras_sequential.lem b/riscv/riscv_extras_sequential.lem
index a6fa1298..7028d5b8 100644
--- a/riscv/riscv_extras_sequential.lem
+++ b/riscv/riscv_extras_sequential.lem
@@ -97,6 +97,10 @@ val plat_enable_misaligned_access : unit -> bool
let plat_enable_misaligned_access () = false
declare ocaml target_rep function plat_enable_misaligned_access = `Platform.enable_misaligned_access`
+val plat_mtval_has_illegal_inst_bits : unit -> bool
+let plat_mtval_has_illegal_inst_bits () = false
+declare ocaml target_rep function plat_mtval_has_illegal_inst_bits = `Platform.mtval_has_illegal_inst_bits`
+
val plat_insns_per_tick : unit -> integer
let plat_insns_per_tick () = 1
declare ocaml target_rep function plat_insns_per_tick = `Platform.insns_per_tick`
diff --git a/riscv/riscv_platform.c b/riscv/riscv_platform.c
index 5eeb0eb7..f0aff76a 100644
--- a/riscv/riscv_platform.c
+++ b/riscv/riscv_platform.c
@@ -14,6 +14,9 @@ bool plat_enable_dirty_update(unit u)
bool plat_enable_misaligned_access(unit u)
{ return rv_enable_misaligned; }
+bool plat_mtval_has_illegal_inst_bits(unit u)
+{ return rv_mtval_has_illegal_inst_bits; }
+
mach_bits plat_ram_base(unit u)
{ return rv_ram_base; }
diff --git a/riscv/riscv_platform.h b/riscv/riscv_platform.h
index 4401ad49..93782660 100644
--- a/riscv/riscv_platform.h
+++ b/riscv/riscv_platform.h
@@ -3,6 +3,7 @@
bool plat_enable_dirty_update(unit);
bool plat_enable_misaligned_access(unit);
+bool plat_mtval_has_illegal_inst_bits(unit);
mach_bits plat_ram_base(unit);
mach_bits plat_ram_size(unit);
diff --git a/riscv/riscv_platform.sail b/riscv/riscv_platform.sail
index c4af9c79..3020d23d 100644
--- a/riscv/riscv_platform.sail
+++ b/riscv/riscv_platform.sail
@@ -22,6 +22,11 @@ val plat_enable_misaligned_access = {ocaml: "Platform.enable_misaligned_access",
c: "plat_enable_misaligned_access",
lem: "plat_enable_misaligned_access"} : unit -> bool
+/* whether mtval stores the bits of a faulting instruction on illegal instruction exceptions */
+val plat_mtval_has_illegal_inst_bits = {ocaml: "Platform.mtval_has_illegal_inst_bits",
+ c: "plat_mtval_has_illegal_inst_bits",
+ lem: "plat_mtval_has_illegal_inst_bits"} : unit -> bool
+
/* ROM holding reset vector and device-tree DTB */
val plat_rom_base = {ocaml: "Platform.rom_base", c: "plat_rom_base", lem: "plat_rom_base"} : unit -> xlenbits
val plat_rom_size = {ocaml: "Platform.rom_size", c: "plat_rom_size", lem: "plat_rom_size"} : unit -> xlenbits
@@ -265,3 +270,14 @@ function tick_platform() -> unit = {
cancel_reservation();
htif_tick();
}
+
+/* Platform-specific handling of instruction faults */
+
+function handle_illegal() -> unit = {
+ let info = if plat_mtval_has_illegal_inst_bits ()
+ then Some(instbits)
+ else None();
+ let t : sync_exception = struct { trap = E_Illegal_Instr,
+ excinfo = info };
+ nextPC = handle_exception(cur_privilege, CTL_TRAP(t), PC)
+}
diff --git a/riscv/riscv_platform_impl.c b/riscv/riscv_platform_impl.c
index d8d52da0..04a661c0 100644
--- a/riscv/riscv_platform_impl.c
+++ b/riscv/riscv_platform_impl.c
@@ -4,8 +4,9 @@
/* Settings of the platform implementation, with common defaults. */
-bool rv_enable_dirty_update = false;
-bool rv_enable_misaligned = false;
+bool rv_enable_dirty_update = false;
+bool rv_enable_misaligned = false;
+bool rv_mtval_has_illegal_inst_bits = false;
uint64_t rv_ram_base = UINT64_C(0x80000000);
uint64_t rv_ram_size = UINT64_C(0x80000000);
diff --git a/riscv/riscv_platform_impl.h b/riscv/riscv_platform_impl.h
index 562f8554..85e25c95 100644
--- a/riscv/riscv_platform_impl.h
+++ b/riscv/riscv_platform_impl.h
@@ -10,6 +10,7 @@
extern bool rv_enable_dirty_update;
extern bool rv_enable_misaligned;
+extern bool rv_mtval_has_illegal_inst_bits;
extern uint64_t rv_ram_base;
extern uint64_t rv_ram_size;
diff --git a/riscv/riscv_sim.c b/riscv/riscv_sim.c
index 79c353f9..9db1ea59 100644
--- a/riscv/riscv_sim.c
+++ b/riscv/riscv_sim.c
@@ -42,11 +42,12 @@ struct tv_spike_t *s = NULL;
char *term_log = NULL;
static struct option options[] = {
- {"enable-dirty", no_argument, 0, 'd'},
- {"enable-misaligned", no_argument, 0, 'm'},
- {"dump-dts", no_argument, 0, 's'},
- {"terminal-log", required_argument, 0, 't'},
- {"help", no_argument, 0, 'h'},
+ {"enable-dirty", no_argument, 0, 'd'},
+ {"enable-misaligned", no_argument, 0, 'm'},
+ {"mtval-has-illegal-inst-bits", no_argument, 0, 'i'},
+ {"dump-dts", no_argument, 0, 's'},
+ {"terminal-log", required_argument, 0, 't'},
+ {"help", no_argument, 0, 'h'},
{0, 0, 0, 0}
};
diff --git a/riscv/riscv_step.sail b/riscv/riscv_step.sail
index f9675115..218be598 100644
--- a/riscv/riscv_step.sail
+++ b/riscv/riscv_step.sail
@@ -63,7 +63,8 @@ function step(step_no) = {
match decodeCompressed(h) {
None() => {
print("[" ^ string_of_int(step_no) ^ "] [" ^ cur_privilege ^ "]: " ^ BitStr(PC) ^ " (" ^ BitStr(h) ^ ") <no-decode>");
- handle_decode_exception(EXTZ(h));
+ instbits = EXTZ(h);
+ handle_illegal();
(false, true)
},
Some(ast) => {
@@ -77,7 +78,8 @@ function step(step_no) = {
match decode(w) {
None() => {
print("[" ^ string_of_int(step_no) ^ "] [" ^ cur_privilege ^ "]: " ^ BitStr(PC) ^ " (" ^ BitStr(w) ^ ") <no-decode>");
- handle_decode_exception(EXTZ(w));
+ instbits = EXTZ(w);
+ handle_illegal();
(false, true)
},
Some(ast) => {
diff --git a/riscv/riscv_sys.sail b/riscv/riscv_sys.sail
index 37c45117..9c49d9e5 100644
--- a/riscv/riscv_sys.sail
+++ b/riscv/riscv_sys.sail
@@ -976,21 +976,9 @@ function handle_mem_exception(addr : xlenbits, e : ExceptionType) -> unit = {
nextPC = handle_exception(cur_privilege, CTL_TRAP(t), PC)
}
-function handle_decode_exception(instbits : xlenbits) -> unit = {
- let t : sync_exception = struct { trap = E_Illegal_Instr,
- excinfo = Some(instbits) };
- nextPC = handle_exception(cur_privilege, CTL_TRAP(t), PC)
-}
-
function handle_interrupt(i : InterruptType, del_priv : Privilege) -> unit =
nextPC = handle_trap(del_priv, true, i, PC, None())
-function handle_illegal() -> unit = {
- let t : sync_exception = struct { trap = E_Illegal_Instr,
- excinfo = None() };
- nextPC = handle_exception(cur_privilege, CTL_TRAP(t), PC)
-}
-
/* state state initialization */
function init_sys() -> unit = {
diff --git a/riscv/riscv_types.sail b/riscv/riscv_types.sail
index d269356c..4cbc6f87 100644
--- a/riscv/riscv_types.sail
+++ b/riscv/riscv_types.sail
@@ -34,8 +34,11 @@ let sp : regbits = 0b00010 /* x2, stack pointer */
/* program counter */
-register PC : xlenbits
-register nextPC : xlenbits
+register PC : xlenbits
+register nextPC : xlenbits
+
+/* internal state to hold instruction bits for faulting instructions */
+register instbits : xlenbits
/* register file and accessors */