[llvm] [AArch64] Fix pairing different types of registers when computing CSRs. (PR #66642)
via llvm-commits
llvm-commits at lists.llvm.org
Sun Oct 15 17:38:48 PDT 2023
================
@@ -195,46 +198,84 @@ static MachineFunction &createFrameHelperMachineFunction(Module *M,
}
/// Emit a store-pair instruction for frame-setup.
+/// If Reg2 is AArch64::NoRegister, emit STR instead.
static void emitStore(MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator Pos,
const TargetInstrInfo &TII, unsigned Reg1, unsigned Reg2,
int Offset, bool IsPreDec) {
+ assert(Reg1 != AArch64::NoRegister);
+ const bool IsPaired = Reg2 != AArch64::NoRegister;
bool IsFloat = AArch64::FPR64RegClass.contains(Reg1);
assert(!(IsFloat ^ AArch64::FPR64RegClass.contains(Reg2)));
unsigned Opc;
- if (IsPreDec)
- Opc = IsFloat ? AArch64::STPDpre : AArch64::STPXpre;
- else
- Opc = IsFloat ? AArch64::STPDi : AArch64::STPXi;
+ if (IsPreDec) {
+ if (IsFloat)
+ Opc = IsPaired ? AArch64::STPDpre : AArch64::STRDpre;
+ else
+ Opc = IsPaired ? AArch64::STPXpre : AArch64::STRXpre;
+ } else {
+ if (IsFloat)
+ Opc = IsPaired ? AArch64::STPDi : AArch64::STRDui;
+ else
+ Opc = IsPaired ? AArch64::STPXi : AArch64::STRXui;
+ }
+ // The implicit scale for Offset is 8.
+ TypeSize Scale(0U, false);
+ unsigned Width;
+ int64_t MinOffset, MaxOffset;
+ bool Success =
+ AArch64InstrInfo::getMemOpInfo(Opc, Scale, Width, MinOffset, MaxOffset);
+ assert(Success && "Invalid Opcode");
+ Offset *= (8 / (int)Scale);
MachineInstrBuilder MIB = BuildMI(MBB, Pos, DebugLoc(), TII.get(Opc));
if (IsPreDec)
MIB.addDef(AArch64::SP);
- MIB.addReg(Reg2)
- .addReg(Reg1)
+ if (IsPaired)
+ MIB.addReg(Reg2);
+ MIB.addReg(Reg1)
.addReg(AArch64::SP)
.addImm(Offset)
.setMIFlag(MachineInstr::FrameSetup);
}
/// Emit a load-pair instruction for frame-destroy.
+/// If Reg2 is AArch64::NoRegister, emit LTR instead.
----------------
kyulee-com wrote:
LTR -> LDR
https://github.com/llvm/llvm-project/pull/66642
More information about the llvm-commits
mailing list