[LSR] Attempt to increase the accuracy of LSR's setup cost
authorDavid Green <david.green@arm.com>
Thu, 7 Mar 2019 13:44:40 +0000 (13:44 +0000)
committerDavid Green <david.green@arm.com>
Thu, 7 Mar 2019 13:44:40 +0000 (13:44 +0000)
commitffc922ec35f8991d5c97b89ae4fe18c15684b1d6
tree6f441e4f2193ec551ae35c0f425bc4727fb2a947
parent5caba3069e8185b2c8225080c95755ea906b624e
[LSR] Attempt to increase the accuracy of LSR's setup cost

In some loops, we end up generating loop induction variables that look like:
  {(-1 * (zext i16 (%i0 * %i1) to i32))<nsw>,+,1}
As opposed to the simpler:
  {(zext i16 (%i0 * %i1) to i32),+,-1}
i.e we count up from -limit to 0, not the simpler counting down from limit to
0. This is because the scores, as LSR calculates them, are the same and the
second is filtered in place of the first. We end up with a redundant SUB from 0
in the code.

This patch tries to make the calculation of the setup cost a little more
thoroughly, recursing into the scev members to better approximate the setup
required. The cost function for comparing LSR costs is:

return std::tie(C1.NumRegs, C1.AddRecCost, C1.NumIVMuls, C1.NumBaseAdds,
                C1.ScaleCost, C1.ImmCost, C1.SetupCost) <
       std::tie(C2.NumRegs, C2.AddRecCost, C2.NumIVMuls, C2.NumBaseAdds,
                C2.ScaleCost, C2.ImmCost, C2.SetupCost);
So this will only alter results if none of the other variables turn out to be
different.

Differential Revision: https://reviews.llvm.org/D58770

llvm-svn: 355597
llvm/lib/Transforms/Scalar/LoopStrengthReduce.cpp
llvm/test/CodeGen/ARM/lsr-setupcost.ll [new file with mode: 0644]
llvm/test/CodeGen/Hexagon/swp-carried-1.ll
llvm/test/CodeGen/Hexagon/swp-epilog-phi5.ll
llvm/test/Transforms/LoopStrengthReduce/two-combinations-bug.ll