Closed leekillough closed 3 weeks ago
I test using rv32g with and without '_zicntr' and confirmed that without the zicntr extension I received a very helpful message that will save people a lot of time scratching their heads ( thanks)
FATAL: RevCPU[cpu0:fatal:34790000]: Illegal instruction at PC = 0x11e44: Zicntr extension not available
I updated my tests in tests/tracer to use the zicntr extension and everything is passing. I'll push these changes after the PR is merged
This makes changes to the CSR implementation to make it more modular and more easily expanded for F***a:
RevRegFile
, moving it to aRevCSR
base class ofRevRegFile
.RevCSR
being a scopedenum class
with names of CSR registers, it is now a fullclass
with an unscopedenum
listing the names of all CSR registers. The syntax to access a CSR register is stillRevCSR::name
.constexpr
functions for better safety. The return type of a decoding is the smallest unsigned integer type capable of representing all values of the decoded field.ZeroExt()
if the type was smaller thanint
, it would get promoted toint
and that could cause undefined behavior because left-shifting a negative signed value is undefined. I changed the syntax slightly so that it only left-shifts unsigned values.RevCore::output
member was madepublic
so that error messages could be outputted just knowing the owningRevCore
.RevFCSR.h
.GetFRM()
was fixed -- it only returned the bottom 2 bits of the dynamic rounding mode, instead of the 3 bits it contains.#include
d to#include
another header file they depended on. Now every header file that a file needs is explicitly#include
d by it instead of depending on another header file to#include
it.Zicntr
(rdcycle
,rdtime
,rdinstret
, etc.) was added as another extension (Zicntr
impliesZicsr
).Zicntr
was moved into its own header fileRevZicntr.h
RevCSR
was structured in a way so that handling additional CSR registers is made easy with base classes ofRevCSR
.RevZicntr
is the first example.GetPC()
inRevRegFile
fromRevZicntr
, the functions are declared pure virtual (= 0
) in the base classes, not as an abstract interface declaration, but to indicate that some derived class must implement it for the base class. Pure virtual function calls do not use dynamic dispatch, so there is less of a performance hit than with regular virtual function calls.RevRegFile::IsRV64
andRevRegFile::HasD
were changed fromconst
data members to member functions, so that they could be accessed from base classes which declare them pure virtual. Since they are justRevFeature
queries,R->IsRV64()
was changed toF->IsRV64()
wherever possible, even though making them pure virtual in base classes should not require dynamic dispatch.RevRegFile::GetCore()
was added, so thatRevCSR
and its base classes could access theRevCore
owning the hart by declaringGetCore()
as a pure virtual function.RevFenv.h
, instead of storing a reference to theFCSR
floating-point status and modifying it atRevFenv
destruction time, only a pointer to theRevRegFile
is stored, and a new functionRevCSR::SetFFlags()
is used to set floating-point exception flags.Zicntr
is not enabled, then accessing theTIME
,CYCLE
, andINSTRET
CSR registers will print a fatal error message aboutZicntr
not being enabled.RV64
is in effect, theRDCYCLEH
,RDTIMEH
andRDINSTRETH
instructions will produce a fatal error message about them being illegal instructions onRV64
.SetCSR()
was changed to returnbool
, currently alwaystrue
. Iffalse
, it will make CSR instructions which modify CSR registers produce a fatal non-specific error message.zicntr
label was added to the tests, so thatRDCYCLE
,RDTIME
andRDINSTRET
tests pass theZicntr
architecture string to Rev. CurrentlyZicntr
is not supported by my toolchain, but it is enabled by default withZicsr
. If we move up in toolchains to whereZicntr
is not enabled by default, the testMakefile
s have commented out-march=
flags which will enableZicntr
.Cc: @tdysart