| 1 |
60 |
zero_gravi |
<<<
|
| 2 |
|
|
:sectnums:
|
| 3 |
|
|
=== Control and Status Registers (CSRs)
|
| 4 |
|
|
|
| 5 |
|
|
The following table shows a summary of all available CSRs. The address field defines the CSR address for
|
| 6 |
|
|
the CSR access instructions. The *[ASM]* name can be used for (inline) assembly code and is directly
|
| 7 |
|
|
understood by the assembler/compiler. The *[C]* names are defined by the NEORV32 core library and can be
|
| 8 |
|
|
used as immediate in plain C code. The *R/W* column shows whether the CSR can be read and/or written.
|
| 9 |
|
|
The NEORV32-specific CSRs are mapped to the official "custom CSRs" CSR address space.
|
| 10 |
|
|
|
| 11 |
|
|
[IMPORTANT]
|
| 12 |
|
|
The CSRs, the CSR-related instructions as well as the complete exception/interrupt processing
|
| 13 |
|
|
system are only available when the `CPU_EXTENSION_RISCV_Zicsr` generic is _true_.
|
| 14 |
|
|
|
| 15 |
|
|
[IMPORTANT]
|
| 16 |
|
|
When trying to write to a read-only CSR (like the `time` CSR) or when trying to access a nonexistent
|
| 17 |
|
|
CSR or when trying to access a machine-mode CSR from less-privileged user-mode an
|
| 18 |
|
|
illegal instruction exception is raised.
|
| 19 |
|
|
|
| 20 |
|
|
[NOTE]
|
| 21 |
|
|
CSR reset value: Please note that most of the CSRs do *NOT* provide a dedicated reset. Hence,
|
| 22 |
|
|
these CSRs are not initialized by a hardware reset and keep an *UNDEFINED* value until they are
|
| 23 |
|
|
explicitly initialized by the software (normally, this is already done by the NEORV32-specific
|
| 24 |
|
|
`crt0.S` start-up code). For more information see section <<_cpu_hardware_reset>>.
|
| 25 |
|
|
|
| 26 |
|
|
**CSR Listing**
|
| 27 |
|
|
|
| 28 |
|
|
The description of each single CSR provides the following summary:
|
| 29 |
|
|
|
| 30 |
|
|
.CSR description
|
| 31 |
|
|
[cols="4,27,>7"]
|
| 32 |
|
|
[frame="topbot",grid="none"]
|
| 33 |
|
|
|======
|
| 34 |
|
|
| _Address_ | _Description_ | _ASM alias_
|
| 35 |
|
|
3+| Reset value: _CSR content after hardware reset_ (also see <<_cpu_hardware_reset>>)
|
| 36 |
|
|
3+| _Detailed description_
|
| 37 |
|
|
|======
|
| 38 |
|
|
|
| 39 |
|
|
.Not Implemented CSRs / CSR Bits
|
| 40 |
|
|
[IMPORTANT]
|
| 41 |
|
|
All CSR bits that are unused / not implemented / not shown are _hardwired to zero_. All CSRs that are not
|
| 42 |
|
|
implemented at all (and are not "disabled" using certain configuration generics) will trigger an exception on
|
| 43 |
|
|
access. The CSR that are implemented within the NEORV32 might cause an exception if they are disabled.
|
| 44 |
|
|
See the according CSR description for more information.
|
| 45 |
|
|
|
| 46 |
|
|
.Debug Mode CSRs
|
| 47 |
|
|
[IMPORTANT]
|
| 48 |
|
|
The _debug mode_ CSRs are not listed here since they are only accessible in debug mode and not during normal CPU operation.
|
| 49 |
|
|
See section <<_cpu_debug_mode_csrs>>.
|
| 50 |
|
|
|
| 51 |
|
|
|
| 52 |
|
|
<<<
|
| 53 |
|
|
// ####################################################################################################################
|
| 54 |
|
|
**CSR Listing Notes**
|
| 55 |
|
|
|
| 56 |
|
|
CSRs with the following notes ...
|
| 57 |
|
|
|
| 58 |
61 |
zero_gravi |
* `X`: _custom_ - have or are a custom CPU-specific extension (that is allowed by the RISC-V specs)
|
| 59 |
|
|
* `R`: _read-only_ - are read-only (in contrast to the originally specified r/w capability)
|
| 60 |
|
|
* `C`: _constrained_ - have a constrained compatibility, not all specified bits are implemented
|
| 61 |
60 |
zero_gravi |
|
| 62 |
|
|
.NEORV32 Control and Status Registers (CSRs)
|
| 63 |
61 |
zero_gravi |
[cols="<4,<7,<10,^3,<11,^3"]
|
| 64 |
60 |
zero_gravi |
[options="header"]
|
| 65 |
|
|
|=======================
|
| 66 |
61 |
zero_gravi |
| Address | Name [ASM] | Name [C] | R/W | Function | Note
|
| 67 |
60 |
zero_gravi |
6+^| **<<_floating_point_csrs>>**
|
| 68 |
|
|
| 0x001 | <<_fflags>> | _CSR_FFLAGS_ | r/w | Floating-point accrued exceptions |
|
| 69 |
|
|
| 0x002 | <<_frm>> | _CSR_FRM_ | r/w | Floating-point dynamic rounding mode |
|
| 70 |
|
|
| 0x003 | <<_fcsr>> | _CSR_FCSR_ | r/w | Floating-point control and status (`frm` + `fflags`) |
|
| 71 |
|
|
6+^| **<<_machine_trap_setup>>**
|
| 72 |
62 |
zero_gravi |
| 0x300 | <<_mstatus>> | _CSR_MSTATUS_ | r/w | Machine status register - low word | `C`
|
| 73 |
60 |
zero_gravi |
| 0x301 | <<_misa>> | _CSR_MISA_ | r/- | Machine CPU ISA and extensions | `R`
|
| 74 |
61 |
zero_gravi |
| 0x304 | <<_mie>> | _CSR_MIE_ | r/w | Machine interrupt enable register | `X`
|
| 75 |
60 |
zero_gravi |
| 0x305 | <<_mtvec>> | _CSR_MTVEC_ | r/w | Machine trap-handler base address (for ALL traps) |
|
| 76 |
61 |
zero_gravi |
| 0x306 | <<_mcounteren>> | _CSR_MCOUNTEREN_ | r/w | Machine counter-enable register | `C`
|
| 77 |
62 |
zero_gravi |
| 0x310 | <<_mstatush>> | _CSR_MSTATUSH_ | r/- | Machine status register - high word | `C`
|
| 78 |
60 |
zero_gravi |
6+^| **<<_machine_trap_handling>>**
|
| 79 |
|
|
| 0x340 | <<_mscratch>> | _CSR_MSCRATCH_ | r/w | Machine scratch register |
|
| 80 |
|
|
| 0x341 | <<_mepc>> | _CSR_MEPC_ | r/w | Machine exception program counter |
|
| 81 |
61 |
zero_gravi |
| 0x342 | <<_mcause>> | _CSR_MCAUSE_ | r/w | Machine trap cause | `X`
|
| 82 |
60 |
zero_gravi |
| 0x343 | <<_mtval>> | _CSR_MTVAL_ | r/- | Machine bad address or instruction | `R`
|
| 83 |
61 |
zero_gravi |
| 0x344 | <<_mip>> | _CSR_MIP_ | r/- | Machine interrupt pending register | `XR`
|
| 84 |
60 |
zero_gravi |
6+^| **<<_machine_physical_memory_protection>>**
|
| 85 |
61 |
zero_gravi |
| 0x3a0 .. 0x3af | <<_pmpcfg, `pmpcfg0`>> .. <<_pmpcfg, `pmpcfg15`>> | _CSR_PMPCFG0_ .. _CSR_PMPCFG15_ | r/w | Physical memory protection config. for region 0..63 | `C`
|
| 86 |
60 |
zero_gravi |
| 0x3b0 .. 0x3ef | <<_pmpaddr, `pmpaddr0`>> .. <<_pmpaddr, `pmpaddr63`>> | _CSR_PMPADDR0_ .. _CSR_PMPADDR63_ | r/w | Physical memory protection addr. register region 0..63 |
|
| 87 |
|
|
6+^| **<<_machine_counters_and_timers>>**
|
| 88 |
61 |
zero_gravi |
| 0xb00 | <<_mcycleh, `mcycle`>> | _CSR_MCYCLE_ | r/w | Machine cycle counter low word |
|
| 89 |
62 |
zero_gravi |
| 0xb02 | <<_minstreth, `minstret`>> | _CSR_MINSTRET_ | r/w | Machine instruction-retired counter low word |
|
| 90 |
61 |
zero_gravi |
| 0xb80 | <<_mcycleh>> | _CSR_MCYCLE_ | r/w | Machine cycle counter high word |
|
| 91 |
|
|
| 0xb82 | <<_minstreth>> | _CSR_MINSTRET_ | r/w | Machine instruction-retired counter high word |
|
| 92 |
|
|
| 0xc00 | <<_cycleh, `cycle`>> | _CSR_CYCLE_ | r/- | Cycle counter low word |
|
| 93 |
|
|
| 0xc01 | <<_timeh, `time`>> | _CSR_TIME_ | r/- | System time (from MTIME) low word |
|
| 94 |
60 |
zero_gravi |
| 0xc02 | <<_instreth, `instret`>> | _CSR_INSTRET_ | r/- | Instruction-retired counter low word |
|
| 95 |
61 |
zero_gravi |
| 0xc80 | <<_cycleh>> | _CSR_CYCLEH_ | r/- | Cycle counter high word |
|
| 96 |
|
|
| 0xc81 | <<_timeh>> | _CSR_TIMEH_ | r/- | System time (from MTIME) high word |
|
| 97 |
|
|
| 0xc82 | <<_instreth>> | _CSR_INSTRETH_ | r/- | Instruction-retired counter high word |
|
| 98 |
60 |
zero_gravi |
6+^| **<<_hardware_performance_monitors_hpm>>**
|
| 99 |
61 |
zero_gravi |
| 0x323 .. 0x33f | <<_mhpmevent, `mhpmevent3`>> .. <<_mhpmevent, `mhpmevent31`>> | _CSR_MHPMEVENT3_ .. _CSR_MHPMEVENT31_ | r/w | Machine performance-monitoring event selector 3..31 | `X`
|
| 100 |
60 |
zero_gravi |
| 0xb03 .. 0xb1f | <<_mhpmcounterh, `mhpmcounter3`>> .. <<_mhpmcounterh, `mhpmcounter31`>> | _CSR_MHPMCOUNTER3_ .. _CSR_MHPMCOUNTER31_ | r/w | Machine performance-monitoring counter 3..31 low word |
|
| 101 |
|
|
| 0xb83 .. 0xb9f | <<_mhpmcounterh, `mhpmcounter3h`>> .. <<_mhpmcounterh, `mhpmcounter31h`>> | _CSR_MHPMCOUNTER3H_ .. _CSR_MHPMCOUNTER31H_ | r/w | Machine performance-monitoring counter 3..31 high word |
|
| 102 |
|
|
6+^| **<<_machine_counter_setup>>**
|
| 103 |
|
|
| 0x320 | <<_mcountinhibit>> | _CSR_MCOUNTINHIBIT_ | r/w | Machine counter-enable register |
|
| 104 |
|
|
6+^| **<<_machine_information_registers>>**
|
| 105 |
62 |
zero_gravi |
| 0xf11 | <<_mvendorid>> | _CSR_MVENDORID_ | r/- | Vendor ID |
|
| 106 |
|
|
| 0xf12 | <<_marchid>> | _CSR_MARCHID_ | r/- | Architecture ID |
|
| 107 |
|
|
| 0xf13 | <<_mimpid>> | _CSR_MIMPID_ | r/- | Machine implementation ID / version |
|
| 108 |
|
|
| 0xf14 | <<_mhartid>> | _CSR_MHARTID_ | r/- | Machine thread ID |
|
| 109 |
|
|
| 0xf15 | <<_mconfigptr>> | _CSR_MCONFIGPTR_ | r/- | Machine configuration pointer register |
|
| 110 |
60 |
zero_gravi |
6+^| **<<_neorv32_specific_custom_csrs>>**
|
| 111 |
|
|
| 0xfc0 | <<_mzext>> | _CSR_MZEXT_ | r/- | Available `Z*` CPU extensions |
|
| 112 |
|
|
|=======================
|
| 113 |
|
|
|
| 114 |
|
|
|
| 115 |
|
|
|
| 116 |
|
|
<<<
|
| 117 |
|
|
// ####################################################################################################################
|
| 118 |
|
|
:sectnums:
|
| 119 |
|
|
==== Floating-Point CSRs
|
| 120 |
|
|
|
| 121 |
|
|
These CSRs are available if the `Zfinx` extensions is enabled (`CPU_EXTENSION_RISCV_Zfinx` is _true_).
|
| 122 |
|
|
Otherwise any access to the floating-point CSRs will raise an illegal instruction exception.
|
| 123 |
|
|
|
| 124 |
|
|
|
| 125 |
|
|
:sectnums!:
|
| 126 |
|
|
===== **`fflags`**
|
| 127 |
|
|
|
| 128 |
|
|
[cols="4,27,>7"]
|
| 129 |
|
|
[frame="topbot",grid="none"]
|
| 130 |
|
|
|======
|
| 131 |
|
|
| 0x001 | **Floating-point accrued exceptions** | `fflags`
|
| 132 |
|
|
3+| Reset value: _UNDEFINED_
|
| 133 |
|
|
3+| The `fflags` CSR is compatible to the RISC-V specifications. It shows the accrued ("accumulated")
|
| 134 |
|
|
exception flags in the lowest 5 bits. This CSR is only available if a floating-point CPU extension is enabled.
|
| 135 |
|
|
See the RISC-V ISA spec for more information.
|
| 136 |
|
|
|======
|
| 137 |
|
|
|
| 138 |
|
|
|
| 139 |
|
|
:sectnums!:
|
| 140 |
|
|
===== **`frm`**
|
| 141 |
|
|
|
| 142 |
|
|
[cols="4,27,>7"]
|
| 143 |
|
|
[frame="topbot",grid="none"]
|
| 144 |
|
|
|======
|
| 145 |
|
|
| 0x002 | **Floating-point dynamic rounding mode** | `frm`
|
| 146 |
|
|
3+| Reset value: _UNDEFINED_
|
| 147 |
|
|
3+| The `frm` CSR is compatible to the RISC-V specifications and is used to configure the rounding modes using
|
| 148 |
|
|
the lowest 3 bits. This CSR is only available if a floating-point CPU extension is enabled. See the RISC-V
|
| 149 |
|
|
ISA spec for more information.
|
| 150 |
|
|
|======
|
| 151 |
|
|
|
| 152 |
|
|
|
| 153 |
|
|
:sectnums!:
|
| 154 |
|
|
===== **`fcsr`**
|
| 155 |
|
|
|
| 156 |
|
|
[cols="4,27,>7"]
|
| 157 |
|
|
[frame="topbot",grid="none"]
|
| 158 |
|
|
|======
|
| 159 |
|
|
| 0x003 | **Floating-point control and status register** | `fcsr`
|
| 160 |
|
|
3+| Reset value: _UNDEFINED_
|
| 161 |
|
|
3+| The `fcsr` CSR is compatible to the RISC-V specifications. It provides combined read/write access to the
|
| 162 |
|
|
`fflags` and `frm` CSRs. This CSR is only available if a floating-point CPU extension is enabled. See the
|
| 163 |
|
|
RISC-V ISA spec for more information.
|
| 164 |
|
|
|======
|
| 165 |
|
|
|
| 166 |
|
|
|
| 167 |
|
|
<<<
|
| 168 |
|
|
// ####################################################################################################################
|
| 169 |
|
|
:sectnums:
|
| 170 |
|
|
==== Machine Trap Setup
|
| 171 |
|
|
|
| 172 |
|
|
:sectnums!:
|
| 173 |
|
|
===== **`mstatus`**
|
| 174 |
|
|
|
| 175 |
|
|
[cols="4,27,>7"]
|
| 176 |
|
|
[frame="topbot",grid="none"]
|
| 177 |
|
|
|======
|
| 178 |
61 |
zero_gravi |
| 0x300 | **Machine status register** | `mstatus`
|
| 179 |
|
|
3+| Reset value: _0x00000000_
|
| 180 |
60 |
zero_gravi |
3+| The `mstatus` CSR is compatible to the RISC-V specifications. It shows the CPU's current execution state.
|
| 181 |
|
|
The following bits are implemented (all remaining bits are always zero and are read-only).
|
| 182 |
|
|
|======
|
| 183 |
|
|
|
| 184 |
|
|
.Machine status register
|
| 185 |
|
|
[cols="^1,<3,^1,<5"]
|
| 186 |
|
|
[options="header",grid="rows"]
|
| 187 |
|
|
|=======================
|
| 188 |
|
|
| Bit | Name [C] | R/W | Function
|
| 189 |
62 |
zero_gravi |
| 31 | _CSR_MSTATUS_SD_ | r/- | Read-only bit that is set if the FS field is not all-zero (state _OFF_)
|
| 190 |
|
|
| 21 | _CSR_MSTATUS_TW_ | r/w | Timeout wait: raise illegal instruction exception if `WFI` instruction is executed outside of M-mode when set
|
| 191 |
|
|
| 14:13 | _CSR_MSTATUS_FS_H_ : _CSR_MSTATUS_FS_L_ | r/w | Floating-point extension state; `00` = _OFF_, `11` = _DIRTY_; writing any other value will
|
| 192 |
|
|
always set _DIRTY_; if `FS` is _off_ all FPU instructions and FPU CSR access will raise an illegal instruction exception; these status bits are hardwired
|
| 193 |
|
|
to zero if no FPU is present (_CPU_MZEXT_ZFINX_ = false)
|
| 194 |
60 |
zero_gravi |
| 12:11 | _CSR_MSTATUS_MPP_H_ : _CSR_MSTATUS_MPP_L_ | r/w | Previous machine privilege level, 11 = machine (M) level, 00 = user (U) level
|
| 195 |
|
|
| 7 | _CSR_MSTATUS_MPIE_ | r/w | Previous machine global interrupt enable flag state
|
| 196 |
61 |
zero_gravi |
| 3 | _CSR_MSTATUS_MIE_ | r/w | Machine global interrupt enable flag
|
| 197 |
60 |
zero_gravi |
|=======================
|
| 198 |
|
|
|
| 199 |
|
|
When entering an exception/interrupt, the `MIE` flag is copied to `MPIE` and cleared afterwards. When leaving
|
| 200 |
|
|
the exception/interrupt (via the `mret` instruction), `MPIE` is copied back to `MIE`.
|
| 201 |
|
|
|
| 202 |
|
|
|
| 203 |
|
|
:sectnums!:
|
| 204 |
|
|
===== **`misa`**
|
| 205 |
|
|
|
| 206 |
|
|
[cols="4,27,>7"]
|
| 207 |
|
|
[frame="topbot",grid="none"]
|
| 208 |
|
|
|======
|
| 209 |
|
|
| 0x301 | **ISA and extensions** | `misa`
|
| 210 |
|
|
3+| Reset value: _configuration dependant_
|
| 211 |
|
|
3+| The `misa` CSR gives information about the actual CPU features. The lowest 26 bits show the implemented
|
| 212 |
|
|
CPU extensions. The following bits are implemented (all remaining bits are always zero and are read-only).
|
| 213 |
|
|
|======
|
| 214 |
|
|
|
| 215 |
|
|
[IMPORTANT]
|
| 216 |
|
|
The `misa` CSR is not fully RISC-V-compatible as it is read-only. Hence, implemented CPU
|
| 217 |
|
|
extensions cannot be switch on/off during runtime. For compatibility reasons any write access to this
|
| 218 |
|
|
CSR is simply ignored and will NOT cause an illegal instruction exception.
|
| 219 |
|
|
|
| 220 |
|
|
.Machine ISA and extension register
|
| 221 |
|
|
[cols="^1,<3,^1,<5"]
|
| 222 |
|
|
[options="header",grid="rows"]
|
| 223 |
|
|
|=======================
|
| 224 |
|
|
| Bit | Name [C] | R/W | Function
|
| 225 |
|
|
| 31:30 | _CSR_MISA_MXL_HI_EXT_ : _CSR_MISA_MXL_LO_EXT_ | r/- | 32-bit architecture indicator (always _01_)
|
| 226 |
|
|
| 23 | _CSR_MISA_X_EXT_ | r/- | `X` extension bit is always set to indicate custom non-standard extensions
|
| 227 |
|
|
| 20 | _CSR_MISA_U_EXT_ | r/- | `U` CPU extension (user mode) available, set when _CPU_EXTENSION_RISCV_U_ enabled
|
| 228 |
|
|
| 12 | _CSR_MISA_M_EXT_ | r/- | `M` CPU extension (mul/div) available, set when _CPU_EXTENSION_RISCV_M_ enabled
|
| 229 |
|
|
| 8 | _CSR_MISA_I_EXT_ | r/- | `I` CPU base ISA, cleared when _CPU_EXTENSION_RISCV_E_ enabled
|
| 230 |
|
|
| 4 | _CSR_MISA_E_EXT_ | r/- | `E` CPU extension (embedded) available, set when _CPU_EXTENSION_RISCV_E_ enabled
|
| 231 |
|
|
| 2 | _CSR_MISA_C_EXT_ | r/- | `C` CPU extension (compressed instruction) available, set when _CPU_EXTENSION_RISCV_C_ enabled
|
| 232 |
|
|
| 0 | _CSR_MISA_A_EXT_ | r/- | `A` CPU extension (atomic memory access) available, set when _CPU_EXTENSION_RISCV_A_ enabled
|
| 233 |
|
|
|=======================
|
| 234 |
|
|
|
| 235 |
|
|
[TIP]
|
| 236 |
61 |
zero_gravi |
Information regarding the implemented RISC-V `Z*` _sub-extensions_ (like `Zicsr` or `Zfinx`) can be found in the <<_mzext>> CSR.
|
| 237 |
60 |
zero_gravi |
|
| 238 |
|
|
|
| 239 |
|
|
:sectnums!:
|
| 240 |
|
|
===== **`mie`**
|
| 241 |
|
|
|
| 242 |
|
|
[cols="4,27,>7"]
|
| 243 |
|
|
[frame="topbot",grid="none"]
|
| 244 |
|
|
|======
|
| 245 |
|
|
| 0x304 | **Machine interrupt-enable register** | `mie`
|
| 246 |
|
|
3+| Reset value: _UNDEFINED_
|
| 247 |
|
|
3+| The `mie` CSR is compatible to the RISC-V specifications and features custom extensions for the fast
|
| 248 |
|
|
interrupt channels. It is used to enabled specific interrupts sources. Please note that interrupts also have to be
|
| 249 |
|
|
globally enabled via the `CSR_MSTATUS_MIE` flag of the `mstatus` CSR. The following bits are implemented
|
| 250 |
|
|
(all remaining bits are always zero and are read-only):
|
| 251 |
|
|
|======
|
| 252 |
|
|
|
| 253 |
|
|
.Machine ISA and extension register
|
| 254 |
|
|
[cols="^1,<3,^1,<5"]
|
| 255 |
|
|
[options="header",grid="rows"]
|
| 256 |
|
|
|=======================
|
| 257 |
|
|
| Bit | Name [C] | R/W | Function
|
| 258 |
|
|
| 31:16 | _CSR_MIE_FIRQ15E_ : _CSR_MIE_FIRQ0E_ | r/w | Fast interrupt channel 15..0 enable
|
| 259 |
|
|
| 11 | _CSR_MIE_MEIE_ | r/w | Machine _external_ interrupt enable
|
| 260 |
|
|
| 7 | _CSR_MIE_MTIE_ | r/w | Machine _timer_ interrupt enable (from _MTIME_)
|
| 261 |
|
|
| 3 | _CSR_MIE_MSIE_ | r/w | Machine _software_ interrupt enable
|
| 262 |
|
|
|=======================
|
| 263 |
|
|
|
| 264 |
|
|
|
| 265 |
|
|
:sectnums!:
|
| 266 |
|
|
===== **`mtvec`**
|
| 267 |
|
|
|
| 268 |
|
|
[cols="4,27,>7"]
|
| 269 |
|
|
[frame="topbot",grid="none"]
|
| 270 |
|
|
|======
|
| 271 |
|
|
| 0x305 | **Machine trap-handler base address** | `mtvec`
|
| 272 |
|
|
3+| Reset value: _UNDEFINED_
|
| 273 |
|
|
3+| The `mtvec` CSR is compatible to the RISC-V specifications. It stores the base address for ALL machine
|
| 274 |
|
|
traps. Thus, it defines the main entry point for exception/interrupt handling regardless of the actual trap
|
| 275 |
|
|
source. The lowest two bits of this register are always zero and cannot be modified (= fixed address mode).
|
| 276 |
|
|
|======
|
| 277 |
|
|
|
| 278 |
|
|
.Machine trap-handler base address
|
| 279 |
|
|
[cols="^1,^1,<8"]
|
| 280 |
|
|
[options="header",grid="rows"]
|
| 281 |
|
|
|=======================
|
| 282 |
|
|
| Bit | R/W | Function
|
| 283 |
|
|
| 31:2 | r/w | 4-byte aligned base address of trap base handler
|
| 284 |
|
|
| 1:0 | r/- | Always zero
|
| 285 |
|
|
|=======================
|
| 286 |
|
|
|
| 287 |
|
|
|
| 288 |
|
|
:sectnums!:
|
| 289 |
|
|
===== **`mcounteren`**
|
| 290 |
|
|
|
| 291 |
|
|
[cols="4,27,>7"]
|
| 292 |
|
|
[frame="topbot",grid="none"]
|
| 293 |
|
|
|======
|
| 294 |
|
|
| 0x306 | **Machine counter enable** | `mcounteren`
|
| 295 |
|
|
3+| Reset value: _UNDEFINED_
|
| 296 |
|
|
3+| The `mcounteren` CSR is compatible to the RISC-V specifications. The bits of this CSR define which
|
| 297 |
|
|
counter/timer CSR can be accessed (read) from code running in a less-privileged modes. For example,
|
| 298 |
61 |
zero_gravi |
if user-level code tries to read from a counter/timer CSR without enabled access, an illegal instruction
|
| 299 |
|
|
exception is raised. If user mode in not implemented (_CPU_EXTENSION_RISCV_U_ = _false_) all bits of the
|
| 300 |
60 |
zero_gravi |
`mcounteren` CSR are tied to zero.
|
| 301 |
|
|
|======
|
| 302 |
|
|
|
| 303 |
|
|
.Machine counter enable register
|
| 304 |
|
|
[cols="^1,<3,^1,<5"]
|
| 305 |
|
|
[options="header",grid="rows"]
|
| 306 |
|
|
|=======================
|
| 307 |
|
|
| Bit | Name [C] | R/W | Function
|
| 308 |
62 |
zero_gravi |
| 31:16 | `0` | r/- | Always zero: user-level code is **not** allowed to read HPM counters
|
| 309 |
60 |
zero_gravi |
| 2 | _CSR_MCOUNTEREN_IR_ | r/w | User-level code is allowed to read `cycle[h]` CSRs when set
|
| 310 |
|
|
| 1 | _CSR_MCOUNTEREN_TM_ | r/w | User-level code is allowed to read `time[h]` CSRs when set
|
| 311 |
|
|
| 0 | _CSR_MCOUNTEREN_CY_ | r/w | User-level code is allowed to read `instret[h]` CSRs when set
|
| 312 |
|
|
|=======================
|
| 313 |
|
|
|
| 314 |
|
|
|
| 315 |
62 |
zero_gravi |
:sectnums!:
|
| 316 |
|
|
===== **`mstatush`**
|
| 317 |
|
|
|
| 318 |
|
|
[cols="4,27,>7"]
|
| 319 |
|
|
[frame="topbot",grid="none"]
|
| 320 |
|
|
|======
|
| 321 |
|
|
| 0x310 | **Machine status register - high word** | `mstatush`
|
| 322 |
|
|
3+| Reset value: _0x00000000_
|
| 323 |
|
|
3+| The `mstatush` CSR is compatible to the RISC-V specifications. In combination with <<_mstatus>> it shows additional
|
| 324 |
|
|
execution state information. The NEORV32 `mstatush` CSR is read-only and all bits are hardwired to zero.
|
| 325 |
|
|
|======
|
| 326 |
|
|
|
| 327 |
|
|
[NOTE]
|
| 328 |
|
|
The NEORV32 `mstatush` CSR is not a physical register. All write access are ignored and all read accesses will always
|
| 329 |
|
|
return zero. However, any access will not raise an illegal instruction exception. The CSR address is implemented
|
| 330 |
|
|
in order to comply with the RISC-V privilege architecture specs.
|
| 331 |
|
|
|
| 332 |
|
|
|
| 333 |
|
|
|
| 334 |
60 |
zero_gravi |
<<<
|
| 335 |
|
|
// ####################################################################################################################
|
| 336 |
|
|
:sectnums:
|
| 337 |
|
|
==== Machine Trap Handling
|
| 338 |
|
|
|
| 339 |
|
|
:sectnums!:
|
| 340 |
|
|
===== **`mscratch`**
|
| 341 |
|
|
|
| 342 |
|
|
[cols="4,27,>7"]
|
| 343 |
|
|
[frame="topbot",grid="none"]
|
| 344 |
|
|
|======
|
| 345 |
|
|
| 0x340 | **Scratch register for machine trap handlers** | `mscratch`
|
| 346 |
|
|
3+| Reset value: _UNDEFINED_
|
| 347 |
|
|
3+| The `mscratch` CSR is compatible to the RISC-V specifications. It is a general purpose scratch register that
|
| 348 |
|
|
can be used by the exception/interrupt handler. The content pf this register after reset is undefined.
|
| 349 |
|
|
|======
|
| 350 |
|
|
|
| 351 |
|
|
:sectnums!:
|
| 352 |
|
|
===== **`mepc`**
|
| 353 |
|
|
|
| 354 |
|
|
[cols="4,27,>7"]
|
| 355 |
|
|
[frame="topbot",grid="none"]
|
| 356 |
|
|
|======
|
| 357 |
|
|
| 0x341 | **Machine exception program counter** | `mepc`
|
| 358 |
|
|
3+| Reset value: _UNDEFINED_
|
| 359 |
|
|
3+| The `mepc` CSR is compatible to the RISC-V specifications. For exceptions (like an illegal instruction) this
|
| 360 |
|
|
register provides the address of the exception-causing instruction. For Interrupt (like a machine timer
|
| 361 |
|
|
interrupt) this register provides the address of the next not-yet-executed instruction.
|
| 362 |
|
|
|======
|
| 363 |
|
|
|
| 364 |
|
|
:sectnums!:
|
| 365 |
|
|
===== **`mcause`**
|
| 366 |
|
|
|
| 367 |
|
|
[cols="4,27,>7"]
|
| 368 |
|
|
[frame="topbot",grid="none"]
|
| 369 |
|
|
|======
|
| 370 |
|
|
| 0x342 | **Machine trap cause** | `mcause`
|
| 371 |
|
|
3+| Reset value: _UNDEFINED_
|
| 372 |
|
|
3+| The `mcause` CSR is compatible to the RISC-V specifications. It show the cause ID for a taken exception.
|
| 373 |
|
|
|======
|
| 374 |
|
|
|
| 375 |
|
|
.Machine trap cause register
|
| 376 |
|
|
[cols="^1,^1,<8"]
|
| 377 |
|
|
[options="header",grid="rows"]
|
| 378 |
|
|
|=======================
|
| 379 |
|
|
| Bit | R/W | Function
|
| 380 |
|
|
| 31 | r/w | `1` if the trap is caused by an interrupt (`0` if the trap is caused by an exception)
|
| 381 |
|
|
| 30:5 | r/- | _Reserved_, read as zero
|
| 382 |
|
|
| 4:0 | r/w | Trap ID, see <<_neorv32_trap_listing>>
|
| 383 |
|
|
|=======================
|
| 384 |
|
|
|
| 385 |
|
|
:sectnums!:
|
| 386 |
|
|
===== **`mtval`**
|
| 387 |
|
|
|
| 388 |
|
|
[cols="4,27,>7"]
|
| 389 |
|
|
[frame="topbot",grid="none"]
|
| 390 |
|
|
|======
|
| 391 |
|
|
| 0x343 | **Machine bad address or instruction** | `mtval`
|
| 392 |
|
|
3+| Reset value: _UNDEFINED_
|
| 393 |
|
|
3+| The `mtval` CSR is compatible to the RISC-V specifications. When a trap is triggered, the CSR shows either
|
| 394 |
|
|
the faulting address (for misaligned/faulting load/stores/fetch) or the faulting instruction itself (for illegal
|
| 395 |
|
|
instructions). For interrupts the CSR is set to zero.
|
| 396 |
|
|
|======
|
| 397 |
|
|
|
| 398 |
|
|
.Machine bad address or instruction register
|
| 399 |
|
|
[cols="^5,^5"]
|
| 400 |
|
|
[options="header",grid="rows"]
|
| 401 |
|
|
|=======================
|
| 402 |
|
|
| Trap cause | `mtval` content
|
| 403 |
|
|
| misaligned instruction fetch address or instruction fetch access fault | address of faulting instruction fetch
|
| 404 |
|
|
| breakpoint | program counter (= address) of faulting instruction itself
|
| 405 |
|
|
| misaligned load address, load access fault, misaligned store address or store access fault | program counter (= address) of faulting instruction itself
|
| 406 |
|
|
| illegal instruction | actual instruction word of faulting instruction
|
| 407 |
|
|
| anything else including interrupts | _0x00000000_ (always zero)
|
| 408 |
|
|
|=======================
|
| 409 |
|
|
|
| 410 |
|
|
[IMPORTAN]
|
| 411 |
|
|
The NEORV32 `mtval` CSR is read-only. A write access will raise an illegal instruction exception.
|
| 412 |
|
|
|
| 413 |
|
|
:sectnums!:
|
| 414 |
|
|
===== **`mip`**
|
| 415 |
|
|
|
| 416 |
|
|
[cols="4,27,>7"]
|
| 417 |
|
|
[frame="topbot",grid="none"]
|
| 418 |
|
|
|======
|
| 419 |
|
|
| 0x344 | **Machine interrupt Pending** | `mip`
|
| 420 |
|
|
3+| Reset value: _0x00000000_
|
| 421 |
|
|
3+| The `mip` CSR is _partly_ compatible to the RISC-V specifications and also provides custom extensions. It shows currently pending interrupts. Since this register is
|
| 422 |
|
|
read-only, pending interrupt can only be cleared by disabling and re-enabling the according `mie` CSr bit. Writing to this CSR will
|
| 423 |
|
|
raise an illegal instruction exception. The following CSR bits are implemented (all remaining bits are always zero and are read-only).
|
| 424 |
|
|
|======
|
| 425 |
|
|
|
| 426 |
|
|
.Machine interrupt pending register
|
| 427 |
|
|
[cols="^1,<3,^1,<5"]
|
| 428 |
|
|
[options="header",grid="rows"]
|
| 429 |
|
|
|=======================
|
| 430 |
|
|
| Bit | Name [C] | R/W | Function
|
| 431 |
|
|
| 31:16 | _CSR_MIP_FIRQ15P_ : _CSR_MIP_FIRQ0P_ | r/- | fast interrupt channel 15..0 pending
|
| 432 |
|
|
| 11 | _CSR_MIP_MEIP_ | r/- | machine _external_ interrupt pending
|
| 433 |
|
|
| 7 | _CSR_MIP_MTIP_ | r/- | machine _timer_ interrupt pending
|
| 434 |
|
|
| 3 | _CSR_MIP_MSIP_ | r/- | machine _software_ interrupt pending
|
| 435 |
|
|
|=======================
|
| 436 |
|
|
|
| 437 |
|
|
|
| 438 |
|
|
<<<
|
| 439 |
|
|
// ####################################################################################################################
|
| 440 |
|
|
:sectnums:
|
| 441 |
|
|
==== Machine Physical Memory Protection
|
| 442 |
|
|
|
| 443 |
|
|
The available physical memory protection logic is configured via the _PMP_NUM_REGIONS_ and
|
| 444 |
|
|
_PMP_MIN_GRANULARITY_ top entity generics. _PMP_NUM_REGIONS_ defines the number of implemented
|
| 445 |
|
|
protection regions and thus, the availability of the according `pmpcfg*` and `pmpaddr*` CSRs.
|
| 446 |
|
|
|
| 447 |
|
|
[TIP]
|
| 448 |
|
|
If trying to access an PMP-related CSR beyond _PMP_NUM_REGIONS_ **no illegal instruction
|
| 449 |
|
|
exception** is triggered. The according CSRs are read-only (writes are ignored) and always return zero.
|
| 450 |
|
|
|
| 451 |
|
|
[IMPORTANT]
|
| 452 |
|
|
The RISC-V-compatible NEORV32 physical memory protection only implements the _NAPOT_
|
| 453 |
|
|
(naturally aligned power-of-two region) mode with a minimal region granularity of 8 bytes.
|
| 454 |
|
|
|
| 455 |
|
|
|
| 456 |
|
|
:sectnums!:
|
| 457 |
|
|
===== **`pmpcfg`**
|
| 458 |
|
|
|
| 459 |
|
|
[cols="4,27,>7"]
|
| 460 |
|
|
[frame="topbot",grid="none"]
|
| 461 |
|
|
|======
|
| 462 |
|
|
| 0x3a0 - 0x3af| **Physical memory protection configuration registers** | `pmpcfg0` - `pmpcfg15`
|
| 463 |
|
|
3+| Reset value: _0x00000000_
|
| 464 |
|
|
3+| The `pmpcfg*` CSRs are compatible to the RISC-V specifications. They are used to configure the protected
|
| 465 |
|
|
regions, where each `pmpcfg*` CSR provides configuration bits for four regions. The following bits (for the
|
| 466 |
|
|
first PMP configuration entry) are implemented (all remaining bits are always zero and are read-only):
|
| 467 |
|
|
|======
|
| 468 |
|
|
|
| 469 |
|
|
.Physical memory protection configuration register entry
|
| 470 |
|
|
[cols="^1,^3,^1,<11"]
|
| 471 |
|
|
[options="header",grid="rows"]
|
| 472 |
|
|
|=======================
|
| 473 |
|
|
| Bit | RISC-V name | R/W | Function
|
| 474 |
|
|
| 7 | _L_ | r/w | lock bit, can be set – but not be cleared again (only via CPU reset)
|
| 475 |
|
|
| 6:5 | - | r/- | reserved, read as zero
|
| 476 |
|
|
| 4:3 | _A_ | r/w | mode configuration; only OFF (`00`) and NAPOT (`11`) are supported
|
| 477 |
|
|
| 2 | _X_ | r/w | execute permission
|
| 478 |
|
|
| 1 | _W_ | r/w | write permission
|
| 479 |
|
|
| 0 | _R_ | r/w | read permission
|
| 480 |
|
|
|=======================
|
| 481 |
|
|
|
| 482 |
|
|
|
| 483 |
|
|
:sectnums!:
|
| 484 |
|
|
===== **`pmpaddr`**
|
| 485 |
|
|
|
| 486 |
|
|
[cols="4,27,>7"]
|
| 487 |
|
|
[frame="topbot",grid="none"]
|
| 488 |
|
|
|======
|
| 489 |
|
|
| 0x3b0 - 0x3ef| **Physical memory protection configuration registers** | `pmpaddr0` - `pmpaddr63`
|
| 490 |
|
|
3+| Reset value: _UNDEFINED_
|
| 491 |
|
|
3+| The `pmpaddr*` CSRs are compatible to the RISC-V specifications. They are used to configure the base
|
| 492 |
|
|
address and the region size.
|
| 493 |
|
|
|======
|
| 494 |
|
|
|
| 495 |
|
|
[NOTE]
|
| 496 |
|
|
When configuring PMP make sure to set `pmpaddr*` before activating the according region via
|
| 497 |
|
|
`pmpcfg*`. When changing the PMP configuration, deactivate the according region via `pmpcfg*`
|
| 498 |
|
|
before modifying `pmpaddr*`.
|
| 499 |
|
|
|
| 500 |
|
|
|
| 501 |
|
|
<<<
|
| 502 |
|
|
// ####################################################################################################################
|
| 503 |
|
|
:sectnums:
|
| 504 |
|
|
==== (Machine) Counters and Timers
|
| 505 |
|
|
|
| 506 |
|
|
[IMPORTANT]
|
| 507 |
61 |
zero_gravi |
The <<_cpu_cnt_width>> generic defines the total size of the CPU's <<_cycleh>> and <<_instreth>>
|
| 508 |
|
|
/ <<_mcycleh>> and <<_minstreth>>
|
| 509 |
60 |
zero_gravi |
counter CSRs (low and high words combined); the time CSRs are not affected by this generic. Any
|
| 510 |
61 |
zero_gravi |
configuration with <<_cpu_cnt_width>> less than 64 is not RISC-V compliant.
|
| 511 |
60 |
zero_gravi |
|
| 512 |
|
|
[IMPORTANT]
|
| 513 |
|
|
If _CPU_CNT_WIDTH_ is less than 64 (the default value) and greater than or equal 32, the according
|
| 514 |
|
|
MSBs of `[m]cycleh` and `[m]instreth` are read-only and always read as zero. This configuration
|
| 515 |
61 |
zero_gravi |
will also set the _ZXSCNT_ flag in the <<_mzext>> CSR. +
|
| 516 |
|
|
+
|
| 517 |
60 |
zero_gravi |
If _CPU_CNT_WIDTH_ is less than 32 and greater than 0, the `[m]cycleh` and `[m]instreth` do not
|
| 518 |
|
|
exist and any access will raise an illegal instruction exception. Furthermore, the according MSBs of
|
| 519 |
|
|
`[m]cycle` and `[m]instret` are read-only and always read as zero. This configuration will also
|
| 520 |
61 |
zero_gravi |
set the _ZXSCNT_ flag in the <<_mzext>> CSR. +
|
| 521 |
|
|
+
|
| 522 |
|
|
If _CPU_CNT_WIDTH_ is 0, <<_cycleh>> and <<_instreth>> / <<_mcycleh>> and <<_minstreth>> do not
|
| 523 |
60 |
zero_gravi |
exist and any access will raise an illegal instruction exception. This configuration will also set the
|
| 524 |
61 |
zero_gravi |
_ZXNOCNT_ flag in the <<_mzext>> CSR.
|
| 525 |
60 |
zero_gravi |
|
| 526 |
|
|
|
| 527 |
|
|
:sectnums!:
|
| 528 |
|
|
===== **`cycle[h]`**
|
| 529 |
|
|
|
| 530 |
|
|
[cols="4,27,>7"]
|
| 531 |
|
|
[frame="topbot",grid="none"]
|
| 532 |
|
|
|======
|
| 533 |
|
|
| 0xc00 | **Cycle counter - low word** | `cycle`
|
| 534 |
|
|
| 0xc80 | **Cycle counter - high word** | `cycleh`
|
| 535 |
|
|
3+| Reset value: _UNDEFINED_
|
| 536 |
|
|
3+| The `cycle[h]` CSR is compatible to the RISC-V specifications. It shows the lower/upper 32-bit of the 64-bit cycle
|
| 537 |
|
|
counter. The `cycle[h]` CSR is a read-only shadowed copy of the `mcycle[h]` CSR.
|
| 538 |
|
|
|======
|
| 539 |
|
|
|
| 540 |
|
|
|
| 541 |
|
|
:sectnums!:
|
| 542 |
|
|
===== **`time[h]`**
|
| 543 |
|
|
|
| 544 |
|
|
[cols="4,27,>7"]
|
| 545 |
|
|
[frame="topbot",grid="none"]
|
| 546 |
|
|
|======
|
| 547 |
|
|
| 0xc01 | **System time - low word** | `time`
|
| 548 |
|
|
| 0xc81 | **System time - high word** | `timeh`
|
| 549 |
|
|
3+| Reset value: _UNDEFINED_
|
| 550 |
|
|
3+| The `time[h]` CSR is compatible to the RISC-V specifications. It shows the lower/upper 32-bit of the 64-bit system
|
| 551 |
|
|
time. The system time is either generated by the processor-internal _MTIME_ system timer unit (if _IO_MTIME_EN_ = _true_) or can be provided by an
|
| 552 |
|
|
external timer unit via the processor's `mtime_i` signal (if _IO_MTIME_EN_ = _false_).
|
| 553 |
|
|
CSR is read-only. Change the system time via the _MTIME_ unit.
|
| 554 |
|
|
|======
|
| 555 |
|
|
|
| 556 |
|
|
|
| 557 |
|
|
:sectnums!:
|
| 558 |
|
|
===== **`instret[h]`**
|
| 559 |
|
|
|
| 560 |
|
|
[cols="4,27,>7"]
|
| 561 |
|
|
[frame="topbot",grid="none"]
|
| 562 |
|
|
|======
|
| 563 |
|
|
| 0xc02 | **Instructions-retired counter - low word** | `instret`
|
| 564 |
|
|
| 0xc82 | **Instructions-retired counter - high word** | `instreth`
|
| 565 |
|
|
3+| Reset value: _UNDEFINED_
|
| 566 |
|
|
3+| The `instret[h]` CSR is compatible to the RISC-V specifications. It shows the lower/upper 32-bit of the 64-bit retired
|
| 567 |
|
|
instructions counter. The `instret[h]` CSR is a read-only shadowed copy of the `minstret[h]` CSR.
|
| 568 |
|
|
|======
|
| 569 |
|
|
|
| 570 |
|
|
|
| 571 |
|
|
:sectnums!:
|
| 572 |
|
|
===== **`mcycle[h]`**
|
| 573 |
|
|
|
| 574 |
|
|
[cols="4,27,>7"]
|
| 575 |
|
|
[frame="topbot",grid="none"]
|
| 576 |
|
|
|======
|
| 577 |
|
|
| 0xb00 | **Machine cycle counter - low word** | `mcycle`
|
| 578 |
|
|
| 0xb80 | **Machine cycle counter - high word** | `mcycleh`
|
| 579 |
|
|
3+| Reset value: _UNDEFINED_
|
| 580 |
|
|
3+| The `mcycle[h]` CSR is compatible to the RISC-V specifications. It shows the lower/upper 32-bit of the 64-bit cycle
|
| 581 |
|
|
counter. The `mcycle[h]` CSR can also be written when in machine mode and is copied to the `cycle[h]` CSR.
|
| 582 |
|
|
|======
|
| 583 |
|
|
|
| 584 |
|
|
|
| 585 |
|
|
:sectnums!:
|
| 586 |
|
|
===== **`minstret[h]`**
|
| 587 |
|
|
|
| 588 |
|
|
[cols="4,27,>7"]
|
| 589 |
|
|
[frame="topbot",grid="none"]
|
| 590 |
|
|
|======
|
| 591 |
|
|
| 0xb02 | **Machine instructions-retired counter - low word** | `minstret`
|
| 592 |
|
|
| 0xb82 | **Machine instructions-retired counter - high word** | `minstreth`
|
| 593 |
|
|
3+| Reset value: _UNDEFINED_
|
| 594 |
|
|
3+| The `minstret[h]` CSR is compatible to the RISC-V specifications. It shows the lower/upper 32-bit of the 64-bit retired
|
| 595 |
|
|
instructions counter. The `minstret[h]` CSR also be written when in machine mode and is copied to the `instret[h]` CSR.
|
| 596 |
|
|
|======
|
| 597 |
|
|
|
| 598 |
|
|
|
| 599 |
|
|
|
| 600 |
|
|
<<<
|
| 601 |
|
|
// ####################################################################################################################
|
| 602 |
|
|
:sectnums:
|
| 603 |
|
|
==== Hardware Performance Monitors (HPM)
|
| 604 |
|
|
|
| 605 |
61 |
zero_gravi |
The available hardware performance logic is configured via the <<_hpm_num_cnts>> top entity generic,
|
| 606 |
|
|
which defines the number of implemented performance monitors and thus, the availability of the
|
| 607 |
|
|
according `mhpmcounter*[h]` and `mhpmevent*` CSRs.
|
| 608 |
60 |
zero_gravi |
|
| 609 |
61 |
zero_gravi |
[IMPORTANT]
|
| 610 |
|
|
The HPM system only implements machine-mode access. Hence, `hpmcounter*[h]` CSR are not implemented
|
| 611 |
|
|
and any access (even) from machine mode will raise an exception. Furthermore, the according bits of <<_mcounteren>>
|
| 612 |
|
|
used to configure user-mode access to `hpmcounter*[h]` are hard-wired to zero.
|
| 613 |
60 |
zero_gravi |
|
| 614 |
61 |
zero_gravi |
The total counter size of the HPMs can be configured before synthesis via the <<_hpm_cnt_width>> generic (0..64-bit).
|
| 615 |
|
|
|
| 616 |
60 |
zero_gravi |
[TIP]
|
| 617 |
61 |
zero_gravi |
If trying to access an HPM-related CSR beyond <<_hpm_num_cnts>> **no illegal instruction exception is
|
| 618 |
60 |
zero_gravi |
triggered**. The according CSRs are read-only (writes are ignored) and always return zero.
|
| 619 |
|
|
|
| 620 |
|
|
[NOTE]
|
| 621 |
|
|
The total LSB-aligned HPM counter size (low word CSR + high word CSR) is defined via the
|
| 622 |
61 |
zero_gravi |
<<_hpm_num_cnts>> generic (0..64-bit). If <<_hpm_num_cnts>> is less than 64, all unused MSB-aligned
|
| 623 |
60 |
zero_gravi |
bits are hardwired to zero.
|
| 624 |
|
|
|
| 625 |
|
|
|
| 626 |
|
|
:sectnums!:
|
| 627 |
|
|
===== **`mhpmevent`**
|
| 628 |
|
|
|
| 629 |
|
|
[cols="4,27,>7"]
|
| 630 |
|
|
[frame="topbot",grid="none"]
|
| 631 |
|
|
|======
|
| 632 |
|
|
| 0x232 -0x33f | **Machine hardware performance monitor event selector** | `mhpmevent3` - `mhpmevent31`
|
| 633 |
|
|
3+| Reset value: _UNDEFINED_
|
| 634 |
|
|
3+| The `mhpmevent*` CSRs are compatible to the RISC-V specifications. The configuration of these CSR define
|
| 635 |
62 |
zero_gravi |
the architectural events that cause the according `mhpmcounter*[h]` counters to increment. All available events are
|
| 636 |
60 |
zero_gravi |
listed in the table below. If more than one event is selected, the according counter will increment if any of
|
| 637 |
|
|
the enabled events is observed (logical OR). Note that the counter will only increment by 1 step per clock
|
| 638 |
|
|
cycle even if more than one event is observed. If the CPU is in sleep mode, no HPM counter will increment
|
| 639 |
|
|
at all.
|
| 640 |
|
|
|======
|
| 641 |
|
|
|
| 642 |
|
|
The available hardware performance logic is configured via the _HPM_NUM_CNTS_ top entity generic.
|
| 643 |
|
|
_HPM_NUM_CNTS_ defines the number of implemented performance monitors and thus, the availability of the
|
| 644 |
62 |
zero_gravi |
according `mhpmcounter*[h]` and `mhpmevent*` CSRs.
|
| 645 |
60 |
zero_gravi |
|
| 646 |
|
|
.HPM event selector
|
| 647 |
|
|
[cols="^1,<3,^1,<5"]
|
| 648 |
|
|
[options="header",grid="rows"]
|
| 649 |
|
|
|=======================
|
| 650 |
61 |
zero_gravi |
| Bit | Name [C] | R/W | Event
|
| 651 |
|
|
| 0 | _HPMCNT_EVENT_CY_ | r/w | active clock cycle (not in sleep)
|
| 652 |
|
|
| 1 | - | r/- | _not implemented, always read as zero_
|
| 653 |
|
|
| 2 | _HPMCNT_EVENT_IR_ | r/w | retired instruction
|
| 654 |
|
|
| 3 | _HPMCNT_EVENT_CIR_ | r/w | retired compressed instruction
|
| 655 |
60 |
zero_gravi |
| 4 | _HPMCNT_EVENT_WAIT_IF_ | r/w | instruction fetch memory wait cycle (if more than 1 cycle memory latency)
|
| 656 |
|
|
| 5 | _HPMCNT_EVENT_WAIT_II_ | r/w | instruction issue pipeline wait cycle (if more than 1 cycle latency), caused by pipelines flushes (like taken branches)
|
| 657 |
|
|
| 6 | _HPMCNT_EVENT_WAIT_MC_ | r/w | multi-cycle ALU operation wait cycle
|
| 658 |
61 |
zero_gravi |
| 7 | _HPMCNT_EVENT_LOAD_ | r/w | load operation
|
| 659 |
|
|
| 8 | _HPMCNT_EVENT_STORE_ | r/w | store operation
|
| 660 |
60 |
zero_gravi |
| 9 | _HPMCNT_EVENT_WAIT_LS_ | r/w | load/store memory wait cycle (if more than 1 cycle memory latency)
|
| 661 |
61 |
zero_gravi |
| 10 | _HPMCNT_EVENT_JUMP_ | r/w | unconditional jump
|
| 662 |
|
|
| 11 | _HPMCNT_EVENT_BRANCH_ | r/w | conditional branch (taken or not taken)
|
| 663 |
60 |
zero_gravi |
| 12 | _HPMCNT_EVENT_TBRANCH_ | r/w | taken conditional branch
|
| 664 |
61 |
zero_gravi |
| 13 | _HPMCNT_EVENT_TRAP_ | r/w | entered trap
|
| 665 |
60 |
zero_gravi |
| 14 | _HPMCNT_EVENT_ILLEGAL_ | r/w | illegal instruction exception
|
| 666 |
|
|
|=======================
|
| 667 |
|
|
|
| 668 |
|
|
|
| 669 |
|
|
:sectnums!:
|
| 670 |
|
|
===== **`mhpmcounter[h]`**
|
| 671 |
|
|
|
| 672 |
|
|
[cols="4,27,>7"]
|
| 673 |
|
|
[frame="topbot",grid="none"]
|
| 674 |
|
|
|======
|
| 675 |
|
|
| 0xb03 - 0xb1f | **Machine hardware performance monitor - counter low** | `mhpmcounter3` - `mhpmcounter31`
|
| 676 |
|
|
| 0xb83 - 0xb9f | **Machine hardware performance monitor - counter high** | `mhpmcounter3h` - `mhpmcounter31h`
|
| 677 |
|
|
3+| Reset value: _UNDEFINED_
|
| 678 |
|
|
3+| The `mhpmcounter*[h]` CSRs are compatible to the RISC-V specifications. These CSRs provide the lower/upper 32-
|
| 679 |
61 |
zero_gravi |
bit of arbitrary event counters. The event(s) that trigger an increment of theses counters are selected via the according
|
| 680 |
|
|
`mhpmevent*` CSRs bits.
|
| 681 |
60 |
zero_gravi |
|======
|
| 682 |
|
|
|
| 683 |
|
|
|
| 684 |
|
|
<<<
|
| 685 |
|
|
// ####################################################################################################################
|
| 686 |
|
|
:sectnums:
|
| 687 |
|
|
==== Machine Counter Setup
|
| 688 |
|
|
|
| 689 |
|
|
:sectnums!:
|
| 690 |
|
|
===== **`mcountinhibit`**
|
| 691 |
|
|
|
| 692 |
|
|
[cols="4,27,>7"]
|
| 693 |
|
|
[frame="topbot",grid="none"]
|
| 694 |
|
|
|======
|
| 695 |
|
|
| 0x320 | **Machine counter-inhibit register** | `mcountinhibit`
|
| 696 |
|
|
3+| Reset value: _UNDEFINED_
|
| 697 |
|
|
3+| The `mcountinhibit` CSR is compatible to the RISC-V specifications. The bits in this register define which
|
| 698 |
|
|
counter/timer CSR are allowed to perform an automatic increment. Automatic update is enabled if the
|
| 699 |
|
|
according bit in `mcountinhibit` is cleared. The following bits are implemented (all remaining bits are
|
| 700 |
|
|
always zero and are read-only).
|
| 701 |
|
|
|======
|
| 702 |
|
|
|
| 703 |
|
|
.Machine counter-inhibit register
|
| 704 |
|
|
[cols="^1,<3,^1,<5"]
|
| 705 |
|
|
[options="header",grid="rows"]
|
| 706 |
|
|
|=======================
|
| 707 |
|
|
| Bit | Name [C] | R/W | Event
|
| 708 |
|
|
| 0 | _CSR_MCOUNTINHIBIT_IR_ | r/w | the `[m]instret[h]` CSRs will auto-increment with each committed instruction when set
|
| 709 |
|
|
| 2 | _CSR_MCOUNTINHIBIT_IR_ | r/w | the `[m]cycle[h]` CSRs will auto-increment with each clock cycle (if CPU is not in sleep state) when set
|
| 710 |
62 |
zero_gravi |
| 3:31 | _CSR_MCOUNTINHIBIT_HPM3_ _: _CSR_MCOUNTINHIBIT_HPM31_ | r/w | the `mhpmcount*[h]` CSRs will auto-increment according to the configured `mhpmevent*` selector
|
| 711 |
60 |
zero_gravi |
|=======================
|
| 712 |
|
|
|
| 713 |
|
|
|
| 714 |
|
|
<<<
|
| 715 |
|
|
// ####################################################################################################################
|
| 716 |
|
|
:sectnums:
|
| 717 |
|
|
==== Machine Information Registers
|
| 718 |
|
|
|
| 719 |
62 |
zero_gravi |
[NOTE]
|
| 720 |
|
|
All machine information registers can only be accessed in machine mode and are read-only.
|
| 721 |
60 |
zero_gravi |
|
| 722 |
|
|
:sectnums!:
|
| 723 |
|
|
===== **`mvendorid`**
|
| 724 |
|
|
|
| 725 |
|
|
[cols="4,27,>7"]
|
| 726 |
|
|
[frame="topbot",grid="none"]
|
| 727 |
|
|
|======
|
| 728 |
|
|
| 0xf11 | **Machine vendor ID** | `mvendorid`
|
| 729 |
|
|
3+| Reset value: _0x00000000_
|
| 730 |
|
|
3+| The `mvendorid` CSR is compatible to the RISC-V specifications. It is read-only and always reads zero.
|
| 731 |
|
|
|======
|
| 732 |
|
|
|
| 733 |
|
|
|
| 734 |
|
|
:sectnums!:
|
| 735 |
|
|
===== **`marchid`**
|
| 736 |
|
|
|
| 737 |
|
|
[cols="4,27,>7"]
|
| 738 |
|
|
[frame="topbot",grid="none"]
|
| 739 |
|
|
|======
|
| 740 |
|
|
| 0xf12 | **Machine architecture ID** | `marchid`
|
| 741 |
|
|
3+| Reset value: _0x00000013_
|
| 742 |
|
|
3+| The `marchid` CSR is compatible to the RISC-V specifications. It is read-only and shows the NEORV32
|
| 743 |
|
|
official _RISC-V open-source architecture ID_ (decimal: 19, 32-bit hexadecimal: 0x00000013).
|
| 744 |
|
|
|======
|
| 745 |
|
|
|
| 746 |
|
|
|
| 747 |
|
|
:sectnums!:
|
| 748 |
|
|
===== **`mimpid`**
|
| 749 |
|
|
|
| 750 |
|
|
[cols="4,27,>7"]
|
| 751 |
|
|
[frame="topbot",grid="none"]
|
| 752 |
|
|
|======
|
| 753 |
|
|
| 0xf13 | **Machine implementation ID** | `mimpid`
|
| 754 |
|
|
3+| Reset value: _HW version number_
|
| 755 |
|
|
3+| The `mimpid` CSR is compatible to the RISC-V specifications. It is read-only and shows the version of the
|
| 756 |
|
|
NEORV32 as BCD-coded number (example: `mimpid` = _0x01020312_ → 01.02.03.12 → version 1.2.3.12).
|
| 757 |
|
|
|======
|
| 758 |
|
|
|
| 759 |
|
|
|
| 760 |
|
|
:sectnums!:
|
| 761 |
|
|
===== **`mhartid`**
|
| 762 |
|
|
|
| 763 |
|
|
[cols="4,27,>7"]
|
| 764 |
|
|
[frame="topbot",grid="none"]
|
| 765 |
|
|
|======
|
| 766 |
|
|
| 0xf14 | **Machine hardware thread ID** | `mhartid`
|
| 767 |
|
|
3+| Reset value: _HW_THREAD_ID_ generic
|
| 768 |
|
|
3+| The `mhartid` CSR is compatible to the RISC-V specifications. It is read-only and shows the core's hart ID,
|
| 769 |
|
|
which is assigned via the CPU's _HW_THREAD_ID_ generic.
|
| 770 |
|
|
|======
|
| 771 |
|
|
|
| 772 |
|
|
|
| 773 |
62 |
zero_gravi |
:sectnums!:
|
| 774 |
|
|
===== **`mconfigptr`**
|
| 775 |
60 |
zero_gravi |
|
| 776 |
62 |
zero_gravi |
[cols="4,27,>7"]
|
| 777 |
|
|
[frame="topbot",grid="none"]
|
| 778 |
|
|
|======
|
| 779 |
|
|
| 0xf15 | **Machine configuration pointer register** | `mconfigptr`
|
| 780 |
|
|
3+| Reset value: `0x00000000`
|
| 781 |
|
|
3+| This register holds a physical address (if not zero) that points to the base address of an architecture configuration structure.
|
| 782 |
|
|
Software can traverse this data structure to discover information about the harts, the platform, and their configuration.
|
| 783 |
|
|
**NOTE: Not assigned yet.**
|
| 784 |
|
|
|======
|
| 785 |
|
|
|
| 786 |
|
|
|
| 787 |
|
|
|
| 788 |
60 |
zero_gravi |
<<<
|
| 789 |
|
|
// ####################################################################################################################
|
| 790 |
|
|
:sectnums:
|
| 791 |
|
|
==== NEORV32-Specific Custom CSRs
|
| 792 |
|
|
|
| 793 |
|
|
|
| 794 |
|
|
:sectnums!:
|
| 795 |
|
|
===== **`mzext`**
|
| 796 |
|
|
|
| 797 |
|
|
[cols="4,27,>7"]
|
| 798 |
|
|
[frame="topbot",grid="none"]
|
| 799 |
|
|
|======
|
| 800 |
|
|
| 0xfc0 | **Available Z* extensions** | `mzext`
|
| 801 |
|
|
3+| Reset value: _0x00000000_
|
| 802 |
|
|
3+| The `mzext` CSR is a custom read-only CSR that shows the implemented Z* extensions. The following bits
|
| 803 |
|
|
are implemented (all remaining bits are always zero). The entire CSR is read-only.
|
| 804 |
|
|
|======
|
| 805 |
|
|
|
| 806 |
|
|
.Machine counter-inhibit register
|
| 807 |
|
|
[cols="^1,<3,^1,<5"]
|
| 808 |
|
|
[options="header",grid="rows"]
|
| 809 |
|
|
|=======================
|
| 810 |
|
|
| Bit | Name [C] | R/W | Event
|
| 811 |
61 |
zero_gravi |
| 0 | _CPU_MZEXT_ZICSR_ | r/- | `Zicsr` extensions available (enabled via <<_cpu_extension_riscv_zicsr>> generic)
|
| 812 |
|
|
| 1 | _CPU_MZEXT_ZIFENCEI_ | r/- | `Zifencei` extensions available (enabled via <<_cpu_extension_riscv_zifencei>> generic)
|
| 813 |
|
|
| 2 | _CPU_MZEXT_ZMMUL_ | r/- | `Zmmul` extensions available (enabled via <<_cpu_extension_riscv_zmmul>> generic)
|
| 814 |
|
|
| 5 | _CPU_MZEXT_ZFINX_ | r/- | `Zfinx` extensions available (enabled via <<_cpu_extension_riscv_zfinx>> generic)
|
| 815 |
|
|
| 6 | _CPU_MZEXT_ZXSCNT_ | r/- | custom extension: "Small CPU counters": `cycle[h]` & `instret[h]` CSRs have less than 64-bit when set (when <<_cpu_cnt_width>> generic is less than 64)
|
| 816 |
|
|
| 7 | _CPU_MZEXT_ZXNOCNT_ | r/- | custom extension: "NO CPU counters": `cycle[h]` & `instret[h]` CSRs are not available at all when set (when <<_cpu_cnt_width>> generic is 0)
|
| 817 |
|
|
| 8 | _CSR_MZEXT_PMP_ | r/- | PMP (physical memory protection) extension available (<<_pmp_num_regions>> generic > 0)
|
| 818 |
|
|
| 9 | _CSR_MZEXT_HPM_ | r/- | HPM (hardware performance monitors) extension available (<<_hpm_num_cnts>> generic > 0)
|
| 819 |
|
|
| 10 | _CSR_MZEXT_DEBUGMODE_ | r/- | RISC-V "CPU debug mode" extension available (enabled via <<_cpu_top_entity_generics,_CPU_EXTENSION_RISCV_DEBUG_>> generic)
|
| 820 |
60 |
zero_gravi |
|=======================
|