Commit Graph

1200 Commits

Author SHA1 Message Date
Max Kazantsev
8500e487c7 [NFC] Rename variable from Cond to Pred to make it more sound
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@320144 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-08 12:54:32 +00:00
Max Kazantsev
99dd56e4a9 [SCEV] Fix predicate usage in computeExitLimitFromICmp
In this method, we invoke `SimplifyICmpOperands` which takes the `Cond` predicate
by reference and may change it along with `LHS` and `RHS` SCEVs. But then we invoke
`computeShiftCompareExitLimit` with Values from which the SCEVs have been derived,
these Values have not been modified while `Cond` could be.

One of possible outcomes of this is that we may falsely prove that an infinite loop ends
within some finite number of iterations.

In this patch, we save the original `Cond` and pass it along with original operands.
This logic may be removed in future once `computeShiftCompareExitLimit` works
with SCEVs instead of value operands.

Reviewed By: sanjoy
Differential Revision: https://reviews.llvm.org/D40953


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@320142 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-08 12:19:45 +00:00
Max Kazantsev
0c3c7c5485 [SCEV][NFC] Check NoWrap flags before lexicographical comparison of SCEVs
Lexicographical comparison of SCEV trees is potentially expensive for big
expression trees. We can define ordering between them for AddRecs and
N-ary operations by SCEV NoWrap flags to make non-equality check
cheaper.

This change does not prevent grouping eqivalent SCEVs together and is
not supposed to have any meaningful impact on behavior of any transforms.


Reviewed By: sanjoy
Differential Revision: https://reviews.llvm.org/D40645


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319889 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-06 12:44:56 +00:00
Max Kazantsev
3126a95a41 [SCEV][NFC] Share value cache between SCEVs in GroupByComplexity
Current implementation of `compareSCEVComplexity` is being unreasonable with `SCEVUnknown`s:
every time it sees one, it creates a new value cache and tries to prove equality of two values using it.
This cache reallocates and gets lost from SCEV to SCEV.

This patch changes this behavior: now we create one cache for all values and share it between SCEVs.

Reviewed By: sanjoy
Differential Revision: https://reviews.llvm.org/D40597


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319880 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-06 08:58:16 +00:00
Sanjoy Das
c965de5bf8 [SCEV] Use a "Discovered" set instead of a "Visited" set; NFC
Suggested by Max Kazantsev in https://reviews.llvm.org/D39361

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319679 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-04 19:22:01 +00:00
Sanjoy Das
abd6d64d20 [SCEV] A different fix for PR33494
Summary:
I don't think rL309080 is the right fix for PR33494 -- caching ExitLimit only
hides the problem[0].  The real issue is that because of how we forget SCEV
expressions ScalarEvolution::getBackedgeTakenInfo, in the test case for PR33494
computing the backedge for any loop invalidates the trip count for every other
loop.  This effectively makes the SCEV cache useless.

I've instead made the SCEV expression invalidation in
ScalarEvolution::getBackedgeTakenInfo less aggressive to fix this issue.

[0]: One way to think about this is that rL309080 essentially augmented the
backedge-taken-count cache with another equivalent exit-limit cache.  The bug
went away because we were explicitly not clearing the exit-limit cache in
getBackedgeTakenInfo.  But instead of doing all of that, we can just avoid
clearing the backedge-taken-count cache.

Reviewers: mkazantsev, mzolotukhin

Subscribers: mcrosier, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319678 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-04 19:22:00 +00:00
Zachary Turner
9a4e15cb76 Mark all library options as hidden.
These command line options are not intended for public use, and often
don't even make sense in the context of a particular tool anyway. About
90% of them are already hidden, but when people add new options they
forget to hide them, so if you were to make a brand new tool today, link
against one of LLVM's libraries, and run tool -help you would get a
bunch of junk that doesn't make sense for the tool you're writing.

This patch hides these options. The real solution is to not have
libraries defining command line options, but that's a much larger effort
and not something I'm prepared to take on.

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319505 91177308-0d34-0410-b5e6-96231b3b80d8
2017-12-01 00:53:10 +00:00
Max Kazantsev
bee1015aa6 [SCEV][NFC] Remove condition that can never happen due to check few lines above
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319293 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-29 06:10:36 +00:00
Max Kazantsev
e58aca6a43 [SCEV][NFC] More efficient caching in CompareValueComplexity
Currently, we use a set of pairs to cache responces like `CompareValueComplexity(X, Y) == 0`. If we had
proved that `CompareValueComplexity(S1, S2) == 0` and `CompareValueComplexity(S2, S3) == 0`,
this cache does not allow us to prove that `CompareValueComplexity(S1, S3)` is also `0`.

This patch replaces this set with `EquivalenceClasses` that merges Values into equivalence sets so that
any two values from the same set are equal from point of `CompareValueComplexity`. This, in particular,
allows us to prove the fact from example above.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319153 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-28 08:26:43 +00:00
Max Kazantsev
413ec67db6 [SCEV][NFC] More efficient caching in CompareSCEVComplexity
Currently, we use a set of pairs to cache responces like `CompareSCEVComplexity(X, Y) == 0`. If we had
proved that `CompareSCEVComplexity(S1, S2) == 0` and `CompareSCEVComplexity(S2, S3) == 0`,
this cache does not allow us to prove that `CompareSCEVComplexity(S1, S3)` is also `0`.

This patch replaces this set with `EquivalenceClasses` any two values from the same set are equal from
point of `CompareSCEVComplexity`. This, in particular, allows us to prove the fact from example above.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@319149 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-28 07:48:12 +00:00
Jatin Bhateja
081379e8b4 [SCEV] Adding a check on outgoing branches of a terminator instr for SCEVBackedgeConditionFolder, NFC.
Summary:
For a given loop, getLoopLatch returns a non-null value
when a loop has only one latch block. In the modified
context adding an assertion to check that both the outgoing branches of
a terminator instruction (of latch) does not target same header.
+
few minor code reorganization.

Reviewers: jbhateja

Reviewed By: jbhateja

Subscribers: sanjoy

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318997 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-26 15:08:41 +00:00
Jatin Bhateja
0d7d3a3c32 [SCEV] NFC : Removing unnecessary check on outgoing branches of a branch instr.
Summary:
For a given loop, getLoopLatch returns a non-null value
when a loop has only one latch block. In the modified
context a check on both the outgoing branches of a terminator instruction (of latch) to same header is redundant.

Reviewers: jbhateja

Reviewed By: jbhateja

Subscribers: sanjoy

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318991 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-26 02:01:01 +00:00
Max Kazantsev
f66b47b328 [SCEV] Strengthen variance condition in calculateLoopDisposition
Given loops `L1` and `L2` with AddRecs `AR1` and `AR2` varying in them respectively.
When identifying loop disposition of `AR2` w.r.t. `L1`, we only say that it is varying if
`L1` contains `L2`. But there is also a possible situation where `L1` and `L2` are
consecutive sibling loops within the parent loop. In this case, `AR2` is also varying
w.r.t. `L1`, but we don't correctly identify it.

It can lead, for exaple, to attempt of incorrect folding. Consider:
  AR1 = {a,+,b}<L1>
  AR2 = {c,+,d}<L2>
  EXAR2 = sext(AR1)
  MUL = mul AR1, EXAR2
If we incorrectly assume that `EXAR2` is invariant w.r.t. `L1`, we can end up trying to
construct something like: `{a * {c,+,d}<L2>,+,b * {c,+,d}<L2>}<L1>`, which is incorrect
because `AR2` is not available on entrance of `L1`.

Both situations "`L1` contains `L2`" and "`L1` preceeds sibling loop `L2`" can be handled
with one check: "header of `L1` dominates header of `L2`". This patch replaces the old
insufficient check with this one.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318819 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-22 06:21:39 +00:00
Javed Absar
4992987dc4 [SCEV] simplify loop. NFC.
Change loop to range-based



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318401 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-16 13:49:27 +00:00
Reid Kleckner
7983d3bb32 Fix clang -Wsometimes-uninitialized warning in SCEV code
I don't believe this was a problem in practice, as it's likely that the
boolean wasn't checked unless the backend condition was non-null.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318073 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-13 18:43:11 +00:00
Jatin Bhateja
5afa924e80 [SCEV] Handling for ICmp occuring in the evolution chain.
Summary:
 If a compare instruction is same or inverse of the compare in the
 branch of the loop latch, then return a constant evolution node.
 This shall facilitate computations of loop exit counts in cases
 where compare appears in the evolution chain of induction variables.

 Will fix PR 34538

Reviewers: sanjoy, hfinkel, junryoungju

Reviewed By: sanjoy, junryoungju

Subscribers: javed.absar, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@318050 91177308-0d34-0410-b5e6-96231b3b80d8
2017-11-13 16:43:24 +00:00
Sanjoy Das
b500839596 [SCEV] Fix an assertion failure in the max backedge taken count
Max backedge taken count is always expected to be a constant; and this is
usually true by construction -- it is a SCEV expression with constant inputs.
However, if the max backedge expression ends up being computed to be a udiv with
a constant zero denominator[0], SCEV does not fold the result to a constant
since there is no constant it can fold it to (SCEV has no representation for
"infinity" or "undef").

However, in computeMaxBECountForLT we already know the denominator is positive,
and thus at least 1; and we can use this fact to avoid dividing by zero.

[0]: We can end up with a constant zero denominator if the signed range of the
stride is more precise than the unsigned range.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@316615 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-25 21:41:00 +00:00
Sanjoy Das
bc1160282c Add a comment to clarify a future change
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@316614 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-25 21:40:59 +00:00
Sanjoy Das
b5cb868aaa Revert "[ScalarEvolution] Handling for ICmp occuring in the evolution chain."
This reverts commit r316054.  There was some confusion over the review process:
http://lists.llvm.org/pipermail/llvm-commits/Week-of-Mon-20171016/495884.html

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@316129 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-18 22:00:57 +00:00
Jatin Bhateja
b8354dd5d8 [ScalarEvolution] Handling for ICmp occuring in the evolution chain.
Summary:
 If a compare instruction is same or inverse of the compare in the
 branch of the loop latch, then return a constant evolution node.
 Currently scope of evaluation is limited to SCEV computation for
 PHI nodes.

 This shall facilitate computations of loop exit counts in cases
 where compare appears in the evolution chain of induction variables.

 Will fix PR 34538
Reviewers: sanjoy, hfinkel, junryoungju

Reviewed By: junryoungju

Subscribers: javed.absar, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@316054 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-18 01:36:16 +00:00
Sanjoy Das
20768d3f1e Revert "[SCEV] Maintain and use a loop->loop invalidation dependency"
This reverts commit r315713.  It causes PR34968.

I think I know what the problem is, but I don't think I'll have time to fix it
this week.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315962 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-17 01:03:56 +00:00
Anna Thomas
1619b651ca [SCEV] Rename getMaxBECount and update comments. NFC
Post commit review comments at D38825.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315920 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-16 17:47:17 +00:00
Aaron Ballman
1d03d382c1 Reverting r315590; it did not include changes for llvm-tblgen, which is causing link errors for several people.
Error LNK2019 unresolved external symbol "public: void __cdecl `anonymous namespace'::MatchableInfo::dump(void)const " (?dump@MatchableInfo@?A0xf4f1c304@@QEBAXXZ) referenced in function "public: void __cdecl `anonymous namespace'::AsmMatcherEmitter::run(class llvm::raw_ostream &)" (?run@AsmMatcherEmitter@?A0xf4f1c304@@QEAAXAEAVraw_ostream@llvm@@@Z) llvm-tblgen D:\llvm\2017\utils\TableGen\AsmMatcherEmitter.obj 1


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315854 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-15 14:32:27 +00:00
Sanjoy Das
ca020c7486 [SCEV] Maintain and use a loop->loop invalidation dependency
Summary:
This change uses the loop use list added in the previous change to remember the
loops that appear in the trip count expressions of other loops; and uses it in
forgetLoop.  This lets us not scan every loop in the function on a forgetLoop
call.

With this change we no longer invalidate clear out backedge taken counts on
forgetValue.  I think this is fine -- the contract is that SCEV users must call
forgetLoop(L) if their change to the IR could have changed the trip count of L;
solely calling forgetValue on a value feeding into the backedge condition of L
is not enough.  Moreover, I don't think we can strengthen forgetValue to be
sufficient for invalidating trip counts without significantly re-architecting
SCEV.  For instance, if we have the loop:

  I = *Ptr;
  E = I + 10;
  do {
    // ...
  } while (++I != E);

then the backedge taken count of the loop is 9, and it has no reference to
either I or E, i.e. there is no way in SCEV today to re-discover the dependency
of the loop's trip count on E or I.  So a SCEV client cannot change E to (say)
"I + 20", call forgetValue(E) and expect the loop's trip count to be updated.

Reviewers: atrick, sunfish, mkazantsev

Subscribers: mcrosier, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315713 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-13 17:13:44 +00:00
Anna Thomas
7f1eb15289 [SCEV] Teach SCEV to find maxBECount when loop endbound is variant
Summary:
This patch teaches SCEV to calculate the maxBECount when the end bound
of the loop can vary. Note that we cannot calculate the exactBECount.

This will only be done when both conditions are satisfied:
1. the loop termination condition is strictly LT.
2. the IV is proven to not overflow.

This provides more information to users of SCEV and can be used to
improve identification of finite loops.

Reviewers: sanjoy, mkazantsev, silviu.baranga, atrick

Reviewed by: mkazantsev

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315683 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-13 14:30:43 +00:00
Sanjoy Das
ce7f87b95a [SCEV] Maintain loop use lists, and use them in forgetLoop
Summary:
Currently we do not correctly invalidate memoized results for add recurrences
that were created directly (i.e. they were not created from a `Value`).  This
change fixes this by keeping loop use lists and using the loop use lists to
determine which SCEV expressions to invalidate.

Here are some statistics on the number of uses of in the use lists of all loops
on a clang bootstrap (config: release, no asserts):

     Count: 731310
       Min: 1
      Mean: 8.555150
50th %time: 4
95th %tile: 25
99th %tile: 53
       Max: 433

Reviewers: atrick, sunfish, mkazantsev

Subscribers: mcrosier, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315672 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-13 05:50:52 +00:00
Don Hinton
5298935fe7 [dump] Remove NDEBUG from test to enable dump methods [NFC]
Summary:
Add LLVM_FORCE_ENABLE_DUMP cmake option, and use it along with
LLVM_ENABLE_ASSERTIONS to set LLVM_ENABLE_DUMP.

Remove NDEBUG and only use LLVM_ENABLE_DUMP to enable dump methods.

Move definition of LLVM_ENABLE_DUMP from config.h to llvm-config.h so
it'll be picked up by public headers.

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315590 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-12 16:16:06 +00:00
Daniel Neilson
7d7645fe0b [SCEV] Properly handle the case of a non-constant start with a zero accum in ScalarEvolution::createAddRecFromPHIWithCastsImpl
Summary:
 This patch fixes an error in the patch to ScalarEvolution::createAddRecFromPHIWithCastsImpl
made in D37265. In that patch we handle the cases where the either the start or accum values can be
zero after truncation. But, we assume that the start value must be a constant if the accum is
zero. This is clearly an erroneous assumption. This change removes that assumption.

Reviewers: sanjoy, dorit, mkazantsev

Reviewed By: sanjoy

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315491 91177308-0d34-0410-b5e6-96231b3b80d8
2017-10-11 19:05:14 +00:00
Michael Liao
61389a6da0 Remove trailing whitespaces.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@314115 91177308-0d34-0410-b5e6-96231b3b80d8
2017-09-25 16:21:21 +00:00
Daniel Neilson
bd3b41b469 [SCEV] Generalize folding of trunc(x)+n*trunc(y) into folding m*trunc(x)+n*trunc(y)
Summary:
A SCEV such as:
 {%v2,+,((-1 * (trunc i64 (-1 * %v1) to i32)) + (-1 * (trunc i64 %v1 to i32)))}<%loop>

can be folded into, simply, {%v2,+,0}. However, the current code in ::getAddExpr()
will not try to apply the simplification m*trunc(x)+n*trunc(y) -> trunc(trunc(m)*x+trunc(n)*y)
because it only keys off having a non-multiplied trunc as the first term in the simplification.

This patch generalizes this code to try to do a more generic fold of these trunc
expressions.

Reviewers: sanjoy

Reviewed By: sanjoy

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@313988 91177308-0d34-0410-b5e6-96231b3b80d8
2017-09-22 15:47:57 +00:00
Marcello Maggioni
022ffdf29f [ScalarEvolution] Refactor forgetLoop() to improve performance
forgetLoop() has pretty bad performance because it goes over
the same instructions over and over again in particular when
nested loop are involved.
The refactoring changes the function to a not-recursive function
and reusing the allocation for data-structures and the Visited
set.

NFCI

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@312920 91177308-0d34-0410-b5e6-96231b3b80d8
2017-09-11 15:44:20 +00:00
Daniel Neilson
f7dd8e2ac0 [SCEV] Ensure ScalarEvolution::createAddRecFromPHIWithCastsImpl properly handles out of range truncations of the start and accum values
Summary:
 When constructing the predicate P1 in ScalarEvolution::createAddRecFromPHIWithCastsImpl() it is possible
for the PHISCEV from which the predicate is constructed to be a SCEVConstant instead of a SCEVAddRec. If
this happens, then the cast<SCEVAddRec>(PHISCEV) in the code will assert.

 Such a PHISCEV is possible if either the start value or the accumulator value is a constant value
that not equal to its truncated value, and if the truncated value is zero.

 This patch adds tests that demonstrate the cast<> assertion, and fixes this problem by checking
whether the PHISCEV is a constant before constructing the P1 predicate; if it is, then P1 is
equivalent to one of P2 or P3. Additionally, if we know that the start value or accumulator
value are constants then we check whether the P2 and/or P3 predicates are known false at compile
time; if either is, then we bail out of constructing the AddRec.

Reviewers: sanjoy, mkazantsev, silviu.baranga

Reviewed By: mkazantsev

Subscribers: mkazantsev, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@312568 91177308-0d34-0410-b5e6-96231b3b80d8
2017-09-05 19:54:03 +00:00
Alexandre Isoard
3b88873b05 [SCEV] Add URem support to SCEV
In LLVM IR the following code:

    %r = urem <ty> %t, %b

is equivalent to

    %q = udiv <ty> %t, %b
    %s = mul <ty> nuw %q, %b
    %r = sub <ty> nuw %t, %q ; (t / b) * b + (t % b) = t

As UDiv, Mul and Sub are already supported by SCEV, URem can be implemented
with minimal effort using that relation:

    %r --> (-%b * (%t /u %b)) + %t

We implement two special cases:

  - if %b is 1, the result is always 0
  - if %b is a power-of-two, we produce a zext/trunc based expression instead

That is, the following code:

    %r = urem i32 %t, 65536

Produces:

    %r --> (zext i16 (trunc i32 %a to i16) to i32)

Note that while this helps get a tighter bound on the range analysis and the
known-bits analysis, this exposes some normalization shortcoming of SCEVs:

    %div = udim i32 %a, 65536
    %mul = mul i32 %div, 65536
    %rem = urem i32 %a, 65536
    %add = add i32 %mul, %rem

Will usually not be reduced.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@312329 91177308-0d34-0410-b5e6-96231b3b80d8
2017-09-01 14:59:59 +00:00
Eugene Zelenko
89688ce180 [Analysis] Fix some Clang-tidy modernize and Include What You Use warnings; other minor fixes (NFC).
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@311212 91177308-0d34-0410-b5e6-96231b3b80d8
2017-08-18 23:51:26 +00:00
Amara Emerson
edab1e126c [SCEV] Preserve NSW information for sext(subtract).
Pushes the sext onto the operands of a Sub if NSW is present.
Also adds support for propagating the nowrap flags of the
llvm.ssub.with.overflow intrinsic during analysis.

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@310117 91177308-0d34-0410-b5e6-96231b3b80d8
2017-08-04 20:19:46 +00:00
Max Kazantsev
511c1a306c [SCEV] Re-enable "Cache results of computeExitLimit"
The patch rL309080 was reverted because it did not clean up the cache on "forgetValue"
method call. This patch re-enables this change, adds the missing check and introduces
two new unit tests that make sure that the cache is cleaned properly.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309925 91177308-0d34-0410-b5e6-96231b3b80d8
2017-08-03 08:41:30 +00:00
Sanjoy Das
2d38e17cd0 [SCEV/IndVars] Always compute loop exiting values if the backedge count is 0
If SCEV can prove that the backedge taken count for a loop is zero, it does not
need to "understand" a recursive PHI to compute its exiting value.

This should fix PR33885.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309758 91177308-0d34-0410-b5e6-96231b3b80d8
2017-08-01 22:37:58 +00:00
Sanjoy Das
10db1a7378 [SCEV] Change an early exit to an assert; NFC
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309480 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-29 05:32:47 +00:00
Max Kazantsev
f4dbee3151 [SCEV] Do not visit nodes twice in containsConstantSomewhere
This patch reworks the function that searches constants in Add and Mul SCEV expression
chains so that now it does not visit a node more than once, and also renames this function
for better correspondence between its implementation and semantics.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309367 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-28 06:42:15 +00:00
Sanjoy Das
e47ec8cfbd Revert "[SCEV] Cache results of computeExitLimit"
This reverts commit r309080.  The patch needs to clear out the
ScalarEvolution::ExitLimits cache in forgetMemoizedResults.

I've replied on the commit thread for the patch with more details.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309357 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-28 03:25:07 +00:00
Max Kazantsev
8df9b4fbf9 [SCEV] Cache results of computeExitLimit
This patch adds a cache for computeExitLimit to save compilation time. A lot of examples of
tests that take extensive time to compile are attached to the bug 33494.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309080 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-26 04:55:54 +00:00
Sanjoy Das
69b28c8782 [SCEV] Remove unnecessary call to forgetMemoizedResults
`SCEVUnknown::allUsesReplacedWith` does not need to call `forgetMemoizedResults`
since RAUW does a value-equivalent replacement by assumption.  If this
assumption was false then the later setValPtr(New) call would be incorrect too.

This is a non-trivial performance optimization for functions with a large number
of loops since `forgetMemoizedResults` walks all loop backedge taken counts to
see if any of them use the SCEVUnknown being RAUWed.  However, this improvement
is difficult to demonstrate without checking in an excessively large IR file.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309072 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-26 01:32:19 +00:00
Max Kazantsev
33ec7a1ff0 [SCEV] Limit max size of AddRecExpr during evolving
When SCEV calculates product of two SCEVAddRecs from the same loop, it
tries to combine them into one big AddRecExpr. If the sizes of the initial
SCEVs were `S1` and `S2`, the size of their product is `S1 + S2 - 1`, and every
operand of the resulting SCEV is combined from operands of initial SCEV and
has much higher complexity than they have.

As result, if we try to calculate something like:
  %x1 = {a,+,b}
  %x2 = mul i32 %x1, %x1
  %x3 = mul i32 %x2, %x1
  %x4 = mul i32 %x3, %x2
  ...
The size of such SCEVs grows as `2^N`, and the arguments
become more and more complex as we go forth. This leads
to long compilation and huge memory consumption.

This patch sets a limit after which we don't try to combine two
`SCEVAddRecExpr`s into one. By default, max allowed size of the
resulting AddRecExpr is set to 16.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@308847 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-23 15:40:19 +00:00
Dorit Nuzman
bdc92341e1 PSCEV] Create AddRec for Phis in cases of possible integer overflow,
using runtime checks

Extend the SCEVPredicateRewriter to work a bit harder when it encounters an
UnknownSCEV for a Phi node; Try to build an AddRecurrence also for Phi nodes
whose update chain involves casts that can be ignored under the proper runtime
overflow test. This is one step towards addressing PR30654.

Differential revision: http://reviews.llvm.org/D30041



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@308299 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-18 11:57:08 +00:00
Craig Topper
099c15e7b4 [Constants] Replace calls to ConstantInt::equalsInt(0)/equalsInt(1) with isZero and isOne. NFCI
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@307293 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-06 18:39:49 +00:00
Craig Topper
6dbd34d261 [Constants] If we already have a ConstantInt*, prefer to use isZero/isOne/isMinusOne instead of isNullValue/isOneValue/isAllOnesValue inherited from Constant. NFCI
Going through the Constant methods requires redetermining that the Constant is a ConstantInt and then calling isZero/isOne/isMinusOne.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@307292 91177308-0d34-0410-b5e6-96231b3b80d8
2017-07-06 18:39:47 +00:00
Max Kazantsev
76aac8f1ce [SCEV] Use depth limit instead of local cache for SExt and ZExt
In rL300494 there was an attempt to deal with excessive compile time on
invocations of getSign/ZeroExtExpr using local caching. This approach only
helps if we request the same SCEV multiple times throughout recursion. But
in the bug PR33431 we see a case where we request different values all the time,
so caching does not help and the size of the cache grows enormously.

In this patch we remove the local cache for this methods and add the recursion
depth limit instead, as we do for arithmetics. This gives us a guarantee that the
invocation sequence is limited and reasonably short.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@306785 91177308-0d34-0410-b5e6-96231b3b80d8
2017-06-30 05:04:09 +00:00
Alexandre Isoard
1894c02307 Reverting r306695 while investigating failing test case.
Failing test case:
    Transforms/LoopVectorize.iv_outside_user.ll



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@306723 91177308-0d34-0410-b5e6-96231b3b80d8
2017-06-29 18:48:56 +00:00
Alexandre Isoard
a70a8a0aa7 ScalarEvolution: Add URem support
In LLVM IR the following code:

    %r = urem <ty> %t, %b

is equivalent to:

    %q = udiv <ty> %t, %b
    %s = mul <ty> nuw %q, %b
    %r = sub <ty> nuw %t, %q ; (t / b) * b + (t % b) = t

As UDiv, Mul and Sub are already supported by SCEV, URem can be
implemented with minimal effort this way.

Note: While SRem and SDiv are also related this way, SCEV does not
provides SDiv yet.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@306695 91177308-0d34-0410-b5e6-96231b3b80d8
2017-06-29 16:29:04 +00:00
Craig Topper
5e4b09c56f [SCEV] Avoid copying ConstantRange just to get the min/max value
Summary:
This patch changes getRange to getRangeRef and returns a reference to the ConstantRange object stored inside the DenseMap caches. We then take advantage of that to add new helper methods that can return min/max value of a signed or unsigned ConstantRange using that reference without first copying the ConstantRange.

getRangeRef calls itself recursively and I believe the reference return is fine for those calls.

I've left getSignedRange and getUnsignedRange returning a ConstantRange object so they will make a copy now. This is to ensure safety since the reference will be invalidated if the DenseMap changes.

I'm sure there are still more places that can take advantage of the reference and I'll submit future patches as I find them.

Reviewers: sanjoy, davide

Reviewed By: sanjoy

Subscribers: zzheng, llvm-commits, mzolotukhin

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@306229 91177308-0d34-0410-b5e6-96231b3b80d8
2017-06-24 23:34:50 +00:00