From c1513c69cad2c26c6dcb66416e152952ceb0597e Mon Sep 17 00:00:00 2001 From: Curtis Dunham Date: Fri, 3 Nov 2017 17:39:45 -0500 Subject: [PATCH] arm: extend MiscReg metadata structures Implement proper handling of RES0/RES1 and RAZ/RAO bitfields. Change-Id: I344c32c3fb1d142acfb0521ba3590ddd2b1f5360 Signed-off-by: Curtis Dunham Reviewed-by: Andreas Sandberg Reviewed-by: Jack Travaglini Reviewed-on: https://gem5-review.googlesource.com/6802 Maintainer: Andreas Sandberg --- src/arch/arm/isa.cc | 40 +++++++++++++++++++++++++++++----------- src/arch/arm/isa.hh | 34 +++++++++++++++++++++++++++++++++- 2 files changed, 62 insertions(+), 12 deletions(-) diff --git a/src/arch/arm/isa.cc b/src/arch/arm/isa.cc index 6a803feb5..a9648d203 100644 --- a/src/arch/arm/isa.cc +++ b/src/arch/arm/isa.cc @@ -205,6 +205,9 @@ ISA::initializeMiscRegMetadata() InitReg(MISCREG_PMXEVCNTR_EL0).mapsTo(MISCREG_PMXEVCNTR); InitReg(MISCREG_PMXEVTYPER_EL0).mapsTo(MISCREG_PMXEVTYPER); + InitReg(MISCREG_SCR).res0(0xff40) // [31:16], [6] + .res1(0x0030); // [5:4] + // from ARM DDI 0487A.i, template text // "AArch64 System register ___ can be mapped to // AArch32 System register ___, but this is not @@ -492,10 +495,22 @@ ISA::readMiscRegNoEffect(int misc_reg) const { assert(misc_reg < NumMiscRegs); - auto regs = getMiscIndices(misc_reg); - int lower = regs.first, upper = regs.second; - return !upper ? miscRegs[lower] : ((miscRegs[lower] & mask(32)) - |(miscRegs[upper] << 32)); + const auto ® = lookUpMiscReg[misc_reg]; // bit masks + const auto &map = getMiscIndices(misc_reg); + int lower = map.first, upper = map.second; + // NB!: apply architectural masks according to desired register, + // despite possibly getting value from different (mapped) register. + auto val = !upper ? miscRegs[lower] : ((miscRegs[lower] & mask(32)) + |(miscRegs[upper] << 32)); + if (val & reg.res0()) { + DPRINTF(MiscRegs, "Reading MiscReg %s with set res0 bits: %#x\n", + miscRegName[misc_reg], val & reg.res0()); + } + if ((val & reg.res1()) != reg.res1()) { + DPRINTF(MiscRegs, "Reading MiscReg %s with clear res1 bits: %#x\n", + miscRegName[misc_reg], (val & reg.res1()) ^ reg.res1()); + } + return (val & ~reg.raz()) | reg.rao(); // enforce raz/rao } @@ -814,17 +829,20 @@ ISA::setMiscRegNoEffect(int misc_reg, const MiscReg &val) { assert(misc_reg < NumMiscRegs); - auto regs = getMiscIndices(misc_reg); - int lower = regs.first, upper = regs.second; + const auto ® = lookUpMiscReg[misc_reg]; // bit masks + const auto &map = getMiscIndices(misc_reg); + int lower = map.first, upper = map.second; + + auto v = (val & ~reg.wi()) | reg.rao(); if (upper > 0) { - miscRegs[lower] = bits(val, 31, 0); - miscRegs[upper] = bits(val, 63, 32); + miscRegs[lower] = bits(v, 31, 0); + miscRegs[upper] = bits(v, 63, 32); DPRINTF(MiscRegs, "Writing to misc reg %d (%d:%d) : %#x\n", - misc_reg, lower, upper, val); + misc_reg, lower, upper, v); } else { - miscRegs[lower] = val; + miscRegs[lower] = v; DPRINTF(MiscRegs, "Writing to misc reg %d (%d) : %#x\n", - misc_reg, lower, val); + misc_reg, lower, v); } } diff --git a/src/arch/arm/isa.hh b/src/arch/arm/isa.hh index 2241be725..d903ed06a 100644 --- a/src/arch/arm/isa.hh +++ b/src/arch/arm/isa.hh @@ -89,10 +89,26 @@ namespace ArmISA bool haveLargeAsid64; uint8_t physAddrRange64; - /** Register translation entry used in lookUpMiscReg */ + /** MiscReg metadata **/ struct MiscRegLUTEntry { uint32_t lower; // Lower half mapped to this register uint32_t upper; // Upper half mapped to this register + uint64_t _reset; // value taken on reset (i.e. initialization) + uint64_t _res0; // reserved + uint64_t _res1; // reserved + uint64_t _raz; // read as zero (fixed at 0) + uint64_t _rao; // read as one (fixed at 1) + public: + MiscRegLUTEntry() : + lower(0), upper(0), + _reset(0), _res0(0), _res1(0), _raz(0), _rao(0) {} + uint64_t reset() const { return _reset; } + uint64_t res0() const { return _res0; } + uint64_t res1() const { return _res1; } + uint64_t raz() const { return _raz; } + uint64_t rao() const { return _rao; } + // raz/rao implies writes ignored + uint64_t wi() const { return _raz | _rao; } }; /** Metadata table accessible via the value of the register */ @@ -107,6 +123,22 @@ namespace ArmISA entry.upper = u; return *this; } + chain res0(uint64_t mask) const { + entry._res0 = mask; + return *this; + } + chain res1(uint64_t mask) const { + entry._res1 = mask; + return *this; + } + chain raz(uint64_t mask) const { + entry._raz = mask; + return *this; + } + chain rao(uint64_t mask) const { + entry._rao = mask; + return *this; + } MiscRegLUTEntryInitializer(struct MiscRegLUTEntry &e) : entry(e) {} -- 2.30.2