arch-riscv: Support combination of privilege modes configuration (#522)

The user can select privilege modes witch is included in the system, not
always enable the user and supervisor privilege modes.
This commit is contained in:
Bobby R. Bruce
2023-11-29 10:12:57 -08:00
committed by GitHub
13 changed files with 930 additions and 351 deletions

View File

@@ -74,6 +74,16 @@ class RiscvType(Enum):
vals = ["RV32", "RV64"]
class PrivilegeModeSet(Enum):
vals = [
"M", # Machine privilege mode only
"MU", # Machine and user privlege modes implemented
"MNU", # MU privilege modes with user-mode trap
"MSU", # Machine, supervisor and user modes implemented
"MNSU", # MSU privilege modes with user-mode trap
]
class RiscvISA(BaseISA):
type = "RiscvISA"
cxx_class = "gem5::RiscvISA::ISA"
@@ -95,6 +105,11 @@ class RiscvISA(BaseISA):
"Length of each vector element in bits. \
ELEN in Ch. 2 of RISC-V vector spec",
)
privilege_mode_set = Param.PrivilegeModeSet(
"MSU",
"The combination of privilege modes \
in Privilege Levels section of RISC-V privileged spec",
)
enable_Zicbom_fs = Param.Bool(True, "Enable Zicbom extension in FS mode")
enable_Zicboz_fs = Param.Bool(True, "Enable Zicboz extension in FS mode")

View File

@@ -73,7 +73,7 @@ SimObject('RiscvFsWorkload.py',
SimObject('RiscvInterrupts.py', sim_objects=['RiscvInterrupts'],
tags='riscv isa')
SimObject('RiscvISA.py', sim_objects=['RiscvISA'],
enums=['RiscvType'], tags='riscv isa')
enums=['RiscvType', 'PrivilegeModeSet'], tags='riscv isa')
SimObject('RiscvMMU.py', sim_objects=['RiscvMMU'], tags='riscv isa')
SimObject('RiscvSeWorkload.py', sim_objects=[
'RiscvSEWorkload', 'RiscvEmuLinux'], tags='riscv isa')

View File

@@ -67,6 +67,7 @@ RiscvFault::invoke(ThreadContext *tc, const StaticInstPtr &inst)
if (FullSystem) {
PrivilegeMode pp = (PrivilegeMode)tc->readMiscReg(MISCREG_PRV);
PrivilegeMode prv = PRV_M;
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
STATUS status = tc->readMiscReg(MISCREG_STATUS);
// According to riscv-privileged-v1.11, if a NMI occurs at the middle
@@ -82,18 +83,18 @@ RiscvFault::invoke(ThreadContext *tc, const StaticInstPtr &inst)
} else if (isInterrupt()) {
if (pp != PRV_M &&
bits(tc->readMiscReg(MISCREG_MIDELEG), _code) != 0) {
prv = PRV_S;
prv = (misa.rvs) ? PRV_S : ((misa.rvn) ? PRV_U : PRV_M);
}
if (pp == PRV_U &&
if (pp == PRV_U && misa.rvs && misa.rvn &&
bits(tc->readMiscReg(MISCREG_SIDELEG), _code) != 0) {
prv = PRV_U;
}
} else {
if (pp != PRV_M &&
bits(tc->readMiscReg(MISCREG_MEDELEG), _code) != 0) {
prv = PRV_S;
prv = (misa.rvs) ? PRV_S : ((misa.rvn) ? PRV_U : PRV_M);
}
if (pp == PRV_U &&
if (pp == PRV_U && misa.rvs && misa.rvn &&
bits(tc->readMiscReg(MISCREG_SEDELEG), _code) != 0) {
prv = PRV_U;
}

View File

@@ -69,21 +69,41 @@ class Interrupts : public BaseInterrupts
{
INTERRUPT mask = 0;
STATUS status = tc->readMiscReg(MISCREG_STATUS);
INTERRUPT mideleg = tc->readMiscReg(MISCREG_MIDELEG);
INTERRUPT sideleg = tc->readMiscReg(MISCREG_SIDELEG);
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
INTERRUPT mideleg = 0;
if (misa.rvs || misa.rvn) {
mideleg = tc->readMiscReg(MISCREG_MIDELEG);
}
INTERRUPT sideleg = 0;
if (misa.rvs && misa.rvn) {
sideleg = tc->readMiscReg(MISCREG_SIDELEG);
}
PrivilegeMode prv = (PrivilegeMode)tc->readMiscReg(MISCREG_PRV);
switch (prv) {
case PRV_U:
mask.mei = (!sideleg.mei) | (sideleg.mei & status.uie);
mask.mti = (!sideleg.mti) | (sideleg.mti & status.uie);
mask.msi = (!sideleg.msi) | (sideleg.msi & status.uie);
mask.sei = (!sideleg.sei) | (sideleg.sei & status.uie);
mask.sti = (!sideleg.sti) | (sideleg.sti & status.uie);
mask.ssi = (!sideleg.ssi) | (sideleg.ssi & status.uie);
// status.uie is always 0 if misa.rvn is disabled
if (misa.rvs) {
mask.mei = (!sideleg.mei) | (sideleg.mei & status.uie);
mask.mti = (!sideleg.mti) | (sideleg.mti & status.uie);
mask.msi = (!sideleg.msi) | (sideleg.msi & status.uie);
mask.sei = (!sideleg.sei) | (sideleg.sei & status.uie);
mask.sti = (!sideleg.sti) | (sideleg.sti & status.uie);
mask.ssi = (!sideleg.ssi) | (sideleg.ssi & status.uie);
} else {
// According to the RISC-V privilege spec v1.10, if the
// S privilege mode is not implemented and user-trap
// support, setting mideleg/medeleg bits will delegate the
// trap to U-mode trap handler
mask.mei = (!mideleg.mei) | (mideleg.mei & status.uie);
mask.mti = (!mideleg.mti) | (mideleg.mti & status.uie);
mask.msi = (!mideleg.msi) | (mideleg.msi & status.uie);
mask.sei = mask.sti = mask.ssi = 0;
}
if (status.uie)
mask.uei = mask.uti = mask.usi = 1;
break;
case PRV_S:
// status.sie is always 0 if misa.rvn is disabled
mask.mei = (!mideleg.mei) | (mideleg.mei & status.sie);
mask.mti = (!mideleg.mti) | (mideleg.mti & status.sie);
mask.msi = (!mideleg.msi) | (mideleg.msi & status.sie);

View File

@@ -254,9 +254,10 @@ RegClass ccRegClass(CCRegClass, CCRegClassName, 0, debug::IntRegs);
} // anonymous namespace
ISA::ISA(const Params &p) :BaseISA(p),
ISA::ISA(const Params &p) : BaseISA(p),
_rvType(p.riscv_type), checkAlignment(p.check_alignment),
enableRvv(p.enable_rvv),vlen(p.vlen),elen(p.elen)
enableRvv(p.enable_rvv), vlen(p.vlen), elen(p.elen),
_privilegeModeSet(p.privilege_mode_set)
{
_regClasses.push_back(&intRegClass);
_regClasses.push_back(&floatRegClass);
@@ -324,8 +325,25 @@ void ISA::clear()
// default config arch isa string is rv64(32)imafdc
misa.rvi = misa.rvm = misa.rva = misa.rvf = misa.rvd = misa.rvc = 1;
// default privlege modes if MSU
misa.rvs = misa.rvu = 1;
switch (getPrivilegeModeSet()) {
case enums::M:
break;
case enums::MU:
misa.rvu = 1;
break;
case enums::MNU:
misa.rvu = misa.rvn = 1;
break;
case enums::MSU:
misa.rvs = misa.rvu = 1;
break;
case enums::MNSU:
misa.rvs = misa.rvu = misa.rvn = 1;
break;
default:
panic("Privilege mode set config should not reach here");
}
// mark FS is initial
status.fs = INITIAL;
@@ -510,6 +528,24 @@ ISA::readMiscReg(RegIndex idx)
default:
panic("%s: Unknown _rvType: %d", name(), (int)_rvType);
}
// Check status.mpp
MISA misa = readMiscRegNoEffect(MISCREG_ISA);
switch(status.mpp) {
case PRV_U:
status.mpp = (misa.rvu) ? PRV_U : PRV_M;
break;
case PRV_S:
if (misa.rvs)
status.mpp = PRV_S;
else
status.mpp = (misa.rvu) ? PRV_U : PRV_M;
break;
case PRV_M:
break;
default:
status.mpp = (misa.rvu) ? PRV_U : PRV_M;
}
setMiscRegNoEffect(idx, status);
return readMiscRegNoEffect(idx);
@@ -697,6 +733,9 @@ ISA::setMiscReg(RegIndex idx, RegVal val)
if (!getEnableRvv()) {
new_misa.rvv = 0;
}
new_misa.rvn = cur_misa.rvn;
new_misa.rvs = cur_misa.rvs;
new_misa.rvu = cur_misa.rvu;
setMiscRegNoEffect(idx, new_misa);
}
break;

View File

@@ -94,6 +94,11 @@ class ISA : public BaseISA
*/
unsigned elen;
/** The combination of privilege modes
* in Privilege Levels section of RISC-V privileged spec
*/
PrivilegeModeSet _privilegeModeSet;
public:
using Params = RiscvISAParams;
@@ -124,7 +129,7 @@ class ISA : public BaseISA
virtual const std::unordered_map<int, RegVal>&
getCSRMaskMap() const
{
return CSRMasks[_rvType];
return CSRMasks[_rvType][_privilegeModeSet];
}
bool alignmentCheckEnabled() const { return checkAlignment; }
@@ -164,6 +169,8 @@ class ISA : public BaseISA
unsigned getVecLenInBytes() { return vlen >> 3; }
unsigned getVecElemLenInBits() { return elen; }
PrivilegeModeSet getPrivilegeModeSet() { return _privilegeModeSet; }
virtual Addr getFaultHandlerAddr(
RegIndex idx, uint64_t cause, bool intr) const;
};

View File

@@ -4595,6 +4595,12 @@ decode QUADRANT default Unknown::unknown() {
xc->pcState());
}}, IsSerializeAfter, IsNonSpeculative, No_OpClass);
0x2: uret({{
MISA misa = xc->readMiscReg(MISCREG_ISA);
if (!misa.rvn) {
return std::make_shared<IllegalInstFault>(
"sret can't execute without N systems",
machInst);
}
STATUS status = xc->readMiscReg(MISCREG_STATUS);
status.uie = status.upie;
status.upie = 1;
@@ -4604,6 +4610,12 @@ decode QUADRANT default Unknown::unknown() {
}
0x8: decode RS2 {
0x2: sret({{
MISA misa = xc->readMiscReg(MISCREG_ISA);
if (!misa.rvs) {
return std::make_shared<IllegalInstFault>(
"sret can't execute without RVS",
machInst);
}
STATUS status = xc->readMiscReg(MISCREG_STATUS);
auto pm = (PrivilegeMode)xc->readMiscReg(
MISCREG_PRV);
@@ -4623,11 +4635,12 @@ decode QUADRANT default Unknown::unknown() {
}
}}, IsSerializeAfter, IsNonSpeculative, IsReturn);
0x5: wfi({{
MISA misa = xc->readMiscReg(MISCREG_ISA);
STATUS status = xc->readMiscReg(MISCREG_STATUS);
auto pm = (PrivilegeMode)xc->readMiscReg(
MISCREG_PRV);
if (pm == PRV_U ||
(pm == PRV_S && status.tw == 1)) {
if (misa.rvs && (pm == PRV_U ||
(pm == PRV_S && status.tw == 1))) {
return std::make_shared<IllegalInstFault>(
"wfi in user mode or TW enabled",
machInst);
@@ -4647,6 +4660,12 @@ decode QUADRANT default Unknown::unknown() {
IsSerializeAfter, No_OpClass);
}
0x9: sfence_vma({{
MISA misa = xc->readMiscReg(MISCREG_ISA);
if (!misa.rvs) {
return std::make_shared<IllegalInstFault>(
"sfence_vma can't execute without RVS",
machInst);
}
STATUS status = xc->readMiscReg(MISCREG_STATUS);
auto pm = (PrivilegeMode)xc->readMiscReg(MISCREG_PRV);
if (pm == PRV_U || (pm == PRV_S && status.tvm == 1)) {

View File

@@ -334,6 +334,7 @@ def template CSRExecute {{
auto isa = static_cast<RiscvISA::ISA*>(xc->tcBase()->getIsaPtr());
auto& csr_data = isa->getCSRDataMap();
auto& csr_masks = isa->getCSRMaskMap();
MISA misa = isa->readMiscRegNoEffect(MISCREG_ISA);
auto csr_data_it = csr_data.find(csr);
if (csr_data_it == csr_data.end()) {
@@ -351,6 +352,14 @@ def template CSRExecute {{
machInst);
}
MISA csr_exts = csr_data_it->second.isaExts;
if ((csr_exts & misa) != csr_exts) {
return std::make_shared<IllegalInstFault>(
csprintf("%s is not support in the isa spec %d\n",
csrName),
machInst);
}
auto mask_it = csr_masks.find(csr);
RegVal maskVal = (mask_it == csr_masks.end()) ? mask(64)
: mask_it->second;

View File

@@ -44,6 +44,7 @@
#include "arch/generic/pcstate.hh"
#include "arch/riscv/regs/vector.hh"
#include "enums/PrivilegeModeSet.hh"
#include "enums/RiscvType.hh"
namespace gem5
@@ -55,6 +56,8 @@ using RiscvType = enums::RiscvType;
constexpr enums::RiscvType RV32 = enums::RV32;
constexpr enums::RiscvType RV64 = enums::RV64;
using PrivilegeModeSet = enums::PrivilegeModeSet;
class PCState : public GenericISA::UPCState<4>
{
protected:

View File

@@ -106,6 +106,10 @@ RiscvProcess64::initState()
tc->setMiscRegNoEffect(MISCREG_PRV, PRV_U);
auto *isa = dynamic_cast<ISA*>(tc->getIsaPtr());
fatal_if(isa->rvType() != RV64, "RISC V CPU should run in 64 bits mode");
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
fatal_if(!(misa.rvu && misa.rvs),
"RISC V SE mode can't run without supervisor and user "
"privilege modes.");
}
}
@@ -120,6 +124,10 @@ RiscvProcess32::initState()
tc->setMiscRegNoEffect(MISCREG_PRV, PRV_U);
auto *isa = dynamic_cast<ISA*>(tc->getIsaPtr());
fatal_if(isa->rvType() != RV32, "RISC V CPU should run in 32 bits mode");
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
fatal_if(!(misa.rvu && misa.rvs),
"RISC V SE mode can't run without supervisor and user "
"privilege modes.");
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -167,13 +167,22 @@ getRvType(ThreadContext* tc)
return isa->rvType();
}
static PrivilegeModeSet
getPrivilegeModeSet(ThreadContext* tc)
{
auto isa = dynamic_cast<ISA*>(tc->getIsaPtr());
panic_if(!isa, "Cannot derive rv_type from non-riscv isa");
return isa->getPrivilegeModeSet();
}
template <typename xint>
static void
setRegNoEffectWithMask(
ThreadContext *context, RiscvType type, CSRIndex idx, xint val)
ThreadContext *context, RiscvType type, PrivilegeModeSet pms,
CSRIndex idx, xint val)
{
RegVal oldVal, newVal;
RegVal mask = CSRMasks[type].at(idx);
RegVal mask = CSRMasks[type][pms].at(idx);
oldVal = context->readMiscRegNoEffect(CSRData.at(idx).physIndex);
newVal = (oldVal & ~mask) | (val & mask);
context->setMiscRegNoEffect(CSRData.at(idx).physIndex, newVal);
@@ -181,10 +190,12 @@ setRegNoEffectWithMask(
template <typename xint>
static void
setRegWithMask(ThreadContext *context, RiscvType type, CSRIndex idx, xint val)
setRegWithMask(
ThreadContext *context, RiscvType type, PrivilegeModeSet pms,
CSRIndex idx, xint val)
{
RegVal oldVal, newVal;
RegVal mask = CSRMasks[type].at(idx);
RegVal mask = CSRMasks[type][pms].at(idx);
oldVal = context->readMiscReg(CSRData.at(idx).physIndex);
newVal = (oldVal & ~mask) | (val & mask);
context->setMiscReg(CSRData.at(idx).physIndex, newVal);
@@ -207,7 +218,8 @@ RemoteGDB::acc(Addr va, size_t len)
PrivilegeMode pmode = mmu->getMemPriv(context(), BaseMMU::Read);
SATP satp = context()->readMiscReg(MISCREG_SATP);
if (pmode != PrivilegeMode::PRV_M &&
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
if (misa.rvs && pmode != PrivilegeMode::PRV_M &&
satp.mode != AddrXlateMode::BARE) {
Walker *walker = mmu->getDataWalker();
Fault fault = walker->startFunctional(
@@ -225,7 +237,8 @@ void
RemoteGDB::Riscv32GdbRegCache::getRegs(ThreadContext *context)
{
DPRINTF(GDBAcc, "getregs in remotegdb, size %lu\n", size());
auto& RVxCSRMasks = CSRMasks[RV32];
PrivilegeModeSet pms = getPrivilegeModeSet(context);
auto& RVxCSRMasks = CSRMasks[RV32][pms];
// General registers
for (int i = 0; i < int_reg::NumArchRegs; i++) {
@@ -339,6 +352,7 @@ void
RemoteGDB::Riscv32GdbRegCache::setRegs(ThreadContext *context) const
{
DPRINTF(GDBAcc, "setregs in remotegdb \n");
PrivilegeModeSet pms = getPrivilegeModeSet(context);
for (int i = 0; i < int_reg::NumArchRegs; i++)
context->setReg(intRegClass[i], r.gpr[i]);
context->pcState(r.pc);
@@ -347,16 +361,16 @@ RemoteGDB::Riscv32GdbRegCache::setRegs(ThreadContext *context) const
for (int i = 0; i < float_reg::NumRegs; i++)
context->setReg(floatRegClass[i], r.fpu[i]);
setRegNoEffectWithMask(context, RV32, CSR_FFLAGS, r.fflags);
setRegNoEffectWithMask(context, RV32, CSR_FRM, r.frm);
setRegNoEffectWithMask(context, RV32, CSR_FCSR, r.fcsr);
setRegNoEffectWithMask(context, RV32, pms, CSR_FFLAGS, r.fflags);
setRegNoEffectWithMask(context, RV32, pms, CSR_FRM, r.frm);
setRegNoEffectWithMask(context, RV32, pms, CSR_FCSR, r.fcsr);
// TODO: implement CSR counter registers for mcycle(h), minstret(h)
// U mode CSR
setRegNoEffectWithMask(context, RV32, CSR_USTATUS, r.ustatus);
setRegWithMask(context, RV32, CSR_UIE, r.uie);
setRegWithMask(context, RV32, CSR_UIP, r.uip);
setRegNoEffectWithMask(context, RV32, pms, CSR_USTATUS, r.ustatus);
setRegWithMask(context, RV32, pms, CSR_UIE, r.uie);
setRegWithMask(context, RV32, pms, CSR_UIP, r.uip);
context->setMiscRegNoEffect(
CSRData.at(CSR_UTVEC).physIndex, r.utvec);
context->setMiscRegNoEffect(
@@ -369,9 +383,9 @@ RemoteGDB::Riscv32GdbRegCache::setRegs(ThreadContext *context) const
CSRData.at(CSR_UTVAL).physIndex, r.utval);
// S mode CSR
setRegNoEffectWithMask(context, RV32, CSR_SSTATUS, r.sstatus);
setRegWithMask(context, RV32, CSR_SIE, r.sie);
setRegWithMask(context, RV32, CSR_SIP, r.sip);
setRegNoEffectWithMask(context, RV32, pms, CSR_SSTATUS, r.sstatus);
setRegWithMask(context, RV32, pms, CSR_SIE, r.sie);
setRegWithMask(context, RV32, pms, CSR_SIP, r.sip);
context->setMiscRegNoEffect(
CSRData.at(CSR_SEDELEG).physIndex, r.sedeleg);
context->setMiscRegNoEffect(
@@ -392,10 +406,10 @@ RemoteGDB::Riscv32GdbRegCache::setRegs(ThreadContext *context) const
CSRData.at(CSR_SATP).physIndex, r.satp);
// M mode CSR
setRegNoEffectWithMask(context, RV32, CSR_MSTATUS, r.mstatus);
setRegNoEffectWithMask(context, RV32, CSR_MISA, r.misa);
setRegWithMask(context, RV32, CSR_MIE, r.mie);
setRegWithMask(context, RV32, CSR_MIP, r.mip);
setRegNoEffectWithMask(context, RV32, pms, CSR_MSTATUS, r.mstatus);
setRegNoEffectWithMask(context, RV32, pms, CSR_MISA, r.misa);
setRegWithMask(context, RV32, pms, CSR_MIE, r.mie);
setRegWithMask(context, RV32, pms, CSR_MIP, r.mip);
context->setMiscRegNoEffect(
CSRData.at(CSR_MEDELEG).physIndex, r.medeleg);
context->setMiscRegNoEffect(
@@ -420,7 +434,8 @@ void
RemoteGDB::Riscv64GdbRegCache::getRegs(ThreadContext *context)
{
DPRINTF(GDBAcc, "getregs in remotegdb, size %lu\n", size());
auto& RVxCSRMasks = CSRMasks[RV64];
PrivilegeModeSet pms = getPrivilegeModeSet(context);
auto& RVxCSRMasks = CSRMasks[RV64][pms];
// General registers
for (int i = 0; i < int_reg::NumArchRegs; i++) {
@@ -528,6 +543,7 @@ void
RemoteGDB::Riscv64GdbRegCache::setRegs(ThreadContext *context) const
{
DPRINTF(GDBAcc, "setregs in remotegdb \n");
PrivilegeModeSet pms = getPrivilegeModeSet(context);
for (int i = 0; i < int_reg::NumArchRegs; i++)
context->setReg(intRegClass[i], r.gpr[i]);
context->pcState(r.pc);
@@ -536,16 +552,16 @@ RemoteGDB::Riscv64GdbRegCache::setRegs(ThreadContext *context) const
for (int i = 0; i < float_reg::NumRegs; i++)
context->setReg(floatRegClass[i], r.fpu[i]);
setRegNoEffectWithMask(context, RV64, CSR_FFLAGS, r.fflags);
setRegNoEffectWithMask(context, RV64, CSR_FRM, r.frm);
setRegNoEffectWithMask(context, RV64, CSR_FCSR, r.fcsr);
setRegNoEffectWithMask(context, RV64, pms, CSR_FFLAGS, r.fflags);
setRegNoEffectWithMask(context, RV64, pms, CSR_FRM, r.frm);
setRegNoEffectWithMask(context, RV64, pms, CSR_FCSR, r.fcsr);
// TODO: implement CSR counter registers for mcycle, minstret
// U mode CSR
setRegNoEffectWithMask(context, RV64, CSR_USTATUS, r.ustatus);
setRegWithMask(context, RV64, CSR_UIE, r.uie);
setRegWithMask(context, RV64, CSR_UIP, r.uip);
setRegNoEffectWithMask(context, RV64, pms, CSR_USTATUS, r.ustatus);
setRegWithMask(context, RV64, pms, CSR_UIE, r.uie);
setRegWithMask(context, RV64, pms, CSR_UIP, r.uip);
context->setMiscRegNoEffect(
CSRData.at(CSR_UTVEC).physIndex, r.utvec);
context->setMiscRegNoEffect(
@@ -558,9 +574,10 @@ RemoteGDB::Riscv64GdbRegCache::setRegs(ThreadContext *context) const
CSRData.at(CSR_UTVAL).physIndex, r.utval);
// S mode CSR
setRegNoEffectWithMask(context, RV64, CSR_SSTATUS, r.sstatus);
setRegWithMask(context, RV64, CSR_SIE, r.sie);
setRegWithMask(context, RV64, CSR_SIP, r.sip);
setRegNoEffectWithMask(
context, RV64, pms, CSR_SSTATUS, r.sstatus);
setRegWithMask(context, RV64, pms, CSR_SIE, r.sie);
setRegWithMask(context, RV64, pms, CSR_SIP, r.sip);
context->setMiscRegNoEffect(
CSRData.at(CSR_SEDELEG).physIndex, r.sedeleg);
context->setMiscRegNoEffect(
@@ -581,10 +598,11 @@ RemoteGDB::Riscv64GdbRegCache::setRegs(ThreadContext *context) const
CSRData.at(CSR_SATP).physIndex, r.satp);
// M mode CSR
setRegNoEffectWithMask(context, RV64, CSR_MSTATUS, r.mstatus);
setRegNoEffectWithMask(context, RV64, CSR_MISA, r.misa);
setRegWithMask(context, RV64, CSR_MIE, r.mie);
setRegWithMask(context, RV64, CSR_MIP, r.mip);
setRegNoEffectWithMask(
context, RV64, pms, CSR_MSTATUS, r.mstatus);
setRegNoEffectWithMask(context, RV64, pms, CSR_MISA, r.misa);
setRegWithMask(context, RV64, pms, CSR_MIE, r.mie);
setRegWithMask(context, RV64, pms, CSR_MIP, r.mip);
context->setMiscRegNoEffect(
CSRData.at(CSR_MEDELEG).physIndex, r.medeleg);
context->setMiscRegNoEffect(

View File

@@ -341,9 +341,12 @@ TLB::translate(const RequestPtr &req, ThreadContext *tc,
if (FullSystem) {
PrivilegeMode pmode = getMemPriv(tc, mode);
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
SATP satp = tc->readMiscReg(MISCREG_SATP);
if (pmode == PrivilegeMode::PRV_M || satp.mode == AddrXlateMode::BARE)
if (!misa.rvs || pmode == PrivilegeMode::PRV_M ||
satp.mode == AddrXlateMode::BARE) {
req->setFlags(Request::PHYSICAL);
}
Fault fault;
if (req->getFlags() & Request::PHYSICAL) {
@@ -434,8 +437,9 @@ TLB::translateFunctional(const RequestPtr &req, ThreadContext *tc,
MMU *mmu = static_cast<MMU *>(tc->getMMUPtr());
PrivilegeMode pmode = mmu->getMemPriv(tc, mode);
MISA misa = tc->readMiscRegNoEffect(MISCREG_ISA);
SATP satp = tc->readMiscReg(MISCREG_SATP);
if (pmode != PrivilegeMode::PRV_M &&
if (misa.rvs && pmode != PrivilegeMode::PRV_M &&
satp.mode != AddrXlateMode::BARE) {
Walker *walker = mmu->getDataWalker();
unsigned logBytes;