[llvm] r236650 - Fix incorrect kill flags in fastisel.

Pete Cooper peter_cooper at apple.com
Wed May 6 15:09:29 PDT 2015


Author: pete
Date: Wed May  6 17:09:29 2015
New Revision: 236650

URL: http://llvm.org/viewvc/llvm-project?rev=236650&view=rev
Log:
Fix incorrect kill flags in fastisel.

If called twice in the same BB on the same constant, FastISel::fastEmit_ri_ was marking the materialized vreg as killed on each use, instead of only the last use.

Change this to only mark the last use as killed by making earlier uses check if the vreg is already used elsewhere.

Added:
    llvm/trunk/test/CodeGen/ARM/fast-isel-shift-materialize.ll
Modified:
    llvm/trunk/lib/CodeGen/SelectionDAG/FastISel.cpp

Modified: llvm/trunk/lib/CodeGen/SelectionDAG/FastISel.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/FastISel.cpp?rev=236650&r1=236649&r2=236650&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/SelectionDAG/FastISel.cpp (original)
+++ llvm/trunk/lib/CodeGen/SelectionDAG/FastISel.cpp Wed May  6 17:09:29 2015
@@ -1675,6 +1675,7 @@ unsigned FastISel::fastEmit_ri_(MVT VT,
   if (ResultReg)
     return ResultReg;
   unsigned MaterialReg = fastEmit_i(ImmType, ImmType, ISD::Constant, Imm);
+  bool IsImmKill = true;
   if (!MaterialReg) {
     // This is a bit ugly/slow, but failing here means falling out of
     // fast-isel, which would be very slow.
@@ -1683,9 +1684,12 @@ unsigned FastISel::fastEmit_ri_(MVT VT,
     MaterialReg = getRegForValue(ConstantInt::get(ITy, Imm));
     if (!MaterialReg)
       return 0;
+    // If this constant was already materialized, then we don't want to kill it.
+    // In this case we will have a use.
+    if (!MRI.use_empty(MaterialReg))
+      IsImmKill = false;
   }
-  return fastEmit_rr(VT, VT, Opcode, Op0, Op0IsKill, MaterialReg,
-                     /*IsKill=*/true);
+  return fastEmit_rr(VT, VT, Opcode, Op0, Op0IsKill, MaterialReg, IsImmKill);
 }
 
 unsigned FastISel::createResultReg(const TargetRegisterClass *RC) {

Added: llvm/trunk/test/CodeGen/ARM/fast-isel-shift-materialize.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/ARM/fast-isel-shift-materialize.ll?rev=236650&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/ARM/fast-isel-shift-materialize.ll (added)
+++ llvm/trunk/test/CodeGen/ARM/fast-isel-shift-materialize.ll Wed May  6 17:09:29 2015
@@ -0,0 +1,25 @@
+; RUN: llc %s -o - -verify-machineinstrs -fast-isel=true | FileCheck %s
+
+target datalayout = "e-m:o-p:32:32-f64:32:64-v64:32:64-v128:32:128-a:0:32-n32-S32"
+target triple = "thumbv7-apple-ios8.0.0"
+
+; When materializing the '2' for the shifts below, the second shift kills the vreg
+; we materialize in to.  However, the first shift was also killing that vreg.
+; This fails the machine verifier because the second use then thinks its reading an
+; undefined register.
+
+; CHECK: lsr.w
+; CHECK: lsr.w
+
+declare void @foo(i32, i32)
+
+; Function Attrs: minsize
+define i32 @test(i32 %tmp3, i32 %tmp9) #0 {
+bb:
+  %tmp4 = lshr i32 %tmp3, 2
+  %tmp10 = lshr i32 %tmp9, 2
+  call void @foo(i32 %tmp10, i32 %tmp4)
+  unreachable
+}
+
+attributes #0 = { minsize }





More information about the llvm-commits mailing list