Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 22 additions & 1 deletion monitor/filter_exception_decoder.py
Original file line number Diff line number Diff line change
Expand Up @@ -237,6 +237,17 @@ class Esp32ExceptionDecoder(DeviceMonitorFilterBase):
0xf: "Store/AMO page fault",
})

# Standard RISC-V interrupt causes (MCAUSE with bit 31 set).
# Lower 31 bits of MCAUSE identify the interrupt source.
RISCV_INTERRUPT_CAUSES = types.MappingProxyType({
1: "Supervisor software interrupt",
3: "Machine software interrupt",
5: "Supervisor timer interrupt",
7: "Machine timer interrupt",
9: "Supervisor external interrupt",
11: "Machine external interrupt",
})

NON_CODE_REGISTERS = frozenset({
"EXCVADDR",
"MTVAL",
Expand Down Expand Up @@ -543,7 +554,17 @@ def get_xtensa_exception(self, code):
return None

def get_riscv_exception(self, code):
"""Return the human-readable name of a RISC-V MCAUSE value, or None."""
"""Return a human-readable description for a RISC-V MCAUSE value.

MCAUSE bit 31 distinguishes interrupts (1) from exceptions (0).
Returns a descriptive string, or None if the cause is unknown.
"""
if code & 0x80000000:
cause = code & 0x7FFFFFFF
desc = self.RISCV_INTERRUPT_CAUSES.get(cause)
if desc:
return "Interrupt: " + desc
return "Interrupt (cause %d)" % cause
return self.RISCV_EXCEPTIONS.get(code)

# -------------------------------------------------------------------------
Expand Down