#include #include #include "riscv-traps.h" #include "riscv-csr.h" // Expect this to increment one time per second - inside exception handler, after each return of MTI handler. static volatile uint64_t ecall_count = 0; void exception(uintptr_t mcause, uintptr_t mepc, uintptr_t mtval) { switch(mcause) { case RISCV_EXCP_INSTRUCTION_ADDRESS_MISALIGNED: { puts("[EXCEPTION] : Instruction address misaligned\n"); break; } case RISCV_EXCP_INSTRUCTION_ACCESS_FAULT: { puts("[EXCEPTION] : Instruction access fault\n"); break; } case RISCV_EXCP_ILLEGAL_INSTRUCTION: { puts("[EXCEPTION] : Illegal Instruction\n"); break; } case RISCV_EXCP_BREAKPOINT: { puts("[EXCEPTION] : Breakpoint\n"); break; } case RISCV_EXCP_LOAD_ADDRESS_MISALIGNED: { puts("[EXCEPTION] : Load address misaligned"); printf("[EXCEPTION] : PC: 0x%x\n", mepc); printf("[EXCEPTION] : Addr: 0x%x\n", mtval); break; } case RISCV_EXCP_LOAD_ACCESS_FAULT: { puts("[EXCEPTION] : Load access fault\n"); break; } case RISCV_EXCP_STORE_AMO_ADDRESS_MISALIGNED: { puts("[EXCEPTION] : Store/AMO address misaligned"); printf("[EXCEPTION] : PC: 0x%x\n", mepc); printf("[EXCEPTION] : Addr: 0x%x\n", mtval); break; } case RISCV_EXCP_STORE_AMO_ACCESS_FAULT: { puts("[EXCEPTION] : Store/AMO access fault\n"); break; } case RISCV_EXCP_ENVIRONMENT_CALL_FROM_U_MODE: { puts("[EXCEPTION] : Environment call from U-mode\n"); break; } case RISCV_EXCP_ENVIRONMENT_CALL_FROM_S_MODE: { puts("[EXCEPTION] : Environment call from S-mode\n"); break; } case RISCV_EXCP_ENVIRONMENT_CALL_FROM_M_MODE: { puts("[EXCEPTION] : Environment call from M-mode\n"); ecall_count++; csr_write_mepc(mepc+4); break; } case RISCV_EXCP_INSTRUCTION_PAGE_FAULT: { puts("[EXCEPTION] : Instruction page fault\n"); break; } case RISCV_EXCP_LOAD_PAGE_FAULT: { puts("[EXCEPTION] : Load page fault\n"); break; } case RISCV_EXCP_STORE_AMO_PAGE_FAULT: { puts("[EXCEPTION] : Store/AMO page fault\n"); break; } default: { printf("[EXCEPTION] : Unknown trap cause: %lu\n", mcause); } } while(1) ; }