From 5d1fb6b8c4eea6af9ebf02234724716ca25db3a1 Mon Sep 17 00:00:00 2001 From: Tim Newsome Date: Thu, 21 Apr 2016 15:53:46 -0700 Subject: [PATCH] Add writing to DCSR, DPC, DSCRATCH. Make those 3 CSRs writable. --- riscv/decode.h | 5 +++++ riscv/processor.cc | 37 +++++++++++++++++++++++++++++++++++++ riscv/processor.h | 17 +++++++++++++++++ 3 files changed, 59 insertions(+) diff --git a/riscv/decode.h b/riscv/decode.h index 6e54431..b922e02 100644 --- a/riscv/decode.h +++ b/riscv/decode.h @@ -225,4 +225,9 @@ private: throw trap_illegal_instruction(); \ (which); }) +/* Debug CSRs. These should probably be in encoding.h, but that file is + * automatically generated. */ +/* TODO */ +#include "/media/sf_tnewsome/Synced/SiFive/debug-spec/core_registers.tex.h" + #endif diff --git a/riscv/processor.cc b/riscv/processor.cc index b12efe8..996f9e3 100644 --- a/riscv/processor.cc +++ b/riscv/processor.cc @@ -363,6 +363,22 @@ void processor_t::set_csr(int which, reg_t val) case CSR_MSCRATCH: state.mscratch = val; break; case CSR_MCAUSE: state.mcause = val; break; case CSR_MBADADDR: state.mbadaddr = val; break; + case DCSR_ADDRESS: + state.dcsr.prv = (val & DCSR_PRV_MASK) >> DCSR_PRV_OFFSET; + state.dcsr.step = (val & DCSR_STEP_MASK) >> DCSR_STEP_OFFSET; + // TODO: ndreset and fullreset + state.dcsr.ebreakm = (val & DCSR_EBREAKM_MASK) >> DCSR_EBREAKM_OFFSET; + state.dcsr.ebreakh = (val & DCSR_EBREAKH_MASK) >> DCSR_EBREAKH_OFFSET; + state.dcsr.ebreaks = (val & DCSR_EBREAKS_MASK) >> DCSR_EBREAKS_OFFSET; + state.dcsr.ebreaku = (val & DCSR_EBREAKU_MASK) >> DCSR_EBREAKU_OFFSET; + state.dcsr.halt = (val & DCSR_HALT_MASK) >> DCSR_HALT_OFFSET; + break; + case DPC_ADDRESS: + state.dpc = val; + break; + case DSCRATCH_ADDRESS: + state.dscratch = val; + break; } } @@ -451,6 +467,27 @@ reg_t processor_t::get_csr(int which) case CSR_MTVEC: return state.mtvec; case CSR_MEDELEG: return state.medeleg; case CSR_MIDELEG: return state.mideleg; + case DCSR_ADDRESS: + return + (1 << DCSR_XDEBUGVER_OFFSET) | + (0 << DCSR_HWBPCOUNT_OFFSET) | + (0 << DCSR_NDRESET_OFFSET) | + (0 << DCSR_FULLRESET_OFFSET) | + (state.dcsr.prv << DCSR_PRV_OFFSET) | + (state.dcsr.step << DCSR_STEP_OFFSET) | + (state.dcsr.debugint << DCSR_DEBUGINT_OFFSET) | + (0 << DCSR_STOPCYCLE_OFFSET) | + (0 << DCSR_STOPTIME_OFFSET) | + (state.dcsr.ebreakm << DCSR_EBREAKM_OFFSET) | + (state.dcsr.ebreakh << DCSR_EBREAKH_OFFSET) | + (state.dcsr.ebreaks << DCSR_EBREAKS_OFFSET) | + (state.dcsr.ebreaku << DCSR_EBREAKU_OFFSET) | + (state.dcsr.halt << DCSR_HALT_OFFSET) | + (state.dcsr.cause << DCSR_CAUSE_OFFSET); + case DPC_ADDRESS: + return state.dpc; + case DSCRATCH_ADDRESS: + return state.dscratch; } throw trap_illegal_instruction(); } diff --git a/riscv/processor.h b/riscv/processor.h index 869873f..e014299 100644 --- a/riscv/processor.h +++ b/riscv/processor.h @@ -31,6 +31,19 @@ struct commit_log_reg_t reg_t data; }; +typedef struct +{ + uint8_t prv; + bool step; + bool debugint; + bool ebreakm; + bool ebreakh; + bool ebreaks; + bool ebreaku; + bool halt; + uint8_t cause; +} dcsr_t; + // architectural state of a RISC-V hart struct state_t { @@ -61,6 +74,10 @@ struct state_t reg_t stvec; reg_t sptbr; reg_t scause; + reg_t dpc; + reg_t dscratch; + dcsr_t dcsr; + uint32_t fflags; uint32_t frm; bool serialized; // whether timer CSRs are in a well-defined state -- 2.30.2