818 Commits

Author SHA1 Message Date
Nikita Popov
8cdca96690 [GVN] Adjust metadata for coerced load CSE
When reusing a load in a way that requires coercion (i.e. casts or
bit extraction) we currently fail to adjust metadata. Unfortunately,
none of our existing tooling for this is really suitable, because
combineMetadataForCSE() expects both loads to have the same type.
In this case we may work on loads of different types and possibly
offset memory location.

As such, what this patch does is to simply drop all metadata, with
the following exceptions:

* Metadata for which violation is known to always cause UB.
* If the load is !noundef, keep all metadata, as this will turn
  poison-generating metadata into UB as well.

This fixes the miscompile that was exposed by D146629.

Differential Revision: https://reviews.llvm.org/D148129
2023-04-17 12:52:31 +02:00
Nikita Popov
ae28e016d3 [VNCoercion] Drop some redundant functions (NFC)
These load and store APIs now do the same thing, so combine them
into one.
2023-04-12 16:46:54 +02:00
Nikita Popov
6e78fd58cd [GVN][VNCoercion] Remove load widening leftovers (NFCI)
GVN load widening was disabled in D24096. This removes various
support code that is no longer relevant.

The way this works nowadays is that we return PartialAlias with
an offset from BasicAA and this gets passed on as a clobber by
MDA. However, PartialAlias will only be returned if the load is
properly nested inside the other load.

This just removes the bulk of the code, but some additional
cleanup can be done here now that we don't need to distinguish
between load and store cases.
2023-04-12 16:32:46 +02:00
Nikita Popov
e7618a6361 [GVN] Fix change reporting when removing assume (PR61574)
Report a change when removing a true/false assume.

Fixes https://github.com/llvm/llvm-project/issues/61574.
2023-03-22 15:23:31 +01:00
Sergey Kachkov
1aece0e5ed Revert "[GVN] Support address translation through select instructions"
This reverts commit b5bf6f6392a3408be1b7b7e036eb69358c5a2c29.
2023-02-27 12:57:59 +03:00
Sergey Kachkov
b5bf6f6392 [GVN] Support address translation through select instructions
Process cases when phi incoming in predecessor block has select
instruction, and this select address is unavailable, but there
are addresses translated from both sides of select instruction.

Differential Revision: https://reviews.llvm.org/D142705
2023-02-27 12:08:15 +03:00
Liren Peng
529ee9750b [NFC] Use single quotes for single char output during printPipline
Reviewed By: arsenm

Differential Revision: https://reviews.llvm.org/D144365
2023-02-22 02:35:13 +00:00
Sergey Kachkov
6f9e3f3b33 [NFC] Fix function naming conventions in PHITransAddr methods
Differential Revision: https://reviews.llvm.org/D143166
2023-02-02 16:38:39 +03:00
Guozhi Wei
43969af627 Revert "[GVN] Improve PRE on load instructions"
This reverts commit 5f1448fe1585b5677d5f0064e4eeac3b493d8a18.
2023-02-01 22:48:31 +00:00
Guozhi Wei
3a5777f630 Revert "[GVN] Don't count debug instructions when limit the number of checked instructions"
This reverts commit f494b366ff8a076a72a8e1b7a6f401686d6eb0e6.
2023-02-01 22:48:06 +00:00
Guozhi Wei
f494b366ff [GVN] Don't count debug instructions when limit the number of checked instructions
Don't count debug instructions when limit the number of checked instructions.
Otherwise the debug information may impact optimization like the test case
shows.

Differential Revision: https://reviews.llvm.org/D142787
2023-01-31 21:04:03 +00:00
NAKAMURA Takumi
6595ef0900 GVN.cpp: Suppress a warning in D141712 [-Wunused-variable] 2023-01-26 09:53:59 +09:00
Guozhi Wei
5f1448fe15 [GVN] Improve PRE on load instructions
This patch implements the enhancement proposed by
https://github.com/llvm/llvm-project/issues/59312.

Suppose we have following code

   v0 = load %addr
   br %LoadBB

 LoadBB:
   v1 = load %addr
   ...

 PredBB:
   ...
   br %cond, label %LoadBB, label %SuccBB

 SuccBB:
   v2 = load %addr
   ...

Instruction v1 in LoadBB is partially redundant, edge (PredBB, LoadBB) is a
critical edge. SuccBB is another successor of PredBB, it contains another load
v2 which is identical to v1. Current GVN splits the critical edge
(PredBB, LoadBB) and inserts a new load in it. A better method is move the load
of v2 into PredBB, then v1 can be changed to a PHI instruction.

If there are two or more similar predecessors, like the test case in the bug
entry, current GVN simply gives up because otherwise it needs to split multiple
critical edges. But we can move all loads in successor blocks into predecessors.

Differential Revision: https://reviews.llvm.org/D141712
2023-01-25 19:45:01 +00:00
Sergey Kachkov
e1a702db2f [GVN] Refactor findDominatingLoad function
Improve findDominatingLoad implementation:
1. Result is saved into gvn::AvailableValue struct
2. Search is done in extended BB (while there is a single predecessor or
   limit is reached)

Differential Revision: https://reviews.llvm.org/D141680
2023-01-20 11:54:11 +03:00
Sergey Kachkov
bfd2dd49ff [GVN] Refactor handling of pointer-select in GVN pass
This patch extends Def memory dependency with support of select
instructions to consistently handle pointer-select conversion.

Differential Revision: https://reviews.llvm.org/D141619
2023-01-17 11:32:06 +03:00
Sergey Kachkov
868abc471d Revert "[GVN] Refactor handling of pointer-select in GVN pass"
This reverts commit fc7cdaa373308ce3d72218b4d80101ae19850a6c.
2023-01-16 15:13:17 +03:00
Sergey Kachkov
fc7cdaa373 [GVN] Refactor handling of pointer-select in GVN pass
This patch introduces new type of memory dependency - Select to
consistently handle it like Def/Clobber dependency.

Differential Revision: https://reviews.llvm.org/D141619
2023-01-16 14:12:28 +03:00
Sergey Kachkov
fc9b92e14f [GVN][NFC] Refactor GVN::AnalyzeLoadAvailability method
Simplify AnalyzeLoadAvailability code:
1. Use std::optional for return value
2. Use range-based loop for non-local dependencies

Differential Revision: https://reviews.llvm.org/D141664
2023-01-13 12:24:47 +03:00
Guozhi Wei
9852941f01 Revert "[GVN] Improve PRE on load instructions"
This reverts commit 1f1d501843e5cf8741599035d6ef66a3eb5e1e9e.

This patch caused several sanitizer tests failed. Revert it to unblock
others.
2023-01-10 02:35:35 +00:00
Benjamin Kramer
38c481ddcb [GVN] Fold variable into assert. NFC
Avoids unused variable warnings when asserts are disabled.
2023-01-10 00:39:51 +01:00
Guozhi Wei
1f1d501843 [GVN] Improve PRE on load instructions
This patch implements the enhancement proposed by
https://github.com/llvm/llvm-project/issues/59312.

Suppose we have following code

   v0 = load %addr
   br %LoadBB

 LoadBB:
   v1 = load %addr
   ...

 PredBB:
   ...
   br %cond, label %LoadBB, label %SuccBB

 SuccBB:
   v2 = load %addr
   ...

Instruction v1 in LoadBB is partially redundant, edge (PredBB, LoadBB) is a
critical edge. SuccBB is another successor of PredBB, it contains another load
v2 which is identical to v1. Current GVN splits the critical edge
(PredBB, LoadBB) and inserts a new load in it. A better method is move the load
of v2 into PredBB, then v1 can be changed to a PHI instruction.

If there are two or more similar predecessors, like the test case in the bug
entry, current GVN simply gives up because otherwise it needs to split multiple
critical edges. But we can move all loads in successor blocks into predecessors.

Differential Revision: https://reviews.llvm.org/D139582
2023-01-09 23:08:41 +00:00
Fangrui Song
51b685734b [Transforms,CodeGen] std::optional::value => operator*/operator->
value() has undesired exception checking semantics and calls
__throw_bad_optional_access in libc++. Moreover, the API is unavailable without
_LIBCPP_NO_EXCEPTIONS on older Mach-O platforms (see
_LIBCPP_AVAILABILITY_BAD_OPTIONAL_ACCESS).
2022-12-16 23:21:27 +00:00
Simon Pilgrim
d46f6cd767 [GVN] reportMayClobberedLoad - avoid repeated cast<> calls. NFCI.
Just perform each cast<Instruction> once - we can make OtherAccess a Instruction* type as we only ever assign it from a known LoadInst/StoreInst
2022-12-15 15:44:35 +00:00
Simon Pilgrim
23e3e107dc [GVN] GVNPass::ValueTable::lookupOrAdd - merge isa<> and cast<> into single dyn_cast<>. NFCI.
Avoid calling separate isa<> and cast<> if we can - dyn_cast<> can more efficiently check for a safe cast and give the casted pointer.
2022-12-14 19:47:57 +00:00
Simon Pilgrim
636089d8dc [GVN] hasUsersIn - merge isa<> and cast<> into single dyn_cast<> and convert for-range loop to any_of() test. NFCI.
Avoid running isa<> and cast<> if we can - dyn_cast<> can more efficiently check for a safe cast and give the casted pointer.
2022-12-14 19:42:42 +00:00
Kazu Hirata
343de6856e [Transforms] Use std::nullopt instead of None (NFC)
This patch mechanically replaces None with std::nullopt where the
compiler would warn if None were deprecated.  The intent is to reduce
the amount of manual work required in migrating from Optional to
std::optional.

This is part of an effort to migrate from llvm::Optional to
std::optional:

https://discourse.llvm.org/t/deprecating-llvm-optional-x-hasvalue-getvalue-getvalueor/63716
2022-12-02 21:11:37 -08:00
Kazu Hirata
b54cd3f09c [Scalar] Use std::optional in GVN.cpp (NFC)
This is part of an effort to migrate from llvm::Optional to
std::optional:

https://discourse.llvm.org/t/deprecating-llvm-optional-x-hasvalue-getvalue-getvalueor/63716
2022-11-25 23:55:44 -08:00
Alex Gatea
7d0648cb6c [GVN] Patch for invalid GVN replacement
If PRE is performed as part of the main GVN pass (to PRE GEP
operands before processing loads), and it is performed across a
backedge, we will end up adding the new instruction to the leader
table of a block that has not yet been processed. When it will be
processed, GVN will incorrectly assume that the value is already
available, even though it is only available at the end of the
block.

Avoid this by not performing PRE across backedges.

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

Differential Revision: https://reviews.llvm.org/D136095
2022-11-04 14:28:17 +01:00
Chuanqi Xu
1cedc51ff5 [Coroutines] Don't merge readnone calls in presplit coroutines
Another alternative to fix the thread identification problem in
coroutines.

We plan to fix this problem by unifying memory effecting attributes. See
https://discourse.llvm.org/t/rfc-unify-memory-effect-attributes/65579.
But it may be a long-term project. And it is a pity that the coroutines
can't resume in different threads for years. So this one is temporary
fix. It may cause unnecessary performance regression for coroutines. But
correctness are more important. And this one is planned to be reverted
after we are able to unify the memory effecting attributes actually.

Reviewed By: jdoerfert, rjmccall

Differential Revision: https://reviews.llvm.org/D135550
2022-10-17 10:22:43 +08:00
Matt Arsenault
84a2e48ce6 GVN: Pass through AssumptionCache to queries 2022-09-19 19:25:22 -04:00
Matt Arsenault
ce44357216 Analysis: Add AssumptionCache to isSafeToSpeculativelyExecute
Does not update any of the uses.
2022-09-19 19:25:22 -04:00
Kazu Hirata
fedc59734a [llvm] Use range-based for loops (NFC) 2022-09-03 11:17:40 -07:00
Kazu Hirata
50724716cd [Transforms] Qualify auto in range-based for loops (NFC)
Identified with readability-qualified-auto.
2022-08-14 12:51:58 -07:00
Kazu Hirata
0e37ef0186 [Transforms] Fix comment typos (NFC) 2022-08-07 23:55:24 -07:00
Kazu Hirata
611ffcf4e4 [llvm] Use value instead of getValue (NFC) 2022-07-13 23:11:56 -07:00
Nikita Popov
34a5c2bcf2 [BasicBlockUtils] Allow critical edge splitting with callbr terminators
After D129205, we support SplitBlockPredecessors() for predecessors
with callbr terminators. This means that it is now also safe to
invoke critical edge splitting for an edge coming from a callbr
terminator. Remove checks in various passes that were protecting
against that.

Differential Revision: https://reviews.llvm.org/D129256
2022-07-08 09:20:44 +02:00
Vir Narula
89a99ec900
[GVN] Bug fix to reportMayClobberedLoad remark
Bug fix to avoid assert crashing when generating remarks for GVN crashing.

Intention of assert is correct but ignores edge case of instructions being equivalent.

Reduced input that causes crash when remarks are turned on:
```
target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
target triple = "arm64-apple-macosx12.0.0"

define ptr @ReplaceWithTidy(ptr %zz_hold) {
cond.end480.us:
  %0 = load ptr, ptr null, align 8
  store ptr %0, ptr %0, align 8
  store ptr null, ptr %zz_hold, align 8
  %1 = load ptr, ptr %0, align 8
  store ptr %1, ptr null, align 8
  ret ptr null
}
```

Reviewed By: fhahn

Differential Revision: https://reviews.llvm.org/D129235
2022-07-06 17:42:05 -07:00
Kazu Hirata
3b7c3a654c Revert "Don't use Optional::hasValue (NFC)"
This reverts commit aa8feeefd3ac6c78ee8f67bf033976fc7d68bc6d.
2022-06-25 11:56:50 -07:00
Kazu Hirata
aa8feeefd3 Don't use Optional::hasValue (NFC) 2022-06-25 11:55:57 -07:00
Nikita Popov
871197d0a3 [MemoryBuiltins] Accept any value in getInitialValueOfAllocation() (NFC)
Drop the requirement that getInitialValueOfAllocation() must be
passed an allocator function, shifting the responsibility for
checking that into the function (which it does anyway). The
motivation is to avoid some calls to isAllocationFn(), which has
somewhat ill-defined semantics (given the number of
allocator-related attributes we have floating around...)

(For this function, all we eventually need is an allockind of
zeroed or uninitialized.)

Differential Revision: https://reviews.llvm.org/D127274
2022-06-24 16:08:07 +02:00
Kazu Hirata
7a47ee51a1 [llvm] Don't use Optional::getValue (NFC) 2022-06-20 22:45:45 -07:00
Kazu Hirata
129b531c9c [llvm] Use value_or instead of getValueOr (NFC) 2022-06-18 23:07:11 -07:00
Simon Moll
b8c2781ff6 [NFC] format InstructionSimplify & lowerCaseFunctionNames
Clang-format InstructionSimplify and convert all "FunctionName"s to
"functionName".  This patch does touch a lot of files but gets done with
the cleanup of InstructionSimplify in one commit.

This is the alternative to the less invasive clang-format only patch: D126783

Reviewed By: spatel, rengolin

Differential Revision: https://reviews.llvm.org/D126889
2022-06-09 16:10:08 +02:00
Fangrui Song
557efc9a8b [llvm] Remove unneeded cl::ZeroOrMore for cl::opt options. NFC
Some cl::ZeroOrMore were added to avoid the `may only occur zero or one times!`
error. More were added due to cargo cult. Since the error has been removed,
cl::ZeroOrMore is unneeded.

Also remove cl::init(false) while touching the lines.
2022-06-03 21:59:05 -07:00
Nikita Popov
1721ff1dfd [GVN] Enable enable-split-backedge-in-load-pre option by default
This option was added in D89854. It prevents GVN from performing
load PRE in a loop, if doing so would require critical edge
splitting on the backedge. From the review:

> I know that GVN Load PRE negatively impacts peeling,
> loop predication, so the passes expecting that latch has
> a conditional branch.

In the PhaseOrdering test in this patch, splitting the backedge
negatively affects vectorization: After critical edge splitting,
the loop gets rotated, effectively peeling off the first loop
iteration. The effect is that the first element is handled
separately, then the bulk of the elements use a vectorized
reduction (but using unaligned, off-by-one memory accesses) and
then a tail of 15 elements is handled separately again.

It's probably worth noting that the loop load PRE from D99926 is
not affected by this change (as it does not need backedge
splitting). This is about normal load PRE that happens to occur
inside a loop.

Differential Revision: https://reviews.llvm.org/D126382
2022-05-30 09:55:58 +02:00
Owen Anderson
939a43461b Revert "Replace the custom linked list in LeaderTableEntry with TinyPtrVector."
This reverts commit 1e9114984490b83d4665f12a11f84c83f50ca8f0.

Pending further discussion.
2022-05-26 09:50:36 -07:00
Owen Anderson
1e91149844 Replace the custom linked list in LeaderTableEntry with TinyPtrVector.
The purpose of the custom linked list was to optimize for the case
of a single-element list. It turns out that TinyPtrVector handles
the same basic scenario even better, reducing the size of
LeaderTableEntry by 33%, and requiring only log2(N) allocations
as the size of the list grows. The only downside is that we have
to store the Value's and BasicBlock's in separate vectors, which
is slightly awkward in a few cases. Fortunately that ends up being
entirely encapsulated inside helper functions.

Reviewed By: asbirlea

Differential Revision: https://reviews.llvm.org/D125205
2022-05-25 23:52:44 -07:00
Nikita Popov
b9dc565147 [GVN] Encode GEPs in offset representation
When using opaque pointers, convert GEPs into offset representation
of the form P + V1 * Scale1 + V2 * Scale2 + ... + ConstantOffset.
This allows us to recognize equivalent address calculations even if
the GEPs don't use the same source element type.

This fixes an opaque pointer codegen regression seen in rustc.

Differential Revision: https://reviews.llvm.org/D124527
2022-04-28 09:32:05 +02:00
Martin Storsjö
46776f7556 Fix warnings about variables that are set but only used in debug mode
Add void casts to mark the variables used, next to the places where
they are used in assert or `LLVM_DEBUG()` expressions.

Differential Revision: https://reviews.llvm.org/D123117
2022-04-06 10:01:46 +03:00
Nikita Popov
cf18ec445d [GVN] Check load type in select PRE
This is no longer implicitly guaranteed with opaque pointers.
2022-03-14 12:46:54 +01:00