arch-riscv: Consistently check privilege mode for CSR accesses
According to the RISC-V privileged spec (section 2.1), bits 8 and 9 of
the CSR number encode the lowest privilege mode that is permitted to
access the CSR. Commit 55e7d3e5b6 added
this check for for CSR_MSTATUS but none of the other CSRs.
Change-Id: Iecf2e387fa9ee810e8b8471341bfa371693b97c5
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/55404
Reviewed-by: Nils Asmussen <nils.asmussen@barkhauseninstitut.org>
Maintainer: Jason Lowe-Power <power.jg@gmail.com>
Tested-by: kokoro <noreply+kokoro@google.com>
This commit is contained in:
@@ -290,23 +290,19 @@ def template CSRExecute {{
|
||||
%(op_rd)s;
|
||||
|
||||
RegVal data, olddata;
|
||||
|
||||
auto lowestAllowedMode = (PrivilegeMode)bits(csr, 9, 8);
|
||||
auto pm = (PrivilegeMode)xc->readMiscReg(MISCREG_PRV);
|
||||
if (pm < lowestAllowedMode) {
|
||||
return std::make_shared<IllegalInstFault>(
|
||||
csprintf("%s is not accessible in %s\n", csrName, pm),
|
||||
machInst);
|
||||
}
|
||||
switch (csr) {
|
||||
case CSR_SATP: {
|
||||
auto pm = (PrivilegeMode)xc->readMiscReg(MISCREG_PRV);
|
||||
STATUS status = xc->readMiscReg(MISCREG_STATUS);
|
||||
if (pm == PRV_U || (pm == PRV_S && status.tvm == 1)) {
|
||||
if (pm == PRV_S && status.tvm == 1) {
|
||||
return std::make_shared<IllegalInstFault>(
|
||||
"SATP access in user mode or with TVM enabled\n",
|
||||
machInst);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case CSR_MSTATUS: {
|
||||
auto pm = (PrivilegeMode)xc->readMiscReg(MISCREG_PRV);
|
||||
if (pm != PrivilegeMode::PRV_M) {
|
||||
return std::make_shared<IllegalInstFault>(
|
||||
"MSTATUS is only accessibly in machine mode\n",
|
||||
"SATP access with TVM enabled\n",
|
||||
machInst);
|
||||
}
|
||||
break;
|
||||
|
||||
Reference in New Issue
Block a user