This refactors the invalidation control logic into an explicit state
machine. The top-level icache_invalid_o signal is also removed.
Replaced with an explicit scramble key request instead.
This has all been done to better deal with corner cases around a new
invalidation being requested whilst another is still going on.
Previously there was a bug wher an invalidation request in the final
cycle of an ongoing invalidation didn't restart the invalidation but did
rotate the scrambling key producing an ECC failure and an alert.
The following changes are made:
- For unimplemented counters corresponding bits in MCOUNTINHIBIT read as
0 not 1
- For MHPMEVENTx we start at x = 3 with the first bit set (0-2
MHPMEVENTx CSRs do not exist)
- When writing an invalid privilege mode to MSTATUS.MPP/DCSR.PRV default
to U rather than M mode.
These new behaviours remain spec compliant and match spike.
Initially the 'B' bit was going to be used to indicate the presence of
the bit-manipulation extension. Now that has been seperated into
multiple smaller extensions the 'B' MISA bit isn't being used and
remains a reserved bit that should read as 0.
For the RV32B configurations where we implement non ratified
bit-manipulation extensions we must set the 'X' bit.
These changes matche the behaviour of spike.
As Greg pointed out:
When we have an instruction in ID/EX that writes a PMP register that
update gets written to the CSR the same cycle the next instruction
moves from IF to ID/EX with it's PMP check done with the old value.
The solution is to flush the pipeline when we get a PMP CSR write.
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
The relevant page [Debug Spec v1.0.0-STABLE, p.53] gives the following
priorities for resolving multiple concurrent reasons for entering debug mode....
DCSR.cause : Explains why Debug Mode was entered.
When there are multiple reasons to enter Debug Mode in a single cycle,
hardware should set cause to the cause with the highest priority.
1: An ebreak instruction was executed. (priority 3)
2: A Trigger Module trigger fired with action=1. (priority 4)
3: The debugger requested entry to Debug Mode using haltreq. (priority 1)
4: The hart single stepped because step was set. (priority 0, lowest)
5: The hart halted directly out of reset due to resethaltreq. (priority 2)
It is also acceptable to report 3 when this happens.
6: The hart halted because it’s part of a halt group. (priority 5, highest)
Harts may report 3 for this cause instead.
Other values are reserved for future use.
In ePMP spec, it specifies as:
```
Executing code with Machine mode privileges is only possible from memory
regions with a matching Mmode-only rule or a locked Shared-Region rule
with executable privileges. Executing code from a region without a
matching rule or with a matching S/U-mode-only rule is denied.
```
This change provides that.
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
Some aspects of the memory response are only relevant to reads. This
introduces outstanding request tracking so we know which outstanding
requests are reads and applies X checks appropriately.
Fixes#1645
Extends RVFI connections further to include 30 mhpmcounterX registers.
Sets them up before every cosim step to let Spike know their real values.
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
Adds some signal to the load store unit to catch when we have the
fetch error signals from both first and second part of the misaligned
load/store access cases.
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
Includes coverpoints for:
- Hardware trigger point matches
- Debug simple step entrance in controller
- Seeing different insns while single stepping
Also updates on coverage plan to fill up missing mentions of
coverpoints/crosses
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
- mtval is a bit more useful for double fault situations
as on the second exception we can still "remember" the
data address and PC of the first exception.
Signed-off-by: Timothy Chen <timothytim@google.com>
This makes use of functions in a way that enables us to use `priv_lvl`
dependent logic in the DV environment.
Signed-off-by: Canberk Topal <ctopal@lowrisc.org>
This functional code coverage section has hierarchical paths, which will
break certain synthesis and lint flows.
Signed-off-by: Michael Schaffner <msf@google.com>
Vivado gives synthesis error complaining about assignment of irq_nm_int_cause to '0 by saying it is an enum type.
Change the assignment to NMI_INT_CAUSE_ECC, which is defined to 5'b0 in ibex_pkg.sv
The prefetch buffer and icache both treat the branch_i and
branch_mispredict_i signals identically, so it's a bit cleaner to pull
that treatment up into ibex_if_stage.sv
This commit doesn't change the modules below: it just passes zeros for
the "mispredict" version. Removing those ports will be done in a
follow-up commit.
An internal interrupt triggers an NMI. A single one is implemented, one
on integrity errors being seen in load data. This replaces a synchronous
exception on an integrity error which caused timing issues.
This groups the various different illegal instructions categories within
ibex_id_stage rather than spreading them between ibex_id_stage and
ibex_controller.
Previously integrity checks for incoming memory reads and integrity
generation for outgoing memory writes were handled within ibex_lockstep
and weren't duplicated.
This moves the integrity checks and generation into the core so they are
replicated and checked as part of the lockstep mechanism.
Additionally it generates a bus error on any memory integrity check
failure. This will result in Ibex taking an exception if any data read
or instruction fetch has bad integrity.
This is triggered by the fact that if the ICache parameter is false
then we don't instantiate the ibex_icache module. For verilator
simulations, the module is then discarded entirely, which means that
its two DPI functions are not defined. That's unfortunate because
we're also compiling the code in scrambled_ecc32_mem_area.cc, which
expects the functions to be defined.
The obvious solution (don't include scrambled_ecc32_mem_area.cc if you
don't have an icache) isn't easy to do, because FuseSoc doesn't
currently allow us to use parameters to configure its dependency
tree (see fusesoc issue 438 for a discussion).
The super-clever solution that I came up with before(!) was to declare
these symbols as weak in the C++ code. That way, we can do a runtime
check to make sure that no-one is silly enough to call them without an
icache, but everything will still build properly either way.
Unfortunately, that doesn't work well with xcelium simulations.
Xcelium turns out to compile all the C++ code into one .so library and
generate functions for exported DPI functions in another. These two
solibs then get loaded at runtime with dlopen(). But this doesn't work
with weak symbols: in fact, it seems you end up with the C++ version
every time. Boo!
So let's be stupider about it and define (bogus) versions of the DPI
functions in this case. Fortunately, both of them are designed to
return zero on failure so we can just return zero and needn't worry
too much.
The idea is that when this lands, we can revert the OpenTitan change
that switched the C++ code to using weak symbols and Xcelium
simulations will start working.
A sufficiently agressive optimiser may optimise these away as under
normal functioning they effectively don't do anything. They are purely
to detect the presence of induced faults.
This is to allow more consistent signalling in systems that integrate
Ibex (e.g. OpenTitan) so bus integrity errors external to Ibex and one's
detected within Ibex can be fed into the same alert whilst seperating
out Ibex's various internal alert causes.