diff options
author | Dylan McKay <me@dylanmckay.io> | 2019-01-20 03:41:08 +0000 |
---|---|---|
committer | Dylan McKay <me@dylanmckay.io> | 2019-01-20 03:41:08 +0000 |
commit | 6afef286d92eb37798928d01bfe6139f005e5c38 (patch) | |
tree | 89280f554f8286967baa5b339dc391027778657f /llvm/lib/Target/AVR | |
parent | 52846ab09a02280f8e79aa56bac557ae36255e5d (diff) | |
download | bcm5719-llvm-6afef286d92eb37798928d01bfe6139f005e5c38.tar.gz bcm5719-llvm-6afef286d92eb37798928d01bfe6139f005e5c38.zip |
[AVR] Fix codegen bug in 16-bit loads
Prior to this patch, the AVR::LDWRdPtr instruction was always lowered to
instructions of this pattern:
ld $GPR8, [PTR:XYZ]+
ld $GPR8, [PTR]+1
This has a problem; the [PTR] is incremented in-place once, but never
decremented.
Future uses of the same pointer will use the now clobbered value,
leading to the pointer being incorrect by an offset of one.
This patch modifies the expansion code of the LDWRdPtr pseudo
instruction so that the pointer variable is not silently clobbered in
future uses in the same live range.
Bug first reported by Keshav Kini.
Patch by Kaushik Phatak.
llvm-svn: 351673
Diffstat (limited to 'llvm/lib/Target/AVR')
-rw-r--r-- | llvm/lib/Target/AVR/AVRExpandPseudoInsts.cpp | 10 | ||||
-rw-r--r-- | llvm/lib/Target/AVR/AVRISelLowering.cpp | 3 |
2 files changed, 5 insertions, 8 deletions
diff --git a/llvm/lib/Target/AVR/AVRExpandPseudoInsts.cpp b/llvm/lib/Target/AVR/AVRExpandPseudoInsts.cpp index 60924c23901..c45b2d0e39c 100644 --- a/llvm/lib/Target/AVR/AVRExpandPseudoInsts.cpp +++ b/llvm/lib/Target/AVR/AVRExpandPseudoInsts.cpp @@ -582,8 +582,8 @@ bool AVRExpandPseudo::expand<AVR::LDWRdPtr>(Block &MBB, BlockIt MBBI) { unsigned TmpReg = 0; // 0 for no temporary register unsigned SrcReg = MI.getOperand(1).getReg(); bool SrcIsKill = MI.getOperand(1).isKill(); - OpLo = AVR::LDRdPtrPi; - OpHi = AVR::LDRdPtr; + OpLo = AVR::LDRdPtr; + OpHi = AVR::LDDRdPtrQ; TRI->splitReg(DstReg, DstLoReg, DstHiReg); // Use a temporary register if src and dst registers are the same. @@ -596,8 +596,7 @@ bool AVRExpandPseudo::expand<AVR::LDWRdPtr>(Block &MBB, BlockIt MBBI) { // Load low byte. auto MIBLO = buildMI(MBB, MBBI, OpLo) .addReg(CurDstLoReg, RegState::Define) - .addReg(SrcReg, RegState::Define) - .addReg(SrcReg); + .addReg(SrcReg, RegState::Define); // Push low byte onto stack if necessary. if (TmpReg) @@ -606,7 +605,8 @@ bool AVRExpandPseudo::expand<AVR::LDWRdPtr>(Block &MBB, BlockIt MBBI) { // Load high byte. auto MIBHI = buildMI(MBB, MBBI, OpHi) .addReg(CurDstHiReg, RegState::Define) - .addReg(SrcReg, getKillRegState(SrcIsKill)); + .addReg(SrcReg, getKillRegState(SrcIsKill)) + .addImm(1); if (TmpReg) { // Move the high byte into the final destination. diff --git a/llvm/lib/Target/AVR/AVRISelLowering.cpp b/llvm/lib/Target/AVR/AVRISelLowering.cpp index 42a6b46ed7f..3116eb2a503 100644 --- a/llvm/lib/Target/AVR/AVRISelLowering.cpp +++ b/llvm/lib/Target/AVR/AVRISelLowering.cpp @@ -1278,7 +1278,6 @@ SDValue AVRTargetLowering::LowerCall(TargetLowering::CallLoweringInfo &CLI, } // Add a register mask operand representing the call-preserved registers. - const AVRTargetMachine &TM = (const AVRTargetMachine &)getTargetMachine(); const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo(); const uint32_t *Mask = TRI->getCallPreservedMask(DAG.getMachineFunction(), CallConv); @@ -1441,7 +1440,6 @@ MachineBasicBlock *AVRTargetLowering::insertShift(MachineInstr &MI, bool HasRepeatedOperand = false; MachineFunction *F = BB->getParent(); MachineRegisterInfo &RI = F->getRegInfo(); - const AVRTargetMachine &TM = (const AVRTargetMachine &)getTargetMachine(); const TargetInstrInfo &TII = *Subtarget.getInstrInfo(); DebugLoc dl = MI.getDebugLoc(); @@ -1582,7 +1580,6 @@ static bool isCopyMulResult(MachineBasicBlock::iterator const &I) { // it, but it works for now. MachineBasicBlock *AVRTargetLowering::insertMul(MachineInstr &MI, MachineBasicBlock *BB) const { - const AVRTargetMachine &TM = (const AVRTargetMachine &)getTargetMachine(); const TargetInstrInfo &TII = *Subtarget.getInstrInfo(); MachineBasicBlock::iterator I(MI); ++I; // in any case insert *after* the mul instruction |