+// See LICENSE for license details.
+
#ifndef _RISCV_TRAP_H
#define _RISCV_TRAP_H
-#define TRAP_LIST \
- DECLARE_TRAP(instruction_address_misaligned), \
- DECLARE_TRAP(instruction_access_fault), \
- DECLARE_TRAP(illegal_instruction), \
- DECLARE_TRAP(privileged_instruction), \
- DECLARE_TRAP(fp_disabled), \
- DECLARE_TRAP(reserved0), \
- DECLARE_TRAP(syscall), \
- DECLARE_TRAP(breakpoint), \
- DECLARE_TRAP(load_address_misaligned), \
- DECLARE_TRAP(store_address_misaligned), \
- DECLARE_TRAP(load_access_fault), \
- DECLARE_TRAP(store_access_fault), \
- DECLARE_TRAP(vector_disabled), \
- DECLARE_TRAP(vector_bank), \
- DECLARE_TRAP(vector_illegal_instruction), \
- DECLARE_TRAP(reserved1), \
- DECLARE_TRAP(irq0), \
- DECLARE_TRAP(irq1), \
- DECLARE_TRAP(irq2), \
- DECLARE_TRAP(irq3), \
- DECLARE_TRAP(irq4), \
- DECLARE_TRAP(irq5), \
- DECLARE_TRAP(irq6), \
- DECLARE_TRAP(irq7), \
-
-#define DECLARE_TRAP(x) trap_##x
-enum trap_t
+#include "decode.h"
+#include <stdlib.h>
+
+struct state_t;
+
+class trap_t
{
- TRAP_LIST
- NUM_TRAPS
+ public:
+ trap_t(reg_t which) : which(which) {}
+ virtual const char* name();
+ virtual bool has_badaddr() { return false; }
+ virtual reg_t get_badaddr() { abort(); }
+ reg_t cause() { return which; }
+ private:
+ char _name[16];
+ reg_t which;
};
-#undef DECLARE_TRAP
-struct halt_t {}; // thrown to stop the processor from running
+class mem_trap_t : public trap_t
+{
+ public:
+ mem_trap_t(reg_t which, reg_t badaddr)
+ : trap_t(which), badaddr(badaddr) {}
+ bool has_badaddr() override { return true; }
+ reg_t get_badaddr() override { return badaddr; }
+ private:
+ reg_t badaddr;
+};
+
+#define DECLARE_TRAP(n, x) class trap_##x : public trap_t { \
+ public: \
+ trap_##x() : trap_t(n) {} \
+ const char* name() { return "trap_"#x; } \
+};
+
+#define DECLARE_MEM_TRAP(n, x) class trap_##x : public mem_trap_t { \
+ public: \
+ trap_##x(reg_t badaddr) : mem_trap_t(n, badaddr) {} \
+ const char* name() { return "trap_"#x; } \
+};
-extern "C" const char* trap_name(trap_t t);
+DECLARE_MEM_TRAP(CAUSE_MISALIGNED_FETCH, instruction_address_misaligned)
+DECLARE_MEM_TRAP(CAUSE_FETCH_ACCESS, instruction_access_fault)
+DECLARE_MEM_TRAP(CAUSE_ILLEGAL_INSTRUCTION, illegal_instruction)
+DECLARE_MEM_TRAP(CAUSE_BREAKPOINT, breakpoint)
+DECLARE_MEM_TRAP(CAUSE_MISALIGNED_LOAD, load_address_misaligned)
+DECLARE_MEM_TRAP(CAUSE_MISALIGNED_STORE, store_address_misaligned)
+DECLARE_MEM_TRAP(CAUSE_LOAD_ACCESS, load_access_fault)
+DECLARE_MEM_TRAP(CAUSE_STORE_ACCESS, store_access_fault)
+DECLARE_TRAP(CAUSE_USER_ECALL, user_ecall)
+DECLARE_TRAP(CAUSE_SUPERVISOR_ECALL, supervisor_ecall)
+DECLARE_TRAP(CAUSE_HYPERVISOR_ECALL, hypervisor_ecall)
+DECLARE_TRAP(CAUSE_MACHINE_ECALL, machine_ecall)
+DECLARE_MEM_TRAP(CAUSE_FETCH_PAGE_FAULT, instruction_page_fault)
+DECLARE_MEM_TRAP(CAUSE_LOAD_PAGE_FAULT, load_page_fault)
+DECLARE_MEM_TRAP(CAUSE_STORE_PAGE_FAULT, store_page_fault)
#endif