<html><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; ">Hi Devang,<div><br></div><div>Looks like this patch is miscompiling some tests. Please look into it.</div><div><br></div><div><span class="Apple-style-span" style="font-family: -webkit-monospace; font-size: 11px; ">New Test Failures:<br>SPEC/CFP2006/447.dealII/447.dealII [LLC compile, LLC-BETA compile, JIT codegen, , LLC, LLC-BETA] <br>SPEC/CINT2000/252.eon/252.eon [LLC compile, LLC-BETA compile, JIT codegen, LLC, LLC-BETA, JIT]</span></div><div><font class="Apple-style-span" face="-webkit-monospace" size="3"><span class="Apple-style-span" style="font-size: 11px;"><br></span></font></div><div><font class="Apple-style-span" face="-webkit-monospace" size="3"><span class="Apple-style-span" style="font-size: 11px;">I'll revert it for now.</span></font></div><div><font class="Apple-style-span" face="-webkit-monospace" size="3"><span class="Apple-style-span" style="font-size: 11px;"><br></span></font></div><div><font class="Apple-style-span" face="-webkit-monospace" size="3"><span class="Apple-style-span" style="font-size: 11px;">Evan</span></font></div><div><font class="Apple-style-span" face="-webkit-monospace" size="3"><span class="Apple-style-span" style="font-size: 11px;"><br></span></font><div><div>On Aug 15, 2008, at 2:21 PM, Devang Patel wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div>Author: dpatel<br>Date: Fri Aug 15 16:21:34 2008<br>New Revision: 54821<br><br>URL: <a href="http://llvm.org/viewvc/llvm-project?rev=54821&view=rev">http://llvm.org/viewvc/llvm-project?rev=54821&view=rev</a><br>Log:<br>Reapply 54786. Add overflow and number of mantissa bits checks.<br><br>Modified:<br>    llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp<br>    llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll<br><br>Modified: llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp<br>URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp?rev=54821&r1=54820&r2=54821&view=diff">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp?rev=54821&r1=54820&r2=54821&view=diff</a><br><br>==============================================================================<br>--- llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp (original)<br>+++ llvm/trunk/lib/Transforms/Scalar/LoopStrengthReduce.cpp Fri Aug 15 16:21:34 2008<br>@@ -45,6 +45,7 @@<br> STATISTIC(NumInserted,    "Number of PHIs inserted");<br> STATISTIC(NumVariable,    "Number of PHIs with variable strides");<br> STATISTIC(NumEliminated , "Number of strides eliminated");<br>+STATISTIC(NumShadow , "Number of Shadow IVs optimized");<br><br> namespace {<br><br>@@ -177,8 +178,13 @@<br>                                   IVStrideUse* &CondUse,<br>                                   const SCEVHandle* &CondStride);<br>     void OptimizeIndvars(Loop *L);<br>+<br>+    /// OptimizeShadowIV - If IV is used in a int-to-float cast<br>+    /// inside the loop then try to eliminate the cast opeation.<br>+    void OptimizeShadowIV(Loop *L, ICmpInst *Cond,<br>+                          const SCEVHandle *&CondStride);<br>     bool FindIVUserForCond(ICmpInst *Cond, IVStrideUse *&CondUse,<br>-                       const SCEVHandle *&CondStride);<br>+                           const SCEVHandle *&CondStride);<br>     bool RequiresTypeConversion(const Type *Ty, const Type *NewTy);<br>     unsigned CheckForIVReuse(bool, bool, const SCEVHandle&,<br>                              IVExpr&, const Type*,<br>@@ -1689,6 +1695,115 @@<br>   return Cond;<br> }<br><br>+/// OptimizeShadowIV - If IV is used in a int-to-float cast<br>+/// inside the loop then try to eliminate the cast opeation.<br>+void LoopStrengthReduce::OptimizeShadowIV(Loop *L, ICmpInst *Cond,<br>+                                          const SCEVHandle *&CondStride) {<br>+<br>+  const SCEVConstant *SC = dyn_cast<SCEVConstant>(*CondStride);<br>+  if (!SC) return;<br>+<br>+  SCEVHandle IterationCount = SE->getIterationCount(L);<br>+  if (isa<SCEVCouldNotCompute>(IterationCount))<br>+    return;<br>+<br>+  for (unsigned Stride = 0, e = StrideOrder.size(); Stride != e;<br>+       ++Stride) {<br>+    std::map<SCEVHandle, IVUsersOfOneStride>::iterator SI = <br>+      IVUsesByStride.find(StrideOrder[Stride]);<br>+    assert(SI != IVUsesByStride.end() && "Stride doesn't exist!");<br>+<br>+    for (std::vector<IVStrideUse>::iterator UI = SI->second.Users.begin(),<br>+           E = SI->second.Users.end(); UI != E; /* empty */) {<br>+      std::vector<IVStrideUse>::iterator CandidateUI = UI;<br>+      UI++;<br>+      Instruction *ShadowUse = CandidateUI->User;<br>+      const Type *DestTy = NULL;<br>+<br>+      /* If shadow use is a int->float cast then insert a second IV<br>+         to elminate this cast.<br>+<br>+           for (unsigned i = 0; i < n; ++i) <br>+             foo((double)i);<br>+<br>+         is trnasformed into<br>+<br>+           double d = 0.0;<br>+           for (unsigned i = 0; i < n; ++i, ++d) <br>+             foo(d);<br>+      */<br>+      UIToFPInst *UCast = dyn_cast<UIToFPInst>(CandidateUI->User);<br>+      if (UCast) <br>+        DestTy = UCast->getDestTy();<br>+      else {<br>+        SIToFPInst *SCast = dyn_cast<SIToFPInst>(CandidateUI->User);<br>+        if (!SCast) continue;<br>+        DestTy = SCast->getDestTy();<br>+      }<br>+      <br>+      PHINode *PH = dyn_cast<PHINode>(ShadowUse->getOperand(0));<br>+      if (!PH) continue;<br>+      if (PH->getNumIncomingValues() != 2) continue;<br>+<br>+      const Type *SrcTy = PH->getType();<br>+      int Mantissa = DestTy->getFPMantissaWidth();<br>+      if (Mantissa == -1) continue; <br>+      if ((int)TD->getTypeSizeInBits(SrcTy) > Mantissa)<br>+        continue;<br>+<br>+      unsigned Entry, Latch;<br>+      if (PH->getIncomingBlock(0) == L->getLoopPreheader()) {<br>+        Entry = 0;<br>+        Latch = 1;<br>+      } else {<br>+        Entry = 1;<br>+        Latch = 0;<br>+      }<br>+        <br>+      ConstantInt *Init = dyn_cast<ConstantInt>(PH->getIncomingValue(Entry));<br>+      if (!Init) continue;<br>+      ConstantFP *NewInit = ConstantFP::get(DestTy, Init->getZExtValue());<br>+<br>+      BinaryOperator *Incr = <br>+        dyn_cast<BinaryOperator>(PH->getIncomingValue(Latch));<br>+      if (!Incr) continue;<br>+      if (Incr->getOpcode() != Instruction::Add<br>+          && Incr->getOpcode() != Instruction::Sub)<br>+        continue;<br>+<br>+      /* Initialize new IV, double d = 0.0 in above example. */<br>+      ConstantInt *C = NULL;<br>+      if (Incr->getOperand(0) == PH)<br>+        C = dyn_cast<ConstantInt>(Incr->getOperand(1));<br>+      else if (Incr->getOperand(1) == PH)<br>+        C = dyn_cast<ConstantInt>(Incr->getOperand(0));<br>+      else<br>+        continue;<br>+<br>+      if (!C) continue;<br>+<br>+      /* Add new PHINode. */<br>+      PHINode *NewPH = PHINode::Create(DestTy, "IV.S.", PH);<br>+<br>+      /* create new icnrement. '++d' in above example. */<br>+      ConstantFP *CFP = ConstantFP::get(DestTy, C->getZExtValue());<br>+      BinaryOperator *NewIncr = <br>+        BinaryOperator::Create(Incr->getOpcode(),<br>+                               NewPH, CFP, "IV.S.next.", Incr);<br>+<br>+      NewPH->addIncoming(NewInit, PH->getIncomingBlock(Entry));<br>+      NewPH->addIncoming(NewIncr, PH->getIncomingBlock(Latch));<br>+<br>+      /* Remove cast operation */<br>+      ShadowUse->replaceAllUsesWith(NewPH);<br>+      ShadowUse->eraseFromParent();<br>+      SI->second.Users.erase(CandidateUI);<br>+      NumShadow++;<br>+      break;<br>+    }<br>+  }<br>+}<br>+<br> // OptimizeIndvars - Now that IVUsesByStride is set up with all of the indvar<br> // uses in the loop, look to see if we can eliminate some, in favor of using<br> // common indvars for the different uses.<br>@@ -1716,6 +1831,8 @@<br>   if (!FindIVUserForCond(Cond, CondUse, CondStride))<br>     return; // setcc doesn't use the IV.<br><br>+  OptimizeShadowIV(L, Cond, CondStride);<br>+<br>   // If possible, change stride and operands of the compare instruction to<br>   // eliminate one stride.<br>   Cond = ChangeCompareStride(L, Cond, CondUse, CondStride);<br><br>Modified: llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll<br>URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll?rev=54821&r1=54820&r2=54821&view=diff">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll?rev=54821&r1=54820&r2=54821&view=diff</a><br><br>==============================================================================<br>--- llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll (original)<br>+++ llvm/trunk/test/Transforms/LoopStrengthReduce/2008-08-14-ShadowIV.ll Fri Aug 15 16:21:34 2008<br>@@ -0,0 +1,99 @@<br>+; RUN: llvm-as < %s | opt -loop-reduce | llvm-dis | grep "phi double" | count 1<br>+<br>+define void @foobar(i32 %n) nounwind {<br>+entry:<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>icmp eq i32 %n, 0<span class="Apple-tab-span" style="white-space:pre">   </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1>:0 [#uses=2]<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>br i1 %0, label %return, label %bb.nph<br>+<br>+bb.nph:<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %entry<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>%umax = select i1 %0, i32 1, i32 %n<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>br label %bb<br>+<br>+bb:<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %bb.nph<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>%i.03 = phi i32 [ 0, %bb.nph ], [ %indvar.next, %bb ]<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=3]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>tail call void @bar( i32 %i.03 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>uitofp i32 %i.03 to double<span class="Apple-tab-span" style="white-space:pre">  </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <double>:1 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">     </span>tail call void @foo( double %1 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>%indvar.next = add i32 %i.03, 1<span class="Apple-tab-span" style="white-space:pre">     </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=2]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>%exitcond = icmp eq i32 %indvar.next, %umax<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1> [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>br i1 %exitcond, label %return, label %bb<br>+<br>+return:<span class="Apple-tab-span" style="white-space:pre">      </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %entry<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>ret void<br>+}<br>+<br>+; Unable to eliminate cast because the mantissa bits for double are not enough<br>+; to hold all of i64 IV bits.<br>+define void @foobar2(i64 %n) nounwind {<br>+entry:<br>+<span class="Apple-tab-span" style="white-space:pre">      </span>icmp eq i64 %n, 0<span class="Apple-tab-span" style="white-space:pre">   </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1>:0 [#uses=2]<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>br i1 %0, label %return, label %bb.nph<br>+<br>+bb.nph:<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %entry<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>%umax = select i1 %0, i64 1, i64 %n<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i64> [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>br label %bb<br>+<br>+bb:<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %bb.nph<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>%i.03 = phi i64 [ 0, %bb.nph ], [ %indvar.next, %bb ]<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i64> [#uses=3]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>trunc i64 %i.03 to i32<span class="Apple-tab-span" style="white-space:pre">      </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32>:1 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>tail call void @bar( i32 %1 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>uitofp i64 %i.03 to double<span class="Apple-tab-span" style="white-space:pre">  </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <double>:2 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">     </span>tail call void @foo( double %2 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>%indvar.next = add i64 %i.03, 1<span class="Apple-tab-span" style="white-space:pre">     </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i64> [#uses=2]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>%exitcond = icmp eq i64 %indvar.next, %umax<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1> [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>br i1 %exitcond, label %return, label %bb<br>+<br>+return:<span class="Apple-tab-span" style="white-space:pre">      </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %entry<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>ret void<br>+}<br>+<br>+; Unable to eliminate cast due to potentional overflow.<br>+define void @foobar3() nounwind {<br>+entry:<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>tail call i32 (...)* @nn( ) nounwind<span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32>:0 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>icmp eq i32 %0, 0<span class="Apple-tab-span" style="white-space:pre">   </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1>:1 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>br i1 %1, label %return, label %bb<br>+<br>+bb:<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %entry<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>%i.03 = phi i32 [ 0, %entry ], [ %3, %bb ]<span class="Apple-tab-span" style="white-space:pre">  </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=3]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>tail call void @bar( i32 %i.03 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>uitofp i32 %i.03 to double<span class="Apple-tab-span" style="white-space:pre">  </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <double>:2 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">     </span>tail call void @foo( double %2 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>add i32 %i.03, 1<span class="Apple-tab-span" style="white-space:pre">    </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32>:3 [#uses=2]<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>tail call i32 (...)* @nn( ) nounwind<span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32>:4 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>icmp ugt i32 %4, %3<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1>:5 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>br i1 %5, label %bb, label %return<br>+<br>+return:<span class="Apple-tab-span" style="white-space:pre">     </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %entry<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>ret void<br>+}<br>+<br>+; Unable to eliminate cast due to overflow.<br>+define void @foobar4() nounwind {<br>+entry:<br>+<span class="Apple-tab-span" style="white-space:pre">       </span>br label %bb.nph<br>+<br>+bb.nph:<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %entry<br>+<span class="Apple-tab-span" style="white-space:pre"> </span>br label %bb<br>+<br>+bb:<span class="Apple-tab-span" style="white-space:pre">       </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %bb.nph<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>%i.03 = phi i8 [ 0, %bb.nph ], [ %indvar.next, %bb ]<span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=3]<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>%tmp2 = sext i8 %i.03 to i32<span class="Apple-tab-span" style="white-space:pre">        </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32>:0 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>tail call void @bar( i32 %tmp2 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">        </span>%tmp3 = uitofp i8 %i.03 to double<span class="Apple-tab-span" style="white-space:pre">   </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <double>:1 [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">     </span>tail call void @foo( double %tmp3 ) nounwind<br>+<span class="Apple-tab-span" style="white-space:pre">     </span>%indvar.next = add i8 %i.03, 1<span class="Apple-tab-span" style="white-space:pre">      </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i32> [#uses=2]<br>+        %tmp = sext i8 %indvar.next to i32<br>+<span class="Apple-tab-span" style="white-space:pre">  </span>%exitcond = icmp eq i32 %tmp, 32767<span class="Apple-tab-span" style="white-space:pre"> </span><span class="Apple-tab-span" style="white-space:pre">    </span>; <i1> [#uses=1]<br>+<span class="Apple-tab-span" style="white-space:pre">   </span>br i1 %exitcond, label %return, label %bb<br>+<br>+return:<span class="Apple-tab-span" style="white-space:pre">      </span><span class="Apple-tab-span" style="white-space:pre">    </span>; preds = %bb, %entry<br>+<span class="Apple-tab-span" style="white-space:pre">    </span>ret void<br>+}<br>+<br>+declare void @bar(i32)<br>+<br>+declare void @foo(double)<br>+<br>+declare i32 @nn(...)<br>+<br><br><br>_______________________________________________<br>llvm-commits mailing list<br><a href="mailto:llvm-commits@cs.uiuc.edu">llvm-commits@cs.uiuc.edu</a><br><a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits">http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits</a><br></div></blockquote></div><br></div></body></html>