ARM: correctly determine final tBX_LR in Thumb1 functions
authorTim Northover <tnorthover@apple.com>
Tue, 14 Jan 2014 22:53:28 +0000 (22:53 +0000)
committerTim Northover <tnorthover@apple.com>
Tue, 14 Jan 2014 22:53:28 +0000 (22:53 +0000)
The changes caused by folding an sp-adjustment into a "pop" previously
disrupted the forward search for the final real instruction in a
terminating block. This switches to a backward search (skipping debug
instrs).

This fixes PR18399.

Patch by Zhaoshi.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@199266 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Target/ARM/Thumb1FrameLowering.cpp
test/CodeGen/ARM/fold-stack-adjust.ll

index d8546dac31d083003935878e6749c93ec8a57da3..2a587dd25b0736e7cc1c163bdd7995a22e60b41e 100644 (file)
@@ -304,9 +304,9 @@ void Thumb1FrameLowering::emitEpilogue(MachineFunction &MF,
     // we need to update the SP after popping the value. Therefore, we
     // pop the old LR into R3 as a temporary.
 
-    // Move back past the callee-saved register restoration
-    while (MBBI != MBB.end() && isCSRestore(MBBI, CSRegs))
-      ++MBBI;
+    // Get the last instruction, tBX_RET
+    MBBI = MBB.getLastNonDebugInstr();
+    assert (MBBI->getOpcode() == ARM::tBX_RET);
     // Epilogue for vararg functions: pop LR to R3 and branch off it.
     AddDefaultPred(BuildMI(MBB, MBBI, dl, TII.get(ARM::tPOP)))
       .addReg(ARM::R3, RegState::Define);
index 81d94d16c15254157b380d139d0bf001647a9ccc..feac793f4f8aa422f5e0f23dc8792ebe428b17c4 100644 (file)
@@ -162,3 +162,26 @@ end:
   ; the correct edge-case (first inst in block is correct one to adjust).
   ret void
 }
+
+define void @test_varsize(...) minsize {
+; CHECK-T1-LABEL: test_varsize:
+; CHECK-T1: sub        sp, #16
+; CHECK-T1: push       {r2, r3, r4, r5, r7, lr}
+; ...
+; CHECK-T1: pop        {r2, r3, r4, r5, r7}
+; CHECK-T1: pop        {r3}
+; CHECK-T1: add        sp, #16
+; CHECK-T1: bx r3
+
+; CHECK-LABEL: test_varsize:
+; CHECK: sub   sp, #16
+; CHECK: push  {r5, r6, r7, lr}
+; ...
+; CHECK: pop.w {r2, r3, r7, lr}
+; CHECK: add   sp, #16
+; CHECK: bx    lr
+
+  %var = alloca i8, i32 8
+  call void @bar(i8* %var)
+  ret void
+}