1400 Commits

Author SHA1 Message Date
Noah Goldstein
87528bfefb [ValueTracking] Add support for shufflevector in isKnownNonZero
Shuffles don't modify the data, so if all elements that end up in the
destination are non-zero the result is non-zero.

Closes #87702
2024-04-10 13:13:42 -05:00
Noah Goldstein
f1ee458ddb [ValueTracking] improve isKnownNonZero precision for smax
Instead of relying on known-bits for strictly positive, use the
`isKnownPositive` API. This will use `isKnownNonZero` which is more
accurate.

Closes #88170
2024-04-10 10:40:49 -05:00
Noah Goldstein
37ca6fa1e2 [ValueTracking] Add support for overflow detection functions is isKnownNonZero
Adds support for: `{s,u}{add,sub,mul}.with.overflow`

The logic is identical to the the non-overflow binops, we where just
missing the cases.

Closes #87701
2024-04-10 10:40:48 -05:00
Noah Goldstein
f0a487d7e2 [ValueTracking] Split isNonZero(mul) logic to a helper; NFC 2024-04-10 10:40:48 -05:00
Noah Goldstein
41c52217b0 [ValueTracking] Add support for vector_reduce_{s,u}{min,max} in computeKnownBits
Previously missing. We compute by just applying the reduce function on
the knownbits of each element.

Closes #88169
2024-04-10 10:40:48 -05:00
Noah Goldstein
77d668451a [ValueTracking] Add support for vector_reduce_{s,u}{min,max} in isKnownNonZero
Previously missing, proofs for all implementations:
https://alive2.llvm.org/ce/z/G8wpmG
2024-04-10 10:40:48 -05:00
Noah Goldstein
964df099e1 [ValueTracking] Support non-constant idx for computeKnownBits of insertelement
Its same logic as before, we just need to intersect what we know about
the new Elt and the entire pre-existing Vec.

Closes #87707
2024-04-09 01:01:41 -05:00
Noah Goldstein
b65ab0b726 [ValueTracking] Add comment clarifying missing usub.sat in isKnownNonZero; NFC
Closes #87700
2024-04-08 23:33:06 -05:00
Matt Arsenault
bdf428af98 ValueTracking: Consider demanded elts for vector constants in computeKnownFPClass 2024-04-08 09:32:14 -04:00
Matt Arsenault
2bc637b1ce ValueTracking: Handle ConstantAggregateZero in computeKnownFPClass 2024-04-08 09:26:12 -04:00
Matt Arsenault
95f984f37e ValueTracking: Don't use unnecessary null checked dyn_cast 2024-04-08 08:32:04 -04:00
Noah Goldstein
e4db938a4e [ValueTracking] Support non-constant idx for computeKnownFPClass of insertelement
Its same logic as before, we just need to intersect what we know about
the new Elt and the entire pre-existing Vec.

Closes #87708
2024-04-06 17:51:15 -05:00
Noah Goldstein
678f32ab66 [ValueTracking] Add more conditions in to isTruePredicate
There is one notable "regression". This patch replaces the bespoke `or
disjoint` logic we a direct match. This means we fail some
simplification during `instsimplify`.
All the cases we fail in `instsimplify` we do handle in `instcombine`
as we add `disjoint` flags.

Other than that, just some basic cases.

See proofs: https://alive2.llvm.org/ce/z/_-g7C8

Closes #86083
2024-04-04 12:42:58 -05:00
Noah Goldstein
05cff99a29 [ValueTracking] Infer known bits fromfrom (icmp eq (and/or x,y), C)
In `(icmp eq (and x,y), C)` all 1s in `C` must also be set in both
`x`/`y`.

In `(icmp eq (or x,y), C)` all 0s in `C` must also be set in both
`x`/`y`.

Closes #87143
2024-04-04 12:42:58 -05:00
Noah Goldstein
637421cb88 [ValueTracking] Tracking or disjoint conditions as add in Assumption/DomCondition Cache
We can definitionally treat `or disjoint` as `add` anywhere.

Closes #86302
2024-03-28 13:49:05 -05:00
Andreas Jonson
e66cfebb04
[ValueTracking] Handle range attributes (#85143)
Handle the range attribute in ValueTracking.
2024-03-20 12:43:00 +01:00
Yingwei Zheng
f0420c7bc6
[ValueTracking] Handle not in isImpliedCondition (#85397)
This patch handles `not` in `isImpliedCondition` to enable more fold in
some multi-use cases.
2024-03-20 16:16:42 +08:00
Nikita Popov
2cc75aed09 [ValueTracking] Move MD_range handling to isKnownNonZeroFromOperator()
All the isKnownNonZero() handling for instructions should be inside
this function. This makes the structure more similar to
computeKnownBitsFromOperator() as well.

This may not be entirely NFC due to different depth handling.
2024-03-19 16:16:48 +01:00
Nikita Popov
d1e2305a6d [ValueTracking] Fix release build
Move the declaration of the Ty variable outside the NDEBUG guard
and make use of it in the remainder of the function.
2024-03-19 16:07:14 +01:00
Nikita Popov
6872a64652 [ValueTracking] Handle vector range metadata in isKnownNonZero()
Nowadays !range can be placed on instructions with vector of int
return value. Support this case in isKnownNonZero().
2024-03-19 15:50:13 +01:00
Matt Arsenault
1a6953a75d ValueTracking: Fix bug with fcmp false to nan constant
If we had a comparison to a literal nan with a false predicate,
we were incorrectly treating it as an unordered compare. This was
correct for fcmp true, but not fcmp false. I noticed this in the
review for e44d3b3e503fa12fdaead2936b28844aa36237c1 but misdiagnosed
the reason. Also change the test for the fcmp true case to be more
useful, but it wasn't wrong previously.
2024-03-19 14:52:45 +05:30
Noah Goldstein
01d8e1ca01 [ValueTracking] Handle non-canonical operand order in isImpliedCondICmps
We don't always have canonical order here, so do it manually.

Closes #85575
2024-03-17 17:46:06 -05:00
Noah Goldstein
744a23f24b [ValueTracking] Use select condition to help infer bits of arms
If we have something like `(select (icmp ult x, 8), x, y)`, we can use
the `(icmp ult x, 8)` to help compute the knownbits of `x`.

Closes #84699
2024-03-13 14:27:05 -05:00
mikaelholmen
2d62ce4beb
[ValueTracking] Remove faulty dereference of "InsertBefore" (#85034)
In 2fe81edef6f
 [NFC][RemoveDIs] Insert instruction using iterators in Transforms/
we changed
       if (*req_idx != *i)
         return FindInsertedValue(I->getAggregateOperand(), idx_range,
-                                 InsertBefore);
+                                 *InsertBefore);
     }
but there is no guarantee that is InsertBefore is non-empty at that
point,
which we e.g can see in the added testcase.

Instead just pass on the optional InsertBefore in the recursive call to
FindInsertedValue, as we do at several other places already.
2024-03-13 09:58:47 +01:00
Florian Hahn
b274b23665
[ValueTracking] Treat phi as underlying obj when not decomposing further (#84339)
At the moment, getUnderlyingObjects simply continues for phis that do
not refer to the same underlying object in loops, without adding them to
the list of underlying objects, effectively ignoring those phis.

Instead of ignoring those phis, add them to the list of underlying
objects. This fixes a miscompile where LoopAccessAnalysis fails to
identify a memory dependence, because no underlying objects can be found
for a set of memory accesses.

Fixes https://github.com/llvm/llvm-project/issues/82665.

PR: https://github.com/llvm/llvm-project/pull/84339
2024-03-12 08:55:03 +00:00
Noah Goldstein
a9d913ebcd [KnownBits] Add API support for exact in lshr/ashr; NFC 2024-03-11 15:51:06 -05:00
Björn Pettersson
a41226b055
[ValueTracking] Fix KnownBits conflict for calls (range vs returned) (#84353)
If a function only exits for certain input values we can still derive
that an argument is "returned". We can also derive range metadata that
describe the possible value range returned by the function. However, it
turns out that those two analyses can result in conflicting information.

Example:
  declare i16 @foo(i16 returned)
  ...
  %A = call i16 @foo(i16 4095), !range !{i16 32, i16 33}

To avoid "Bits known to be one AND zero?" assertion failures we know
make sure to discard the known bits for this kind of scenario.
2024-03-07 21:32:49 +01:00
Noah Goldstein
c5aacb0dbc [ValueTracking] Add fast path to avoid second recursive call in isKnownPositive; NFC
Just a simple compile time improvement. This function isn't used much,
however, so its not particularly impactful.

Closes #83638
2024-03-06 13:28:04 -06:00
Yingwei Zheng
3589cacfa8
[ValueTracking] Handle icmp pred (trunc X), C in computeKnownBitsFromCmp (#82803)
This patch handles the pattern `icmp pred (trunc X), C` in
`computeKnownBitsFromCmp` to infer low bits of `X` from dominating
conditions.
2024-03-07 01:05:39 +08:00
Wang Pengcheng
95b52ecb78
[RISCV] Take SEW/LMUL into account for value tracking of vsetvli[max] (#82163)
So that we can benefit from some instcombine optimizations.

This PR contains two commits: the first is for adding tests and the
second is for the optimization.
2024-03-06 14:51:55 +08:00
Noah Goldstein
61c06775c9 [KnownBits] Add API for nuw flag in computeForAddSub; NFC 2024-03-05 12:59:58 -06:00
Jeremy Morse
2fe81edef6 [NFC][RemoveDIs] Insert instruction using iterators in Transforms/
As part of the RemoveDIs project we need LLVM to insert instructions using
iterators wherever possible, so that the iterators can carry a bit of
debug-info. This commit implements some of that by updating the contents of
llvm/lib/Transforms/Utils to always use iterator-versions of instruction
constructors.

There are two general flavours of update:
 * Almost all call-sites just call getIterator on an instruction
 * Several make use of an existing iterator (scenarios where the code is
   actually significant for debug-info)
The underlying logic is that any call to getFirstInsertionPt or similar
APIs that identify the start of a block need to have that iterator passed
directly to the insertion function, without being converted to a bare
Instruction pointer along the way.

Noteworthy changes:
 * FindInsertedValue now takes an optional iterator rather than an
   instruction pointer, as we need to always insert with iterators,
 * I've added a few iterator-taking versions of some value-tracking and
   DomTree methods -- they just unwrap the iterator. These are purely
   convenience methods to avoid extra syntax in some passes.
 * A few calls to getNextNode become std::next instead (to keep in the
   theme of using iterators for positions),
 * SeparateConstOffsetFromGEP has it's insertion-position field changed.
   Noteworthy because it's not a purely localised spelling change.

All this should be NFC.
2024-03-05 15:12:22 +00:00
Noah Goldstein
db3bbe03f1 [Analysis] Unify most of the tracking between AssumptionCache and DomConditionCache
This helps cover some missing cases in both and hopefully serves as
creating an easier framework for extending general condition based
analysis.

Closes #83161
2024-03-04 16:53:27 -06:00
Noah Goldstein
6ee46aba06 [Analysis] Share findAffectedValues between DomConditionCache and AssumptionCache; NFC 2024-03-04 16:53:27 -06:00
Noah Goldstein
3bc0ff28a4 [Analysis] Move DomConditionCache::findAffectedValues to a new file; NFC 2024-03-04 16:53:27 -06:00
Noah Goldstein
6f9b0a7095 [ValueTracking] Compute knownbits for (and/or cond0, cond1) on both sides of branch
The false branch for `and` and true branch for `or` provide less
information (intersection as opposed to union), but still can give
some useful information.

Closes #82818
2024-02-25 12:44:23 -06:00
Yingwei Zheng
ac9e67756e
[ValueTracking][NFC] Early exit when enumerating guaranteed well-defined/non-poison operands. (#82812)
According to the [coverage
result](https://dtcxzyw.github.io/llvm-opt-benchmark/coverage/home/dtcxzyw/llvm-project/llvm/lib/Analysis/ValueTracking.cpp.html#L7193)
on my benchmark, `llvm::mustTriggerUB` returns true with an average of
35.0M/12.3M=2.85 matches. I think we can stop enumerating when one of
the matches succeeds to avoid filling the temporary buffer
`NonPoisonOps`.

This patch introduces two template functions
`handleGuaranteedWellDefinedOps/handleGuaranteedNonPoisonOps`. They will
pass well-defined/non-poison operands to inlinable callbacks `Handle`.
If the callback returns true, stop processing and return true.
Otherwise, return false.

Compile-time improvement:
https://llvm-compile-time-tracker.com/compare.php?from=13acb3af5ad48e850cf37dcf02270ede3f267bd4&to=2b55f513c1b6dd2732cb79a25f3eaf6c5e4d6619&stat=instructions:u

|stage1-O3|stage1-ReleaseThinLTO|stage1-ReleaseLTO-g|stage1-O0-g|stage2-O3|stage2-O0-g|stage2-clang|
|--|--|--|--|--|--|--|
|-0.03%|-0.04%|-0.06%|-0.03%|-0.05%|+0.03%|-0.02%|
2024-02-26 01:53:16 +08:00
Yingwei Zheng
3b70387c54
[ValueTracking] Handle more integer intrinsics in propagatesPoison (#82749)
This patch extends `propagatesPoison` to handle more integer intrinsics.
It will turn more logical ands/ors into bitwise ands/ors.

See also https://reviews.llvm.org/D99671.
2024-02-23 20:57:56 +08:00
Noah Goldstein
9facaaddad [ValueTracking] Improve tracking for constant range of {s|u}rem C, x
Current we only support `C` as the remainder, but we can also limit
with a constant numerator.

Proofs: https://alive2.llvm.org/ce/z/QB95gU

Closes #82303
2024-02-20 10:39:34 -06:00
Yingwei Zheng
a5865c3c3d
[ValueTracking] Fix computeKnownFPClass for fpext (#81972)
This patch adds the missing `subnormal -> normal` part for `fpext` in
`computeKnownFPClass`.
Fixes the miscompilation reported by
https://github.com/llvm/llvm-project/pull/80941#issuecomment-1947302100.
2024-02-17 23:30:45 +08:00
Yingwei Zheng
16a0629e7c
[ValueTracking] Compute known FPClass from signbit idiom (#80740)
This patch improves `computeKnownFPClass` by using context-sensitive
information from `DomConditionCache`.
The motivation of this patch is to optimize the following case found in
[fmt/format.h](e17bc67547/include/fmt/format.h (L3555-L3566)):
```
define float @test(float %x, i1 %cond) {
  %i32 = bitcast float %x to i32
  %cmp = icmp slt i32 %i32, 0
  br i1 %cmp, label %if.then1, label %if.else

if.then1:
  %fneg = fneg float %x
  br label %if.end

if.else:
  br i1 %cond, label %if.then2, label %if.end

if.then2:
  br label %if.end

if.end:
  %value = phi float [ %fneg, %if.then1 ], [ %x, %if.then2 ], [ %x, %if.else ]
  %ret = call float @llvm.fabs.f32(float %value)
  ret float %ret
}
```
We can prove the sign bit of %value is always zero. Then the fabs can be
eliminated.

This pattern also exists in cpython/duckdb/oiio/openexr.

Compile-time impact:
https://llvm-compile-time-tracker.com/compare.php?from=f82e0809ba12170e2f648f8a1ac01e78ef06c958&to=041218bf5491996edd828cc15b3aec5a59ddc636&stat=instructions:u


|stage1-O3|stage1-ReleaseThinLTO|stage1-ReleaseLTO-g|stage1-O0-g|stage2-O3|stage2-O0-g|stage2-clang|
|--|--|--|--|--|--|--|
|-0.00%|+0.01%|+0.00%|-0.03%|+0.00%|+0.00%|+0.02%|
2024-02-14 20:53:16 +08:00
Yingwei Zheng
dc866ae49e
[ValueTracking] Move the isSignBitCheck helper into ValueTracking. NFC. (#81704)
This patch moves the `isSignBitCheck` helper into ValueTracking to reuse
the logic in ValueTracking/InstSimplify.

Addresses the comment
https://github.com/llvm/llvm-project/pull/80740#discussion_r1488440050.
2024-02-14 15:33:08 +08:00
Haojian Wu
a1efe56ace Remove an unused variable in release build. 2024-02-13 09:06:30 +01:00
Yingwei Zheng
542a3cb9cc
[ValueTracking] Compute known FPClass from dominating condition (#80941)
This patch improves `computeKnownFPClass` by using context-sensitive
information from `DomConditionCache`.
2024-02-13 11:18:13 +08:00
Nikita Popov
7c0d52ca91
[ValueTracking] Support dominating known bits condition in and/or (#74728)
This extends computeKnownBits() support for dominating conditions to
also handle and/or conditions. We'll look through either and or or
depending on which edge we're considering.

This change is mainly for the sake of completeness, so we don't start
missing optimizations if SimplifyCFG decides to merge some branches.
2024-02-08 09:47:49 +01:00
Yingwei Zheng
930996e9e4
[ValueTracking][NFC] Pass SimplifyQuery to computeKnownFPClass family (#80657)
This patch refactors the interface of the `computeKnownFPClass` family
to pass `SimplifyQuery` directly.
The motivation of this patch is to compute known fpclass with
`DomConditionCache`, which was introduced by
https://github.com/llvm/llvm-project/pull/73662. With
`DomConditionCache`, we can do more optimization with context-sensitive
information.

Example (extracted from
[fmt/format.h](e17bc67547/include/fmt/format.h (L3555-L3566))):
```
define float @test(float %x, i1 %cond) {
  %i32 = bitcast float %x to i32
  %cmp = icmp slt i32 %i32, 0
  br i1 %cmp, label %if.then1, label %if.else

if.then1:
  %fneg = fneg float %x
  br label %if.end

if.else:
  br i1 %cond, label %if.then2, label %if.end

if.then2:
  br label %if.end

if.end:
  %value = phi float [ %fneg, %if.then1 ], [ %x, %if.then2 ], [ %x, %if.else ]
  %ret = call float @llvm.fabs.f32(float %value)
  ret float %ret
}
```
We can prove the signbit of `%value` is always zero. Then the fabs can
be eliminated.
2024-02-06 02:30:12 +08:00
Yingwei Zheng
50e80e06d1
[ValueTracking] Merge cannotBeOrderedLessThanZeroImpl into computeKnownFPClass (#76360)
This patch merges the logic of `cannotBeOrderedLessThanZeroImpl` into
`computeKnownFPClass` to improve the signbit inference.

---------

Co-authored-by: Matt Arsenault <arsenm2@gmail.com>
2024-01-31 18:26:50 +08:00
Craig Topper
d8e1b451e2
[ValueTracking] Add experimental_get_vector_length to isKnownNonZero. (#79950)
If the input is non-zero, this intrinsic should also return a non-zero
value.
2024-01-30 09:39:13 -08:00
Matt Arsenault
e44d3b3e50
ValueTracking: Merge fcmpImpliesClass and fcmpToClassTest (#66522)
Rushing this one out before vacation starts. Refactoring on top of
#66505
2024-01-27 08:44:36 +05:30
Matt Arsenault
a46422a776 Reapply "ValueTracking: Identify implied fp classes by general fcmp (#66505)"
This reverts commit 0d0c2298552222b049fa3b8db5efef4b161e51e9.

Includes a bug fix for fcmp one handling, as well as for positive constants.
2024-01-25 13:38:23 +05:30