Skip to content

Commit 95af514

Browse files
committed
Add DCSR.MPRVEN support
Adds DCSR.MPRVEN bit support, as specified in RISC-V External Debug Support Version 1.0.0-rc4 (https://github.com/riscv/riscv-debug-spec/releases/tag/1.0.0-rc4, see 4.9.1 Debug Control and Status). This bit allows to enable hardware virtual address translation when memory access is initiated by the debugger (see 4.1 Debug Mode, clause 2). This change: * Increases debug specification coverage, allows more detailed testing of external debuggers with Spike. * Decreases the number of required abstract commands to read virtual memory thus improving the user experience. Commit's changes: * Added MPRVEN field to DCSR register * Updated debug_rom.S to turn off MPRVEN while executing ROM To avoid unwanted address translation in while debug_rom.S executed DCSR.MPRVEN bit has to be cleared on entry and restored on exit. Updated version of debug_rom.S does the following: * On _entry: clears DCSR.MPRVEN bit, stores previous DCSR value to S1 and stores previous S1 value to DSCRATCH01 * On _exception: restores S1 value from DSCRATCH01 * On _resume/going: restores S1 and DCSR values Signed-off-by: Farid Khaydari <f.khaydari@syntacore.com>
1 parent 4cf4915 commit 95af514

File tree

5 files changed

+28
-12
lines changed

5 files changed

+28
-12
lines changed

debug_rom/debug_rom.S

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,12 @@ _entry:
2323
// This fence is required because the execution may have written something
2424
// into the Abstract Data or Program Buffer registers.
2525
fence
26-
csrw CSR_DSCRATCH0, s0 // Save s0 to allow signaling MHARTID
26+
csrw CSR_DSCRATCH0, s0 // Save s0 to allow signaling MHARTID
27+
28+
// We need to disable privilege modification to avoid
29+
// address translation in debug_rom memory accesses
30+
csrw CSR_DSCRATCH1, s1 // Save s1
31+
csrrci s1, CSR_DCSR, DCSR_MPRVEN // Save DCSR and clear MPRVEN
2732

2833
// We continue to let the hart know that we are halted in order that
2934
// a DM which was reset is still made aware that a hart is halted.
@@ -47,13 +52,16 @@ _exception:
4752
// We need this in case the user tried an abstract write to a
4853
// non-existent CSR.
4954
csrr s0, CSR_DSCRATCH0
55+
csrr s1, CSR_DSCRATCH1 // Restore s1
5056
sw zero, DEBUG_ROM_EXCEPTION(zero) // Let debug module know you got an exception.
5157
ebreak
5258

5359
going:
5460
csrr s0, CSR_MHARTID
5561
sw s0, DEBUG_ROM_GOING(zero) // When debug module sees this write, the GO flag is reset.
5662
csrr s0, CSR_DSCRATCH0 // Restore s0 here
63+
csrw CSR_DCSR, s1 // Restore DSCR
64+
csrr s1, CSR_DSCRATCH1 // Restore s1
5765
fence
5866
fence.i
5967
jalr zero, zero, %lo(whereto) // Debug module will put different instructions and data in the RAM,
@@ -64,6 +72,8 @@ _resume:
6472
csrr s0, CSR_MHARTID
6573
sw s0, DEBUG_ROM_RESUMING(zero) // When Debug Module sees this write, the RESUME flag is reset.
6674
csrr s0, CSR_DSCRATCH0 // Restore s0
75+
csrw CSR_DCSR, s1 // Restore DSCR
76+
csrr s1, CSR_DSCRATCH1 // Restore s1
6777
dret
6878

6979
// END OF ACTUAL "ROM" CONTENTS. BELOW IS JUST FOR LINKER SCRIPT.

debug_rom/debug_rom.h

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,15 @@
11
static const unsigned char debug_rom_raw[] = {
2-
0x6f, 0x00, 0xc0, 0x00, 0x6f, 0x00, 0x00, 0x06, 0x6f, 0x00, 0x80, 0x03,
3-
0x0f, 0x00, 0xf0, 0x0f, 0x73, 0x10, 0x24, 0x7b, 0x73, 0x24, 0x40, 0xf1,
4-
0x23, 0x20, 0x80, 0x10, 0x03, 0x44, 0x04, 0x40, 0x13, 0x74, 0x14, 0x00,
5-
0x63, 0x14, 0x04, 0x02, 0x73, 0x24, 0x40, 0xf1, 0x03, 0x44, 0x04, 0x40,
6-
0x13, 0x74, 0x24, 0x00, 0x63, 0x18, 0x04, 0x02, 0x73, 0x00, 0x50, 0x10,
7-
0x6f, 0xf0, 0x9f, 0xfd, 0x73, 0x24, 0x20, 0x7b, 0x23, 0x26, 0x00, 0x10,
2+
0x6f, 0x00, 0xc0, 0x00, 0x6f, 0x00, 0x40, 0x07, 0x6f, 0x00, 0x00, 0x04,
3+
0x0f, 0x00, 0xf0, 0x0f, 0x73, 0x10, 0x24, 0x7b, 0x73, 0x90, 0x34, 0x7b,
4+
0xf3, 0x74, 0x08, 0x7b, 0x73, 0x24, 0x40, 0xf1, 0x23, 0x20, 0x80, 0x10,
5+
0x03, 0x44, 0x04, 0x40, 0x13, 0x74, 0x14, 0x00, 0x63, 0x16, 0x04, 0x02,
6+
0x73, 0x24, 0x40, 0xf1, 0x03, 0x44, 0x04, 0x40, 0x13, 0x74, 0x24, 0x00,
7+
0x63, 0x1e, 0x04, 0x02, 0x73, 0x00, 0x50, 0x10, 0x6f, 0xf0, 0x9f, 0xfd,
8+
0x73, 0x24, 0x20, 0x7b, 0xf3, 0x24, 0x30, 0x7b, 0x23, 0x26, 0x00, 0x10,
89
0x73, 0x00, 0x10, 0x00, 0x73, 0x24, 0x40, 0xf1, 0x23, 0x22, 0x80, 0x10,
9-
0x73, 0x24, 0x20, 0x7b, 0x0f, 0x00, 0xf0, 0x0f, 0x0f, 0x10, 0x00, 0x00,
10-
0x67, 0x00, 0x00, 0x30, 0x73, 0x24, 0x40, 0xf1, 0x23, 0x24, 0x80, 0x10,
11-
0x73, 0x24, 0x20, 0x7b, 0x73, 0x00, 0x20, 0x7b
10+
0x73, 0x24, 0x20, 0x7b, 0x73, 0x90, 0x04, 0x7b, 0xf3, 0x24, 0x30, 0x7b,
11+
0x0f, 0x00, 0xf0, 0x0f, 0x0f, 0x10, 0x00, 0x00, 0x67, 0x00, 0x00, 0x30,
12+
0x73, 0x24, 0x40, 0xf1, 0x23, 0x24, 0x80, 0x10, 0x73, 0x24, 0x20, 0x7b,
13+
0x73, 0x90, 0x04, 0x7b, 0xf3, 0x24, 0x30, 0x7b, 0x73, 0x00, 0x20, 0x7b
1214
};
13-
static const unsigned int debug_rom_raw_len = 116;
15+
static const unsigned int debug_rom_raw_len = 144;

riscv/csrs.cc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1345,6 +1345,7 @@ dcsr_csr_t::dcsr_csr_t(processor_t* const proc, const reg_t addr):
13451345
ebreakvs(false),
13461346
ebreakvu(false),
13471347
v(false),
1348+
mprven(false),
13481349
cause(0),
13491350
ext_cause(0),
13501351
cetrig(0),
@@ -1374,6 +1375,7 @@ reg_t dcsr_csr_t::read() const noexcept {
13741375
result = set_field(result, DCSR_STEP, step);
13751376
result = set_field(result, DCSR_PRV, prv);
13761377
result = set_field(result, CSR_DCSR_V, v);
1378+
result = set_field(result, DCSR_MPRVEN, mprven);
13771379
result = set_field(result, DCSR_PELP, pelp);
13781380
return result;
13791381
}
@@ -1388,6 +1390,7 @@ bool dcsr_csr_t::unlogged_write(const reg_t val) noexcept {
13881390
ebreakvs = proc->extension_enabled('H') ? get_field(val, CSR_DCSR_EBREAKVS) : false;
13891391
ebreakvu = proc->extension_enabled('H') ? get_field(val, CSR_DCSR_EBREAKVU) : false;
13901392
v = proc->extension_enabled('H') ? get_field(val, CSR_DCSR_V) : false;
1393+
mprven = get_field(val, CSR_DCSR_MPRVEN);
13911394
pelp = proc->extension_enabled(EXT_ZICFILP) ?
13921395
static_cast<elp_t>(get_field(val, DCSR_PELP)) : elp_t::NO_LP_EXPECTED;
13931396
cetrig = proc->extension_enabled(EXT_SMDBLTRP) ? get_field(val, DCSR_CETRIG) : false;

riscv/csrs.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -697,6 +697,7 @@ class dcsr_csr_t: public csr_t {
697697
bool ebreakvs;
698698
bool ebreakvu;
699699
bool v;
700+
bool mprven;
700701
uint8_t cause;
701702
uint8_t ext_cause;
702703
bool cetrig;

riscv/mmu.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -486,7 +486,7 @@ class mmu_t
486486
{
487487
return proc != nullptr
488488
&& !(proc->state.mnstatus && !get_field(proc->state.mnstatus->read(), MNSTATUS_NMIE))
489-
&& !proc->state.debug_mode
489+
&& (!proc->state.debug_mode || get_field(proc->state.dcsr->read(), DCSR_MPRVEN))
490490
&& get_field(proc->state.mstatus->read(), MSTATUS_MPRV);
491491
}
492492

0 commit comments

Comments
 (0)