diff options
Diffstat (limited to 'src/arch/arm')
-rw-r--r-- | src/arch/arm/isa.hh | 21 | ||||
-rw-r--r-- | src/arch/arm/utility.cc | 23 |
2 files changed, 37 insertions, 7 deletions
diff --git a/src/arch/arm/isa.hh b/src/arch/arm/isa.hh index 60c572833..a3e89b544 100644 --- a/src/arch/arm/isa.hh +++ b/src/arch/arm/isa.hh @@ -699,15 +699,28 @@ namespace ArmISA } template<> -struct initRenameMode<ArmISA::ISA> +struct RenameMode<ArmISA::ISA> { - static Enums::VecRegRenameMode mode(const ArmISA::ISA* isa) + static Enums::VecRegRenameMode + init(const ArmISA::ISA* isa) { return isa->vecRegRenameMode(); } - static bool equals(const ArmISA::ISA* isa1, const ArmISA::ISA* isa2) + + static Enums::VecRegRenameMode + mode(const ArmISA::PCState& pc) + { + if (pc.aarch64()) { + return Enums::Full; + } else { + return Enums::Elem; + } + } + + static bool + equalsInit(const ArmISA::ISA* isa1, const ArmISA::ISA* isa2) { - return mode(isa1) == mode(isa2); + return init(isa1) == init(isa2); } }; diff --git a/src/arch/arm/utility.cc b/src/arch/arm/utility.cc index 175fd7c00..11c3479c6 100644 --- a/src/arch/arm/utility.cc +++ b/src/arch/arm/utility.cc @@ -145,6 +145,24 @@ skipFunction(ThreadContext *tc) } } +static void +copyVecRegs(ThreadContext *src, ThreadContext *dest) +{ + auto src_mode = RenameMode<ArmISA::ISA>::mode(src->pcState()); + + // The way vector registers are copied (VecReg vs VecElem) is relevant + // in the O3 model only. + if (src_mode == Enums::Full) { + for (auto idx = 0; idx < NumVecRegs; idx++) + dest->setVecRegFlat(idx, src->readVecRegFlat(idx)); + } else { + for (auto idx = 0; idx < NumVecRegs; idx++) + for (auto elem_idx = 0; elem_idx < NumVecElemPerVecReg; elem_idx++) + dest->setVecElemFlat( + idx, elem_idx, src->readVecElemFlat(idx, elem_idx)); + } +} + void copyRegs(ThreadContext *src, ThreadContext *dest) { @@ -154,15 +172,14 @@ copyRegs(ThreadContext *src, ThreadContext *dest) for (int i = 0; i < NumFloatRegs; i++) dest->setFloatRegBitsFlat(i, src->readFloatRegBitsFlat(i)); - for (int i = 0; i < NumVecRegs; i++) - dest->setVecRegFlat(i, src->readVecRegFlat(i)); - for (int i = 0; i < NumCCRegs; i++) dest->setCCReg(i, src->readCCReg(i)); for (int i = 0; i < NumMiscRegs; i++) dest->setMiscRegNoEffect(i, src->readMiscRegNoEffect(i)); + copyVecRegs(src, dest); + // setMiscReg "with effect" will set the misc register mapping correctly. // e.g. updateRegMap(val) dest->setMiscReg(MISCREG_CPSR, src->readMiscRegNoEffect(MISCREG_CPSR)); |