6281 Commits

Author SHA1 Message Date
Florian Hahn
f8b1c7333f
[VPlan] Add getContext helper to VPlan (NFC). 2025-07-27 18:53:53 +01:00
Florian Hahn
4386848776
[VPlan] Add explicit VPUnrollPartAccessor<1> instantiation.
This should fix a build-failure with GCC, including
https://lab.llvm.org/buildbot/#/builders/105/builds/10685.
2025-07-27 14:05:23 +01:00
Florian Hahn
89ae085859
[VPlan] Remove VPVectorPointer for part 0 after unrolling. (#149735)
VPVectorPointer for part 0 is just the pointer operand. Simplify it
after unrolling. This removes a large number of redundant GEPs with
index 0.

PR: https://github.com/llvm/llvm-project/pull/149735
2025-07-27 13:53:26 +01:00
Florian Hahn
c9a87b45a3
[VPlan] Retrieve latch terminator from VPlan. (NFC)
Remove an unnecessary lookup via original IR loop.
2025-07-27 09:48:59 +01:00
Florian Hahn
bc7487d8ed
[VPlan] Cast header and latch to VPBasicBlock early (NFC).
There are only VPBasicBlocks when prepareForVectorization is called.
Cast them early instead of having multiple casts later on.
2025-07-27 09:47:50 +01:00
Florian Hahn
d1f2a661f4
[VPlan] Pass debug location explicitly to VPBlendRecipe (NFC).
This enables creating VPBlendRecipes without underlying PHINode.
2025-07-27 09:12:26 +01:00
Florian Hahn
80c43b6c07
[VPlan] Add ExtractLane VPInst to extract across multiple parts. (#148817)
This patch adds a new ExtractLane VPInstruction which extracts across
multiple parts using a wide index, to be used in combination with
FirstActiveLane.

The patch updates early-exit codegen to use it instead ExtractElement,
which is only per-part. With this change, interleaving should work
correctly with early-exit loops.

The patch removes the restrictions added in 6f43754e9 (#145877), but
does not yet automatically select interleave counts > 1 for early-exit
loops.

I'll share a patch as follow-up. The cost of extracting a lane adds
non-trivial overhead in the exit block, so that should be considered
when picking the interleave count.

PR: https://github.com/llvm/llvm-project/pull/148817
2025-07-27 08:08:25 +01:00
Florian Hahn
82e4b83328
[VPlan] Use terminator debug loc for latch BranchOnCond.
Update VPlan to consistently use the latch branch debug location for the
latch branch in the vector loop, if there is one.
2025-07-26 21:45:25 +01:00
Florian Hahn
fa3ec0c17c
[VPlan] Materialize constant vector trip counts before final opts. (#142309)
Materialize constant vector trip counts before ::execute, if the trip
count can be computed as Original (TC / (VF * UF)) * (VF * UF). For now
this excludes when the tail is folded or scalar epilogues are required.

This enables removing a number of redundant branches from the middle
block.

For now this is also only done when not vectorizing the epilogue, as the
simplification complicates stitching the 2 plans together.

PR: https://github.com/llvm/llvm-project/pull/142309
2025-07-26 17:16:36 +01:00
Florian Hahn
662bede01e
[LV] Handle known-false mem runtime checks in GeneratedRTChecks.
Handle mem checks known to be false in getMemRuntimeChecks the same way
as SCEV checks known to be false in getSCEVChecks. This ensures such
redundant check blocks are not added in the first place.
2025-07-26 15:39:21 +01:00
Florian Hahn
9a201531ed
[LV] Bail out early if runtime checks are known to fail.
There are a number of cases for which SCEV may not be able to prove a
predicate will always be true/false, which may be simplified to a
constant during expansion (see discussion in
https://github.com/llvm/llvm-project/pull/131538).

Bail out early if runtime checks are known to always fail, as the
vector loop generated later will never execute.
2025-07-26 09:26:15 +01:00
Alexey Bataev
ef98e248c7 [SLP]Initial support for copyable elements (non-schedulable only)
Adds initial support for copyable elements. This patch only models adds
and model copyable elements as add <element>, 0, i.e. uses identity
constants for missing lanes.
Only support for elements, which do not require scheduling, is added to
reduce size of the patch.

Fixed compile time regressions, reported crashes, updated release notes

Reviewers: RKSimon, hiraditya

Reviewed By: RKSimon

Pull Request: https://github.com/llvm/llvm-project/pull/140279
2025-07-25 10:55:07 -07:00
Alex Bradbury
5294793bdc Revert "[RISCV][TTI] Enable masked interleave access for scalable vector (#149981)"
This reverts commit ee3a7714b7a69ac9aae4b79f4c67adc38bc6876b.

Causes an assertion for the zvl1024b RISC-V build configuration. See
comment with reproducer at
<https://github.com/llvm/llvm-project/pull/149981#issuecomment-3118482801>
2025-07-25 16:14:10 +01:00
Igor Kirillov
0c91e977c0
[VectorCombine] Refine cost model and decision logic in foldSelectShuffle (#146694)
After PR #136329, shuffle indices may differ, which can cause the
existing cost-based logic to miss optimisation opportunities for
binop/shuffle sequences.

This patch improves the cost model in foldSelectShuffle to more
accurately assess costs, recognising when certain duplicate shuffles do
not require actual instructions.

Additionally, in break-even cases, this change introduces a check for
whether the pattern ultimately feeds into a vector reduction, allowing
the transform to proceed when it is likely to be profitable overall.
2025-07-25 13:28:27 +01:00
Ramkumar Ramachandra
7392131acf
[VPlan] Improve code in VPlanPredicator (NFC) (#150416) 2025-07-25 11:50:19 +01:00
Mel Chen
ee3a7714b7
[RISCV][TTI] Enable masked interleave access for scalable vector (#149981)
Now that support for masked loads/stores of interleave groups has
landed, we can enable the loop vectorizer to generate masked interleave
access where applicable.

This improves vectorization in several ways:
* Internal predication support: This enables interleave group
vectorization for loops with internal control flow predication, provided
all members of the group share the same predicate. Gaps in interleave
groups are still not efficiently handled by masking, so masking for gaps
remains disabled for now.
* Tail folding: This allows tail folding of loops with interleave groups
by using masking. Without this, vectorized loops with interleaves would
fall back to using separate gather/scatter accesses, which can be
significantly less efficient.
* Scalable vector support: Currently, only scalable vector types are
supported for masked interleave lowering. Fixed-length vector support
will be enabled in the future.

As interleave access is not yet supported with tail folding by EVL, that
functionality is temporarily disabled. We are going to create another
patch to support it.

Co-authored-by: Philip Reames <preames@rivosinc.com>

---------

Co-authored-by: Philip Reames <preames@rivosinc.com>
2025-07-25 17:53:08 +08:00
Florian Hahn
1640d51bf8
[VPlan] Mark getUnrollPart argument as const (NFC). 2025-07-25 10:49:33 +01:00
Luke Lau
feb77c0fea
[VPlan] Handle VPWidenSelectRecipe in tryToFoldLiveIns (#150357)
This helps simplify VPBlendRecipes that are expanded to selects in
another patch.
2025-07-25 09:46:19 +08:00
Martin Storsjö
936ee35dcc Revert "[SLP]Initial support for copyable elements (non-schedulable only)"
This reverts commit 898bba311f180ed54de33dc09e7071c279a4942a.

This change caused hangs and crashes, see
https://github.com/llvm/llvm-project/pull/140279#issuecomment-3115051063.
2025-07-25 01:22:20 +03:00
Martin Storsjö
bd170b78bb Revert "[SLP] Check if the user node has state before trying getting main instruction/opcode"
This reverts commit c9cea24fe68e24750b2d479144f839e1c2ec9d2b.

This is being reverted as it is intermixed with another commit
(898bba311f180ed54de33dc09e7071c279a4942a) that needs to be reverted.
2025-07-25 01:22:19 +03:00
Alexey Bataev
c9cea24fe6 [SLP] Check if the user node has state before trying getting main instruction/opcode
Need to check if the parent node has state to prevent compiler crashes.
Fixes #150479
2025-07-24 12:00:43 -07:00
Alexey Bataev
898bba311f [SLP]Initial support for copyable elements (non-schedulable only)
Adds initial support for copyable elements. This patch only models adds
and model copyable elements as add <element>, 0, i.e. uses identity
constants for missing lanes.
Only support for elements, which do not require scheduling, is added to
reduce size of the patch.

Fixed compile time regressions, updated release notes

Reviewers: RKSimon, hiraditya

Reviewed By: RKSimon

Pull Request: https://github.com/llvm/llvm-project/pull/140279
2025-07-23 13:38:34 -07:00
Luke Lau
9563e7a940
[VPlan] Mark VPInstruction::ExplicitVectorLength as single scalar. NFC (#150221)
This allows it to be broadcasted without an explicit
VPInstruction::Broadcast in #150202
2025-07-23 22:38:21 +08:00
Luke Lau
114d74e391
[VPlan] Expand VPBlendRecipes to select instructions. NFC (#133993)
When looking at some EVL tail folded code in SPEC CPU 2017 I noticed we
sometimes have both VPBlendRecipes and select VPInstructions in the same
plan:

    EMIT vp<%active.lane.mask> = active lane mask vp<%5>, vp<%3>
    EMIT vp<%7> = icmp ...
    EMIT vp<%8> = logical-and vp<%active.lane.mask>, vp<%7>
    BLEND ir<%8> = ir<%n.015> ir<%foo>/vp<%8>
    EMIT vp<%9> = select vp<%active.lane.mask>, ir<%8>, ir<%n.015>

Since a blend will ultimately generate a chain of selects, we could fold
the blend into the select:

    EMIT vp<%active.lane.mask> = active lane mask vp<%5>, vp<%3>
    EMIT vp<%7> = icmp ...
    EMIT vp<%8> = logical-and vp<%active.lane.mask>, vp<%7>
    EMIT ir<%8> = select vp<%8>, ir<%foo>, ir<%n.015>

So as a first step, this patch expands blends to a series of select
instructions, which may allow them to be simplified further with other
select instructions.
2025-07-23 20:09:33 +08:00
Florian Hahn
77b1b956da
[LV] Also clamp MaxVF by trip count when maximizing vector bandwidth. (#149794)
Also clamp the max VF when maximizing vector bandwidth by the maximum
trip count. Otherwise we may end up choosing a VF for which the vector
loop never executes.

PR: https://github.com/llvm/llvm-project/pull/149794
2025-07-23 10:19:56 +01:00
Luke Lau
20c52e4231 Reapply "[RISCV][LoopVectorize] Use DataWithEVL as the preferred tail folding style (#148686)"
This reverts commit 25e97fc420f8ecc43fbabadfe9767b4163e6ee36.

The original commit was reverted due to a crash in llvm-test-suite. The
crash stemmed from a multiply reduction, which isn't supported for
scalable VFs on RISC-V. But for EVL tail folding we only support
scalable VFs, so when -force-tail-folding-style=data-with-evl is
specified we check to see if there's a scalable VF, and fall back to
data-without-lane-mask if there isn't.

This is done in setTailFoldingStyles, but previously we were only
checking if the forced tail folding style was legal, not the style
returned by TTI.

This version fixes this by checking the actual computed tail folding
style and not just the forced one, and adds a test for the crash in
llvm/test/Transforms/LoopVectorize/RISCV/low-trip-count.ll
2025-07-22 23:52:02 +08:00
Alexey Bataev
a415d68e48 Revert "[SLP]Initial support for copyable elements (non-schedulable only)"
This reverts commit e202dba288edd47f1b370cc43aa8cd36a924e7c1 to try to
resolve compile time issues, reported in https://llvm-compile-time-tracker.com/compare.php?from=36089e5d983fe9ae00f497c2d500f37227f82db1&to=e202dba288edd47f1b370cc43aa8cd36a924e7c1&stat=instructions%3Au&details=on
2025-07-22 07:39:32 -07:00
Luke Lau
6e723d2de8
[VPlan] Remove loop region in simplifyBranchConditionForVFAndUF with EVL PHI (#150016)
Previously we fell back to just simplifying the branch cond to true
since one of the phis was a VPEVLBasedIVPHIRecipe. However this should
be fine to replace with its start value.
2025-07-22 22:30:34 +08:00
Florian Hahn
37f0f10a85
[LV] Don't vectorize epilogue with scalable VF if no iterations remain. (#149789)
Currently we may try to vectorize the epilogue with a scalable VF, even
if there are no remaining iterations after the main vector loop with a
fixed VF.

Update selectEpilogueVectorizationFactor to always compute the number of
remaining iterations and exit early if no epilogue iterations remain.

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

PR: https://github.com/llvm/llvm-project/pull/149789
2025-07-22 13:13:31 +01:00
Mel Chen
6752369139
[LV] Unify interleaved load handling for fixed and scalable VFs. nfc (#146914)
This patch modifies VPInterleaveRecipe::execute to handle both fixed and
scalable VFs using a single loop.
2025-07-22 09:00:10 +08:00
Alexey Bataev
e202dba288
[SLP]Initial support for copyable elements (non-schedulable only)
Adds initial support for copyable elements. This patch only models adds
and model copyable elements as add <element>, 0, i.e. uses identity
constants for missing lanes.
Only support for elements, which do not require scheduling, is added to
reduce size of the patch.

Reviewers: RKSimon, hiraditya

Reviewed By: RKSimon

Pull Request: https://github.com/llvm/llvm-project/pull/140279
2025-07-21 14:07:28 -04:00
Rahul Yadav
04e5e643f5
[VectorCombine] Generalize foldBitOpOfBitcasts to support more cast operations (#148350)
This patch generalizes the existing foldBitOpOfBitcasts optimization in the VectorCombine pass to handle additional cast operations beyond just bitcast.

  Fixes: [#146037](https://github.com/llvm/llvm-project/issues/146037)

  Summary

The optimization now supports folding bitwise operations (AND/OR/XOR)
with the following cast operations:
  - bitcast (original functionality)
  - trunc (truncate)
  - sext (sign extend)
  - zext (zero extend)

  The transformation pattern is:
  bitop(castop(x), castop(y)) -> castop(bitop(x, y))

This reduces the number of cast instructions from 2 to 1, improving
performance on targets where cast operations
are expensive or where performing bitwise operations on narrower types
is beneficial.
  
  Implementation Details

- Renamed foldBitOpOfBitcasts to foldBitOpOfCastops to reflect broader
functionality
  - Extended pattern matching to handle any CastInst operation
- Added validation for each cast type's constraints (e.g., trunc
requires source > dest)
  - Updated cost model to use the actual cast opcode
  - Preserves IR flags from original instructions
  - Handles multi-use scenarios appropriately

  Testing

- Added comprehensive tests in
test/Transforms/VectorCombine/bitop-of-castops.ll
  - Tests cover all supported cast types with all bitwise operations
  - Includes negative tests for unsupported patterns
  - All existing VectorCombine tests pass
2025-07-21 17:14:56 +01:00
Florian Hahn
3813567e08
[VPlan] Clarify transform name to handlMaxNumNumReductions. (NFC)
Clarify name as suggested in https://github.com/llvm/llvm-project/pull/149736,
as only FMaxNum and FMinNum are handled.
2025-07-21 07:14:46 +01:00
Florian Hahn
e3af202fd2
[VPlan] Remove unused IsReplicator arg from createVPRegionBlock (NFC).
The argument is always true, remove it.
2025-07-20 20:58:25 +01:00
Florian Hahn
3fd53db858
[VPlan] Remove unneeded VPVectorPointer after narrowing to replicate.
The replicate recipes created when narrowing interleave groups don't
need a VPVectorPointer, they can simply use the existing pointer.
2025-07-19 20:18:04 +01:00
Kazu Hirata
28c1433cf3 [Vectorize] Fix a warning
This patch fixes:

  llvm/lib/Transforms/Vectorize/VPlanConstruction.cpp:726:13: error:
  unused variable 'RedPhiRK' [-Werror,-Wunused-variable]
2025-07-18 14:58:52 -07:00
Florian Hahn
004c67ea25
[LV] Vectorize maxnum/minnum w/o fast-math flags. (#148239)
Update LV to vectorize maxnum/minnum reductions without fast-math flags,
by adding an extra check in the loop if any inputs to maxnum/minnum are
NaN, due to maxnum/minnum behavior w.r.t to signaling NaNs. Signed-zeros 
are already handled consistently by maxnum/minnum.

If any input is NaN,
 *exit the vector loop,
 *compute the reduction result up to the vector iteration that contained
   NaN inputs and
 * resume in the scalar loop


New recurrence kinds are added for reductions using maxnum/minnum
without fast-math flags.

PR: https://github.com/llvm/llvm-project/pull/148239
2025-07-18 21:58:19 +01:00
Nicholas Guy
534b9cdddd
[LoopVectorizer][NFC] Update comment regarding VF register pressure. (#149478) 2025-07-18 09:55:00 +01:00
Nicholas Guy
20fc297ce3
[LoopVectorizer] Only check register pressure for VFs that have been enabled via maxBandwidth (#149056)
Currently if MaxBandwidth is enabled, the register pressure is checked
for each VF. This changes that to only perform said check if the VF
would not have otherwise been considered by the LoopVectorizer if
maxBandwidth was not enabled.

Theoretically this allows for higher VFs to be considered than would
otherwise be deemed "safe" (from a regpressure perspective), but more
concretely this reduces the amount of work done at compile-time when
maxBandwidth is enabled.
2025-07-18 09:21:20 +01:00
Alexey Bataev
60ae9c9c63
[SLP]Do not consider non-profitable loads slices
If all slices are small and end up with strided or even vectorization
states, better to not consider these candidates for the vectorization
and try to vectorize the whole bunch as gathered loads.

Reviewers: hiraditya, RKSimon, HanKuanChen

Reviewed By: RKSimon, HanKuanChen

Pull Request: https://github.com/llvm/llvm-project/pull/149209
2025-07-17 08:00:02 -04:00
Florian Hahn
2cdcc4f2c6
[VPlan] Allow cloning of VPWidenRecipe without underlying instr (NFC).
Update VPWidenRecipe::clone() to use the constructor w/o mandatory
Instruction, to facilitate cloning VPWidenRecipe without underlying
instructions.

Split off from https://github.com/llvm/llvm-project/pull/148239.
2025-07-17 10:42:34 +01:00
Piotr Fusik
ade2f1023d
[SLP][NFCI] Don't trim indexes, reuse a variable (#149074) 2025-07-16 14:09:27 +02:00
Piotr Fusik
7674566c96
[SLP][NFC] Simplify count_if to count (#149072) 2025-07-16 14:09:09 +02:00
Piotr Fusik
949103b45c
[SLP][NFC] Use range-based for in matchAssociativeReduction (#149029) 2025-07-16 14:08:41 +02:00
Florian Hahn
afe8150780
[VPlan] Simplify exituser handling by generating all extracts first(NFCI)
Simplify the handling of exit users by generating all extracts first
(safe option), and have FOR handling optimize the extracts, similar to
already done for reductions and inductions.

NFC modulo first-order recurrence extract order in middle block.
2025-07-16 08:14:12 +01:00
Jeremy Morse
57a5f9c47e
[DebugInfo][RemoveDIs] Suppress getNextNonDebugInfoInstruction (#144383)
There are no longer debug-info instructions, thus we don't need this
skipping. Horray!
2025-07-15 15:34:10 +01:00
Gaëtan Bossu
adb6efeac9
[SLP] Fix cost estimation of external uses with wrong VF (#148185)
It assumed that the VF remains constant throughout the tree. That's not
always true. This meant that we could query the extraction cost for a
lane that is out of bounds.

While experimenting with re-vectorisation for AArch64, we ran into this
issue. We cannot add a proper AArch64 test as more changes would need to
be brought in.

This commit is only fixing the computation of VF and adding an assert.
Some tests were failing after adding the assert:
 - foo() in llvm/test/Transforms/SLPVectorizer/X86/horizontal.ll
- test() in
llvm/test/Transforms/SLPVectorizer/X86/reduction-with-removed-extracts.ll
- test_with_extract() in
llvm/test/Transforms/SLPVectorizer/RISCV/segmented-loads.ll
2025-07-15 11:39:09 +01:00
Florian Hahn
a40dc05898
[VPlan] Mark canonical IV and reduction phis as not writing memory (NFC).
Both recipes do not write to memory. Should be NFC at the moment, as
they cannot be removed currently due to being in a cycle.
2025-07-15 11:08:54 +01:00
David Sherwood
c363a3f9c8
[LV] Ensure getScaledReductions only matches extends inside the loop (#148264)
In getScaledReductions for the case where we try to match a partial
reduction of the form:

%phi = phi i32 ...
...
%add = add i32 %phi, %zext

where

%zext = i8 %some_val to i32

we should ensure that %zext is actually inside the loop.

Fixes https://github.com/llvm/llvm-project/issues/148260
2025-07-15 09:54:58 +01:00
Luke Lau
c8d0e24745
[VPlan] Preserve trunc nuw/nsw in VPRecipeWithIRFlags (#144700)
This preserves the nuw/nsw flags on widened truncs by checking for
TruncInst in the VPIRFlags constructor

The motivation for this is to be able to fold away some redundant truncs
feeding into uitofps (or potentially narrow the inductions feeding them)
2025-07-15 15:34:14 +08:00