From: Gabe Black Date: Wed, 13 Nov 2019 00:52:05 +0000 (-0800) Subject: fastmodel: Implement flattened int reg reading and writing. X-Git-Tag: v19.0.0.0~43 X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=d062a82f112640436fdb99f21884363557cede9b;p=gem5.git fastmodel: Implement flattened int reg reading and writing. Because the fast models (or at least the one we've looked at) give access to the integer registers mostly based on the current view of those registers, it does its own flattening and prevents accessing most of the raw storage locations without this extra level of mapping. To store to the flattened locations, we need to unflatten the indexes and in one case shift the mode so that we get the right values. Some registers which have irrelevant values for fast model (the "PC" which is actually diverted elsewhere, the zero register, microcode registers, and the "dummy" register), and those are left out of the mapping so that they return 0 and blow up gem5 when someone attempts to set them. Change-Id: Ia2d315d5ca4c8a65b17ad52beff3a366ca8b3d46 Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/23791 Tested-by: kokoro Reviewed-by: Giacomo Travaglini Reviewed-by: Chun-Chen TK Hsu Maintainer: Gabe Black --- diff --git a/src/arch/arm/fastmodel/CortexA76/thread_context.cc b/src/arch/arm/fastmodel/CortexA76/thread_context.cc index 281c70aca..70a95ede1 100644 --- a/src/arch/arm/fastmodel/CortexA76/thread_context.cc +++ b/src/arch/arm/fastmodel/CortexA76/thread_context.cc @@ -93,11 +93,55 @@ CortexA76TC::initFromIrisInstance(const ResourceMap &resources) extractResourceMap(intReg32Ids, resources, intReg32IdxNameMap); extractResourceMap(intReg64Ids, resources, intReg64IdxNameMap); + extractResourceMap(flattenedIntIds, resources, flattenedIntIdxNameMap); + extractResourceMap(ccRegIds, resources, ccRegIdxNameMap); extractResourceMap(vecRegIds, resources, vecRegIdxNameMap); } +RegVal +CortexA76TC::readIntRegFlat(RegIndex idx) const +{ + ArmISA::CPSR orig_cpsr; + + auto *non_const_this = const_cast(this); + + if (idx == ArmISA::INTREG_R13_MON || idx == ArmISA::INTREG_R14_MON) { + orig_cpsr = readMiscRegNoEffect(ArmISA::MISCREG_CPSR); + ArmISA::CPSR new_cpsr = orig_cpsr; + new_cpsr.mode = MODE_MON; + non_const_this->setMiscReg(ArmISA::MISCREG_CPSR, new_cpsr); + } + + RegVal val = ThreadContext::readIntRegFlat(idx); + + if (idx == ArmISA::INTREG_R13_MON || idx == ArmISA::INTREG_R14_MON) { + non_const_this->setMiscReg(ArmISA::MISCREG_CPSR, orig_cpsr); + } + + return val; +} + +void +CortexA76TC::setIntRegFlat(RegIndex idx, RegVal val) +{ + ArmISA::CPSR orig_cpsr; + + if (idx == ArmISA::INTREG_R13_MON || idx == ArmISA::INTREG_R14_MON) { + orig_cpsr = readMiscRegNoEffect(ArmISA::MISCREG_CPSR); + ArmISA::CPSR new_cpsr = orig_cpsr; + new_cpsr.mode = MODE_MON; + setMiscReg(ArmISA::MISCREG_CPSR, new_cpsr); + } + + ThreadContext::setIntRegFlat(idx, val); + + if (idx == ArmISA::INTREG_R13_MON || idx == ArmISA::INTREG_R14_MON) { + setMiscReg(ArmISA::MISCREG_CPSR, orig_cpsr); + } +} + RegVal CortexA76TC::readCCRegFlat(RegIndex idx) const { @@ -840,6 +884,48 @@ Iris::ThreadContext::IdxNameMap CortexA76TC::intReg64IdxNameMap({ { ArmISA::INTREG_SPX, "SP" }, }); +Iris::ThreadContext::IdxNameMap CortexA76TC::flattenedIntIdxNameMap({ + { ArmISA::INTREG_R0, "X0" }, + { ArmISA::INTREG_R1, "X1" }, + { ArmISA::INTREG_R2, "X2" }, + { ArmISA::INTREG_R3, "X3" }, + { ArmISA::INTREG_R4, "X4" }, + { ArmISA::INTREG_R5, "X5" }, + { ArmISA::INTREG_R6, "X6" }, + { ArmISA::INTREG_R7, "X7" }, + { ArmISA::INTREG_R8, "X8" }, + { ArmISA::INTREG_R9, "X9" }, + { ArmISA::INTREG_R10, "X10" }, + { ArmISA::INTREG_R11, "X11" }, + { ArmISA::INTREG_R12, "X12" }, + { ArmISA::INTREG_R13, "X13" }, + { ArmISA::INTREG_R14, "X14" }, + // Skip PC. + { ArmISA::INTREG_R13_SVC, "X19" }, + { ArmISA::INTREG_R14_SVC, "X18" }, + { ArmISA::INTREG_R13_MON, "R13" }, // Need to be in monitor mode? + { ArmISA::INTREG_R14_MON, "R14" }, // Need to be in monitor mode? + { ArmISA::INTREG_R13_HYP, "X15" }, + { ArmISA::INTREG_R13_ABT, "X21" }, + { ArmISA::INTREG_R14_ABT, "X20" }, + { ArmISA::INTREG_R13_UND, "X23" }, + { ArmISA::INTREG_R14_UND, "X22" }, + { ArmISA::INTREG_R13_IRQ, "X17" }, + { ArmISA::INTREG_R14_IRQ, "X16" }, + { ArmISA::INTREG_R8_FIQ, "X24" }, + { ArmISA::INTREG_R9_FIQ, "X25" }, + { ArmISA::INTREG_R10_FIQ, "X26" }, + { ArmISA::INTREG_R11_FIQ, "X27" }, + { ArmISA::INTREG_R12_FIQ, "X28" }, + { ArmISA::INTREG_R13_FIQ, "X29" }, + { ArmISA::INTREG_R14_FIQ, "X30" }, + // Skip zero, ureg0-2, and dummy regs. + { INTREG_SP0, "SP_EL0" }, + { INTREG_SP1, "SP_EL1" }, + { INTREG_SP2, "SP_EL2" }, + { INTREG_SP3, "SP_EL3" }, +}); + Iris::ThreadContext::IdxNameMap CortexA76TC::ccRegIdxNameMap({ { ArmISA::CCREG_NZ, "CPSR" }, { ArmISA::CCREG_C, "CPSR.C" }, diff --git a/src/arch/arm/fastmodel/CortexA76/thread_context.hh b/src/arch/arm/fastmodel/CortexA76/thread_context.hh index af031140c..a112cf011 100644 --- a/src/arch/arm/fastmodel/CortexA76/thread_context.hh +++ b/src/arch/arm/fastmodel/CortexA76/thread_context.hh @@ -43,6 +43,7 @@ class CortexA76TC : public Iris::ThreadContext static IdxNameMap miscRegIdxNameMap; static IdxNameMap intReg32IdxNameMap; static IdxNameMap intReg64IdxNameMap; + static IdxNameMap flattenedIntIdxNameMap; static IdxNameMap ccRegIdxNameMap; static IdxNameMap vecRegIdxNameMap; static iris::MemorySpaceId bpSpaceId; @@ -57,6 +58,9 @@ class CortexA76TC : public Iris::ThreadContext void initFromIrisInstance(const ResourceMap &resources) override; + RegVal readIntRegFlat(RegIndex idx) const override; + void setIntRegFlat(RegIndex idx, RegVal val) override; + RegVal readCCRegFlat(RegIndex idx) const override; void setCCRegFlat(RegIndex idx, RegVal val) override; diff --git a/src/arch/arm/fastmodel/iris/thread_context.cc b/src/arch/arm/fastmodel/iris/thread_context.cc index c18a5cd7d..f487ebc7c 100644 --- a/src/arch/arm/fastmodel/iris/thread_context.cc +++ b/src/arch/arm/fastmodel/iris/thread_context.cc @@ -520,6 +520,35 @@ ThreadContext::setIntReg(RegIndex reg_idx, RegVal val) call().resource_write(_instId, result, intReg64Ids.at(reg_idx), val); } +/* + * The 64 bit version of registers gives us a pre-flattened view of the reg + * file, no matter what mode we're in or if we're currently 32 or 64 bit. + */ +RegVal +ThreadContext::readIntRegFlat(RegIndex idx) const +{ + if (idx >= flattenedIntIds.size()) + return 0; + iris::ResourceId res_id = flattenedIntIds.at(idx); + if (res_id == iris::IRIS_UINT64_MAX) + return 0; + iris::ResourceReadResult result; + call().resource_read(_instId, result, res_id); + return result.data.at(0); +} + +void +ThreadContext::setIntRegFlat(RegIndex idx, uint64_t val) +{ + iris::ResourceId res_id = + (idx >= flattenedIntIds.size()) ? iris::IRIS_UINT64_MAX : + flattenedIntIds.at(idx); + panic_if(res_id == iris::IRIS_UINT64_MAX, + "Int reg %d is not supported by fast model.", idx); + iris::ResourceWriteResult result; + call().resource_write(_instId, result, flattenedIntIds.at(idx), val); +} + RegVal ThreadContext::readCCRegFlat(RegIndex idx) const { diff --git a/src/arch/arm/fastmodel/iris/thread_context.hh b/src/arch/arm/fastmodel/iris/thread_context.hh index 5590f7fd2..84d1f79fd 100644 --- a/src/arch/arm/fastmodel/iris/thread_context.hh +++ b/src/arch/arm/fastmodel/iris/thread_context.hh @@ -83,6 +83,7 @@ class ThreadContext : public ::ThreadContext ResourceIds miscRegIds; ResourceIds intReg32Ids; ResourceIds intReg64Ids; + ResourceIds flattenedIntIds; ResourceIds ccRegIds; iris::ResourceId pcRscId = iris::IRIS_UINT64_MAX; @@ -490,16 +491,8 @@ class ThreadContext : public ::ThreadContext * serialization code to access all registers. */ - uint64_t - readIntRegFlat(RegIndex idx) const override - { - panic("%s not implemented.", __FUNCTION__); - } - void - setIntRegFlat(RegIndex idx, uint64_t val) override - { - panic("%s not implemented.", __FUNCTION__); - } + RegVal readIntRegFlat(RegIndex idx) const override; + void setIntRegFlat(RegIndex idx, uint64_t val) override; RegVal readFloatRegFlat(RegIndex idx) const override