589 Commits

Author SHA1 Message Date
Sanjay Patel
ad4da63ac2 [InstructionSimplify] Add support for saturating add/sub
Add support for saturating add/sub in InstructionSimplify. In particular, the following simplifications are supported:

    sat(X + 0) -> X
    sat(X + undef) -> -1
    sat(X uadd MAX) -> MAX
    (and commutative variants)

    sat(X - 0) -> X
    sat(X - X) -> 0
    sat(X - undef) -> 0
    sat(undef - X) -> 0
    sat(0 usub X) -> 0
    sat(X usub MAX) -> 0

Patch by: @nikic (Nikita Popov)

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@347330 91177308-0d34-0410-b5e6-96231b3b80d8
2018-11-20 17:20:26 +00:00
Sanjay Patel
fc0780a8a9 [InstSimplify] delete shift-of-zero guard ops around funnel shifts
This is a problem seen in common rotate idioms as noted in:
https://bugs.llvm.org/show_bug.cgi?id=34924

Note that we are not canonicalizing standard IR (shifts and logic) to the intrinsics yet. 
(Although I've written this before...) I think this is the last step before we enable 
that transform. Ie, we could regress code by doing that transform without this 
simplification in place.

In PR34924, I questioned whether this is a valid transform for target-independent IR, 
but I convinced myself this is ok. If we're speculating a funnel shift by turning cmp+br 
into select, then SimplifyCFG has already determined that the transform is justified. 
It's possible that SimplifyCFG is not taking into account profile or other metadata, 
but if that's true, then it's a bug independent of funnel shifts.

Also, we do have CGP code to restore a guard like this around an intrinsic if it can't 
be lowered cheaply. But that isn't necessary for funnel shift because the default 
expansion in SelectionDAGBuilder includes this same cmp+select.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@346960 91177308-0d34-0410-b5e6-96231b3b80d8
2018-11-15 14:53:37 +00:00
Sanjay Patel
e357c8b879 [InstSimplify] fold select (fcmp X, Y), X, Y
This is NFCI for InstCombine because it calls InstSimplify, 
so I left the tests for this transform there. As noted in
the code comment, we can allow this fold more often by using
FMF and/or value tracking.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@346169 91177308-0d34-0410-b5e6-96231b3b80d8
2018-11-05 21:51:39 +00:00
Sanjay Patel
148536769a [InstSimplify] fold icmp based on range of abs/nabs (2nd try)
This is retrying the fold from rL345717 
(reverted at rL347780)
...with a fix for the miscompile
demonstrated by PR39510:
https://bugs.llvm.org/show_bug.cgi?id=39510

Original commit message:

This is a fix for PR39475:
https://bugs.llvm.org/show_bug.cgi?id=39475

We managed to get some of these patterns using computeKnownBits in https://reviews.llvm.org/D47041, but that
can't be used for nabs(). Instead, put in some range-based logic, so we can fold
both abs/nabs with icmp with a constant value.

Alive proofs:
https://rise4fun.com/Alive/21r

Name: abs_nsw_is_positive

  %cmp = icmp slt i32 %x, 0
  %negx = sub nsw i32 0, %x
  %abs = select i1 %cmp, i32 %negx, i32 %x
  %r = icmp sgt i32 %abs, -1
    =>
  %r = i1 true


Name: abs_nsw_is_not_negative

  %cmp = icmp slt i32 %x, 0
  %negx = sub nsw i32 0, %x
  %abs = select i1 %cmp, i32 %negx, i32 %x
  %r = icmp slt i32 %abs, 0
    =>
  %r = i1 false


Name: nabs_is_negative_or_0

  %cmp = icmp slt i32 %x, 0
  %negx = sub i32 0, %x
  %nabs = select i1 %cmp, i32 %x, i32 %negx
  %r = icmp slt i32 %nabs, 1
    =>
  %r = i1 true

Name: nabs_is_not_over_0

  %cmp = icmp slt i32 %x, 0
  %negx = sub i32 0, %x
  %nabs = select i1 %cmp, i32 %x, i32 %negx
  %r = icmp sgt i32 %nabs, 0
    =>
  %r = i1 false

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@345832 91177308-0d34-0410-b5e6-96231b3b80d8
2018-11-01 14:07:39 +00:00
Sanjay Patel
9268a4a0f0 revert rL345717 : [InstSimplify] fold icmp based on range of abs/nabs
This can miscompile as shown in PR39510:
https://bugs.llvm.org/show_bug.cgi?id=39510


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@345780 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-31 21:37:40 +00:00
Sanjay Patel
5406c80642 [InstSimplify] fold 'fcmp nnan ult X, 0.0' when X is not negative
This is the inverted case for the transform added with D53874 / rL345725.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@345728 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-31 15:35:46 +00:00
Sanjay Patel
1ef057dce8 [InstSimplify] fold 'fcmp nnan oge X, 0.0' when X is not negative
This re-raises some of the open questions about how to apply and use fast-math-flags in IR from PR38086:
https://bugs.llvm.org/show_bug.cgi?id=38086
...but given the current implementation (no FMF on casts), this is likely the only way to predicate the 
transform.

This is part of solving PR39475:
https://bugs.llvm.org/show_bug.cgi?id=39475

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@345725 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-31 14:57:23 +00:00
Sanjay Patel
893f08bea2 [InstSimplify] fold icmp based on range of abs/nabs
This is a fix for PR39475:
https://bugs.llvm.org/show_bug.cgi?id=39475

We managed to get some of these patterns using computeKnownBits in D47041, but that 
can't be used for nabs(). Instead, put in some range-based logic, so we can fold 
both abs/nabs with icmp with a constant value.

Alive proofs:
https://rise4fun.com/Alive/21r

Name: abs_nsw_is_positive
  %cmp = icmp slt i32 %x, 0
  %negx = sub nsw i32 0, %x
  %abs = select i1 %cmp, i32 %negx, i32 %x
  %r = icmp sgt i32 %abs, -1
    =>
  %r = i1 true
 
Name: abs_nsw_is_not_negative
  %cmp = icmp slt i32 %x, 0
  %negx = sub nsw i32 0, %x
  %abs = select i1 %cmp, i32 %negx, i32 %x
  %r = icmp slt i32 %abs, 0
    =>
  %r = i1 false
 
Name: nabs_is_negative_or_0
  %cmp = icmp slt i32 %x, 0
  %negx = sub i32 0, %x
  %nabs = select i1 %cmp, i32 %x, i32 %negx
  %r = icmp slt i32 %nabs, 1
    =>
  %r = i1 true

Name: nabs_is_not_over_0
  %cmp = icmp slt i32 %x, 0
  %negx = sub i32 0, %x
  %nabs = select i1 %cmp, i32 %x, i32 %negx
  %r = icmp sgt i32 %nabs, 0
    =>
  %r = i1 false

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@345717 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-31 13:25:10 +00:00
Thomas Lively
9e79a4ff27 [InstCombine] InstCombine and InstSimplify for minimum and maximum
Summary: Depends on D52765

Reviewers: aheejin, dschuff

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@344799 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-19 19:01:26 +00:00
Cameron McInally
fe584de305 [FPEnv] PatternMatcher support for checking FNEG ignoring signed zeros
https://reviews.llvm.org/D52934



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@344084 91177308-0d34-0410-b5e6-96231b3b80d8
2018-10-09 21:48:00 +00:00
Chandler Carruth
9179aee2c1 [IR] Replace isa<TerminatorInst> with isTerminator().
This is a bit awkward in a handful of places where we didn't even have
an instruction and now we have to see if we can build one. But on the
whole, this seems like a win and at worst a reasonable cost for removing
`TerminatorInst`.

All of this is part of the removal of `TerminatorInst` from the
`Instruction` type hierarchy.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@340701 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-26 09:51:22 +00:00
Sanjay Patel
77028e31e5 [InstSimplify] use isKnownNeverNaN to fold more fcmp ord/uno
Remove duplicate tests from InstCombine that were added with
D50582. I left negative tests there to verify that nothing
in InstCombine tries to go overboard. If isKnownNeverNaN is
improved to handle the FP binops or other cases, we should
have coverage under InstSimplify, so we could remove more
duplicate tests from InstCombine at that time.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@340279 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-21 14:45:13 +00:00
Florian Hahn
1bf795160f [InstrSimplify,NewGVN] Add option to ignore additional instr info when simplifying.
NewGVN uses InstructionSimplify for simplifications of leaders of
congruence classes. It is not guaranteed that the metadata or other
flags/keywords (like nsw or exact) of the leader is available for all members
in a congruence class, so we cannot use it for simplification.

This patch adds a InstrInfoQuery struct with a boolean field
UseInstrInfo (which defaults to true to keep the current behavior as
default) and a set of helper methods to get metadata/keywords for a
given instruction, if UseInstrInfo is true. The whole thing might need a
better name, to avoid confusion with TargetInstrInfo but I am not sure
what a better name would be.

The current patch threads through InstrInfoQuery to the required
places, which is messier then it would need to be, if
InstructionSimplify and ValueTracking would share the same Query struct.

The reason I added it as a separate struct is that it can be shared
between InstructionSimplify and ValueTracking's query objects. Also,
some places do not need a full query object, just the InstrInfoQuery.

It also updates some interfaces that do not take a Query object, but a
set of optional parameters to take an additional boolean UseInstrInfo.

See https://bugs.llvm.org/show_bug.cgi?id=37540.

Reviewers: dberlin, davide, efriedma, sebpop, hiraditya

Reviewed By: hiraditya

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@340031 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-17 14:39:04 +00:00
Benjamin Kramer
ac6c5d8a36 [InstSimplify] Guard against large shift amounts.
These are always UB, but can happen for large integer inputs. Testing it
is very fragile as -simplifycfg will nuke the UB top-down.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339515 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-12 11:43:03 +00:00
Matt Arsenault
0904319a62 ValueTracking: Start enhancing isKnownNeverNaN
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339399 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-09 22:40:08 +00:00
Sanjay Patel
54b09599fc [InstSimplify] move minnum/maxnum with Inf folds from instcombine
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339396 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-09 22:20:44 +00:00
Sanjay Patel
c517d08361 [InstSimplify] fold fsub+fadd with common operand
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339176 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-07 20:32:55 +00:00
Sanjay Patel
a5d9c8f92a [InstSimplify] fold fadd+fsub with common operand
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339174 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-07 20:23:49 +00:00
Sanjay Patel
c10f372ba1 [InstSimplify] fold fsub+fsub with common operand
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339171 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-07 20:14:27 +00:00
Sanjay Patel
5ab217ce42 [InstSimplify] move minnum/maxnum with common op fold from instcombine
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@339144 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-07 14:36:27 +00:00
Hiroshi Inoue
ebab95406f [InstSimplify] fold extracting from std::pair (2/2)
This is the second patch of the series which intends to enable jump threading for an inlined method whose return type is std::pair<int, bool> or std::pair<bool, int>. 
The first patch is https://reviews.llvm.org/rL338485.

This patch handles code sequences that merges two values using `shl` and `or`, then extracts one value using `and`.

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338817 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-03 05:39:48 +00:00
Sanjay Patel
e1c9b76cd3 [InstSimplify] move minnum/maxnum with undef fold from instcombine
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338719 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-02 14:33:40 +00:00
Sanjay Patel
5ea9eaae86 [InstSimplify] move minnum/maxnum with same arg fold from instcombine
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338652 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-01 23:05:55 +00:00
Hiroshi Inoue
d967b3d2e7 [InstSimplify] fold extracting from std::pair (1/2)
This patch intends to enable jump threading when a method whose return type is std::pair<int, bool> or std::pair<bool, int> is inlined.
For example, jump threading does not happen for the if statement in func.

std::pair<int, bool> callee(int v) {
  int a = dummy(v);
  if (a) return std::make_pair(dummy(v), true);
  else return std::make_pair(v, v < 0);
}

int func(int v) {
  std::pair<int, bool> rc = callee(v);
  if (rc.second) {
    // do something
  }

SROA executed before the method inlining replaces std::pair by i64 without splitting in both callee and func since at this point no access to the individual fields is seen to SROA.
After inlining, jump threading fails to identify that the incoming value is a constant due to additional instructions (like or, and, trunc).

This series of patch add patterns in InstructionSimplify to fold extraction of members of std::pair. To help jump threading, actually we need to optimize the code sequence spanning multiple BBs.
These patches does not handle phi by itself, but these additional patterns help NewGVN pass, which calls instsimplify to check opportunities for simplifying instructions over phi, apply phi-of-ops optimization to result in successful jump threading. 
SimplifyDemandedBits in InstCombine, can do more general optimization but this patch aims to provide opportunities for other optimizers by supporting a simple but common case in InstSimplify.

This first patch in the series handles code sequences that merges two values using shl and or and then extracts one value using lshr.

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338485 91177308-0d34-0410-b5e6-96231b3b80d8
2018-08-01 04:40:32 +00:00
David Bolvansky
f241788fa5 [InstSimplify] Fold another Select with And/Or pattern
Summary: Proof: https://rise4fun.com/Alive/L5J

Reviewers: lebedev.ri, spatel

Reviewed By: spatel

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338383 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-31 14:17:15 +00:00
Sanjay Patel
5c9b7b9b82 [InstSimplify] fold funnel shifts with 0-shift amount
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338218 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-29 16:36:38 +00:00
Sanjay Patel
769bf94359 [InstSimplify] refactor intrinsic simplifications; NFCI
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338215 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-29 14:42:08 +00:00
David Bolvansky
cf073c23aa [InstCombine] Fold Select with AND/OR condition
Summary:
Fold
```
%A = icmp ne i8 %X, %V1
%B = icmp ne i8 %X, %V2
%C = or i1 %A, %B
%D = select i1 %C, i8 %X, i8 %V1
ret i8 %D
  =>
ret i8 %X

Fixes https://bugs.llvm.org/show_bug.cgi?id=38334
Proof: https://rise4fun.com/Alive/plI8

Reviewers: spatel, lebedev.ri

Reviewed By: lebedev.ri

Subscribers: craig.topper, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@338191 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-28 06:55:51 +00:00
Chen Zheng
ebc7653063 [InstrSimplify] fold sdiv if two operands are negated and non-overflow
Differential Revision: https://reviews.llvm.org/D49382


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@337642 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-21 12:27:54 +00:00
Chen Zheng
da67c6d0ef [InstSimplify] fold srem instruction if its two operands are negated.
Differential Revision: https://reviews.llvm.org/D49423


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@337545 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-20 13:00:47 +00:00
Sanjay Patel
268055dd8c [InstSimplify] fold minnum/maxnum with NaN arg
This fold is repeated/misplaced in instcombine, but I'm
not sure if it's safe to remove that yet because some
other folds appear to be asserting that the transform
has occurred within instcombine itself.

This isn't the best fix for PR37776, but it probably
hides the bug with the given code example:
https://bugs.llvm.org/show_bug.cgi?id=37776

We have another test to demonstrate the more general bug.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@337127 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-15 14:52:16 +00:00
Chen Zheng
7d5acd8e56 [InstSimplify] simplify add instruction if two operands are negative
Differential Revision: https://reviews.llvm.org/D49216


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@336881 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-12 03:06:04 +00:00
Manoj Gupta
c6da6867a1 llvm: Add support for "-fno-delete-null-pointer-checks"
Summary:
Support for this option is needed for building Linux kernel.
This is a very frequently requested feature by kernel developers.

More details : https://lkml.org/lkml/2018/4/4/601

GCC option description for -fdelete-null-pointer-checks:
This Assume that programs cannot safely dereference null pointers,
and that no code or data element resides at address zero.

-fno-delete-null-pointer-checks is the inverse of this implying that
null pointer dereferencing is not undefined.

This feature is implemented in LLVM IR in this CL as the function attribute
"null-pointer-is-valid"="true" in IR (Under review at D47894).
The CL updates several passes that assumed null pointer dereferencing is
undefined to not optimize when the "null-pointer-is-valid"="true"
attribute is present.

Reviewers: t.p.northover, efriedma, jyknight, chandlerc, rnk, srhines, void, george.burgess.iv

Reviewed By: efriedma, george.burgess.iv

Subscribers: eraman, haicheng, george.burgess.iv, drinkcat, theraven, reames, sanjoy, xbolva00, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@336613 91177308-0d34-0410-b5e6-96231b3b80d8
2018-07-09 22:27:23 +00:00
Sanjay Patel
5f8dac1929 [InstSimplify] fold shifts by sext bool
https://rise4fun.com/Alive/c3Y


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@335633 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-26 17:31:38 +00:00
Sanjay Patel
7706083ace [InstSimplify] fold srem with sext bool divisor
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@335616 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-26 15:32:54 +00:00
Sanjay Patel
df0d594dd0 [InstSimplify] fold div/rem of zexted bool
I was looking at an unrelated fold and noticed that
we don't have this simplification (because the other
fold would break existing tests).

Name: zext udiv
  %z = zext i1 %x to i32
  %r = udiv i32 %y, %z
=>
  %r = %y

Name: zext urem
  %z = zext i1 %x to i32
  %r = urem i32 %y, %z
=>
  %r = 0

Name: zext sdiv
  %z = zext i1 %x to i32
  %r = sdiv i32 %y, %z
=>
  %r = %y

Name: zext srem
  %z = zext i1 %x to i32
  %r = srem i32 %y, %z
=>
  %r = 0

https://rise4fun.com/Alive/LZ9


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@335512 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-25 18:51:21 +00:00
Sanjay Patel
0da71804c3 [InstSimplify] Fix missed optimization in simplifyUnsignedRangeCheck()
For both operands are unsigned, the following optimizations are valid, and missing:

   1. X > Y && X != 0 --> X > Y
   2. X > Y || X != 0 --> X != 0
   3. X <= Y || X != 0 --> true
   4. X <= Y || X == 0 --> X <= Y
   5. X > Y && X == 0 --> false

unsigned foo(unsigned x, unsigned y) { return x > y && x != 0; }
should fold to x > y, but I found we haven't done it right now.
besides, unsigned foo(unsigned x, unsigned y) { return x < y && y != 0; }
Has been folded to x < y, so there may be a bug.

Patch by: Li Jia He!

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@335129 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-20 14:22:49 +00:00
Roman Lebedev
65cbabed5f [NFC][InstSimplify] SimplifyAddInst(): coding style: variable names.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@334299 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-08 15:44:53 +00:00
Roman Lebedev
b76b2440ec [InstSimplify] add nuw %x, -1 -> -1 fold.
Summary:
`%ret = add nuw i8 %x, C`
From [[ https://llvm.org/docs/LangRef.html#add-instruction | langref ]]:
    nuw and nsw stand for “No Unsigned Wrap” and “No Signed Wrap”,
    respectively. If the nuw and/or nsw keywords are present,
    the result value of the add is a poison value if unsigned
    and/or signed overflow, respectively, occurs.

So if `C` is `-1`, `%x` can only be `0`, and the result is always `-1`.

I'm not sure we want to use `KnownBits`/`LVI` here, because there is
exactly one possible value (all bits set, `-1`), so some other pass
should take care of replacing the known-all-ones with constant `-1`.

The `test/Transforms/InstCombine/set-lowbits-mask-canonicalize.ll` change *is* confusing.
What happening is, before this: (omitting `nuw` for simplicity)
1. First, InstCombine D47428/rL334127 folds `shl i32 1, %NBits`) to `shl nuw i32 -1, %NBits`
2. Then, InstSimplify D47883/rL334222 folds `shl nuw i32 -1, %NBits` to `-1`,
3. `-1` is inverted to `0`.
But now:
1. *This* InstSimplify fold `%ret = add nuw i32 %setbit, -1` -> `-1` happens first,
   before InstCombine D47428/rL334127 fold could happen.
Thus we now end up with the opposite constant,
and it is all good: https://rise4fun.com/Alive/OA9

https://rise4fun.com/Alive/sldC
Was mentioned in D47428 review.
Follow-up for D47883.

Reviewers: spatel, craig.topper

Reviewed By: spatel

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@334298 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-08 15:44:47 +00:00
Roman Lebedev
fa1dbcce5b [InstSimplify] shl nuw C, %x -> C iff signbit is set on C.
Summary:
`%r = shl nuw i8 C, %x`

As per langref:
```
If the nuw keyword is present, then the shift produces
a poison value if it shifts out any non-zero bits.
```
Thus, if the sign bit is set on `C`, then `%x` can only be `0`,
which means that `%r` can only be `C`.
Or in other words, set sign bit means that the signed value
is negative, so the constant is `<= 0`.

https://rise4fun.com/Alive/WMk
https://rise4fun.com/Alive/udv

Was mentioned in D47428 review.

We already handle the `0` constant, https://godbolt.org/g/UZq1sJ, so this only handles negative constants.

Could use computeKnownBits() / LazyValueInfo,
but the cost-benefit analysis (https://reviews.llvm.org/D47891)
suggests it isn't worth it.

Reviewers: spatel, craig.topper

Reviewed By: spatel

Subscribers: llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@334222 91177308-0d34-0410-b5e6-96231b3b80d8
2018-06-07 20:03:45 +00:00
Adrian Prantl
26b584c691 Remove \brief commands from doxygen comments.
We've been running doxygen with the autobrief option for a couple of
years now. This makes the \brief markers into our comments
redundant. Since they are a visual distraction and we don't want to
encourage more \brief markers in new code either, this patch removes
them all.

Patch produced by

  for i in $(git grep -l '\\brief'); do perl -pi -e 's/\\brief //g' $i & done

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@331272 91177308-0d34-0410-b5e6-96231b3b80d8
2018-05-01 15:54:18 +00:00
George Burgess IV
557491f34d Reland r301880(!): "[InstSimplify] Handle selects of GEPs with 0 offset"
I was reminded today that this patch got reverted in r301885. I can no
longer reproduce the failure that caused the revert locally (...almost
one year later), and the patch applied pretty cleanly, so I guess we'll
see if the bots still get angry about it.

The original breakage was InstSimplify complaining (in "assertion
failed" form) about getting passed some crazy IR when running `ninja
check-sanitizer`. I'm unable to find traces of what, exactly, said crazy
IR was. I suppose we'll find out pretty soon if that's still the case.
:)

Original commit:

  Author: gbiv
  Date: Mon May  1 18:12:08 2017
  New Revision: 301880

  URL: http://llvm.org/viewvc/llvm-project?rev=301880&view=rev
  Log:
  [InstSimplify] Handle selects of GEPs with 0 offset

  In particular (since it wouldn't fit nicely in the summary):
  (select (icmp eq V 0) P (getelementptr P V)) -> (getelementptr P V)

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@330667 91177308-0d34-0410-b5e6-96231b3b80d8
2018-04-24 00:25:01 +00:00
Sanjay Patel
e1bbe84207 [PatternMatch] allow undef elements when matching a vector zero
This is the last step in getting constant pattern matchers to allow
undef elements in constant vectors.

I'm adding a dedicated m_ZeroInt() function and building m_Zero() from
that. In most cases, calling code can be updated to use m_ZeroInt()
directly when there's no need to match pointers, but I'm leaving that
efficiency optimization as a follow-up step because it's not always
clear when that's ok.

There are just enough icmp folds in InstSimplify that can be used for 
integer or pointer types, that we probably still want a generic m_Zero()
for those cases. Otherwise, we could eliminate it (and possibly add a
m_NullPtr() as an alias for isa<ConstantPointerNull>()).

We're conservatively returning a full zero vector (zeroinitializer) in
InstSimplify/InstCombine on some of these folds (see diffs in InstSimplify),
but I'm not sure if that's actually necessary in all cases. We may be 
able to propagate an undef lane instead. One test where this happens is 
marked with 'TODO'.
 


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@330550 91177308-0d34-0410-b5e6-96231b3b80d8
2018-04-22 17:07:44 +00:00
Sanjay Patel
8eacad4a41 [InstSimplify] fix formatting; NFC
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@329736 91177308-0d34-0410-b5e6-96231b3b80d8
2018-04-10 18:38:19 +00:00
Sanjay Patel
1017678677 [PatternMatch] allow undef elements when matching vector FP +0.0
This continues the FP constant pattern matching improvements from:
https://reviews.llvm.org/rL327627
https://reviews.llvm.org/rL327339
https://reviews.llvm.org/rL327307

Several integer constant matchers also have this ability. I'm
separating matching of integer/pointer null from FP positive zero
and renaming/commenting to make the functionality clearer.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@328461 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-25 21:16:33 +00:00
Sanjay Patel
3e65cc15a0 [InstSimplify] fp_binop X, NaN --> NaN
We propagate the existing NaN value when possible.

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



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@328140 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-21 19:31:53 +00:00
Sanjay Patel
d65aba275a [InstSimplify] loosen FMF for sqrt(X) * sqrt(X) --> X
As shown in the code comment, we don't need all of 'fast', 
but we do need reassoc + nsz + nnan.

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


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@327796 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-18 14:12:25 +00:00
Roman Lebedev
73e0892707 [InstSimplify] peek through unsigned FP casts for sign-bit compares (PR36682)
This pattern came up in PR36682 / D44390
https://bugs.llvm.org/show_bug.cgi?id=36682
https://reviews.llvm.org/D44390
https://godbolt.org/g/oKvT5H

See also D44421, D44424

Reviewers: spatel, majnemer, efriedma, arsenm

Reviewed By: spatel

Subscribers: wdng, llvm-commits

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

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@327642 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-15 16:17:46 +00:00
Roman Lebedev
d2827a5a71 [InstSimplify][NFC] simplifyICmpWithConstant(): refactor GetCompareTy() calls
Preparation for D44425.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@327641 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-15 16:17:40 +00:00
Matthew Simpson
828ff3b7ed [ConstantFolding, InstSimplify] Handle more vector GEPs
This patch addresses some additional cases where the compiler crashes upon
encountering vector GEPs. This should fix PR36116.

Differential Revision: https://reviews.llvm.org/D44219
Reference: https://bugs.llvm.org/show_bug.cgi?id=36116

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@327638 91177308-0d34-0410-b5e6-96231b3b80d8
2018-03-15 16:00:29 +00:00