Skip to content

Conversation

@kasuga-fj
Copy link
Contributor

This patch replaces the delinearization function used in LoopCacheAnalysis, switching from one that depends on type information in GEPs to one that does not. Once this patch and #161822 are landed, we can delete tryDelinearizeFixedSize from Delienarization, which is a optimization heuristic guided by GEP type information. After Polly eliminates its use of getIndexExpressionsFromGEP, we will be able to completely delete GEP-driven heuristics from Delinearization.

@llvmbot llvmbot added the llvm:analysis Includes value tracking, cost tables and constant folding label Oct 23, 2025
@llvmbot
Copy link
Member

llvmbot commented Oct 23, 2025

@llvm/pr-subscribers-llvm-transforms

@llvm/pr-subscribers-llvm-analysis

Author: Ryotaro Kasuga (kasuga-fj)

Changes

This patch replaces the delinearization function used in LoopCacheAnalysis, switching from one that depends on type information in GEPs to one that does not. Once this patch and #161822 are landed, we can delete tryDelinearizeFixedSize from Delienarization, which is a optimization heuristic guided by GEP type information. After Polly eliminates its use of getIndexExpressionsFromGEP, we will be able to completely delete GEP-driven heuristics from Delinearization.


Full diff: https://github.com/llvm/llvm-project/pull/164798.diff

3 Files Affected:

  • (modified) llvm/include/llvm/Analysis/LoopCacheAnalysis.h (+2-1)
  • (modified) llvm/lib/Analysis/LoopCacheAnalysis.cpp (+11-15)
  • (modified) llvm/test/Analysis/LoopCacheAnalysis/interchange-refcost-overflow.ll (+1-1)
diff --git a/llvm/include/llvm/Analysis/LoopCacheAnalysis.h b/llvm/include/llvm/Analysis/LoopCacheAnalysis.h
index 3e22487e5e349..70ccd8aaed20f 100644
--- a/llvm/include/llvm/Analysis/LoopCacheAnalysis.h
+++ b/llvm/include/llvm/Analysis/LoopCacheAnalysis.h
@@ -102,7 +102,8 @@ class IndexedReference {
 
   /// Attempt to delinearize \p AccessFn for fixed-size arrays.
   bool tryDelinearizeFixedSize(const SCEV *AccessFn,
-                               SmallVectorImpl<const SCEV *> &Subscripts);
+                               SmallVectorImpl<const SCEV *> &Subscripts,
+                               const SCEV *ElementSize);
 
   /// Return true if the index reference is invariant with respect to loop \p L.
   bool isLoopInvariant(const Loop &L) const;
diff --git a/llvm/lib/Analysis/LoopCacheAnalysis.cpp b/llvm/lib/Analysis/LoopCacheAnalysis.cpp
index 050c32707596a..c1ce736bb51b0 100644
--- a/llvm/lib/Analysis/LoopCacheAnalysis.cpp
+++ b/llvm/lib/Analysis/LoopCacheAnalysis.cpp
@@ -355,22 +355,18 @@ CacheCostTy IndexedReference::computeRefCost(const Loop &L,
 }
 
 bool IndexedReference::tryDelinearizeFixedSize(
-    const SCEV *AccessFn, SmallVectorImpl<const SCEV *> &Subscripts) {
-  SmallVector<int, 4> ArraySizes;
-  if (!tryDelinearizeFixedSizeImpl(&SE, &StoreOrLoadInst, AccessFn, Subscripts,
-                                   ArraySizes))
+    const SCEV *AccessFn, SmallVectorImpl<const SCEV *> &Subscripts,
+    const SCEV *ElementSize) {
+  const SCEV *Offset = SE.removePointerBase(AccessFn);
+  if (!delinearizeFixedSizeArray(SE, Offset, Subscripts, Sizes, ElementSize)) {
+    Sizes.clear();
     return false;
+  }
 
-  // Populate Sizes with scev expressions to be used in calculations later.
-  for (auto Idx : seq<unsigned>(1, Subscripts.size()))
-    Sizes.push_back(
-        SE.getConstant(Subscripts[Idx]->getType(), ArraySizes[Idx - 1]));
-
-  LLVM_DEBUG({
-    dbgs() << "Delinearized subscripts of fixed-size array\n"
-           << "GEP:" << *getLoadStorePointerOperand(&StoreOrLoadInst)
-           << "\n";
-  });
+  // Drop the last element of Sizes which is the same as ElementSize.
+  assert(!Sizes.empty() && Sizes.back() == ElementSize &&
+         "Expecting the last one to be the element size");
+  Sizes.pop_back();
   return true;
 }
 
@@ -397,7 +393,7 @@ bool IndexedReference::delinearize(const LoopInfo &LI) {
 
     bool IsFixedSize = false;
     // Try to delinearize fixed-size arrays.
-    if (tryDelinearizeFixedSize(AccessFn, Subscripts)) {
+    if (tryDelinearizeFixedSize(AccessFn, Subscripts, ElemSize)) {
       IsFixedSize = true;
       // The last element of Sizes is the element size.
       Sizes.push_back(ElemSize);
diff --git a/llvm/test/Analysis/LoopCacheAnalysis/interchange-refcost-overflow.ll b/llvm/test/Analysis/LoopCacheAnalysis/interchange-refcost-overflow.ll
index 7b6529601da32..30554d08a6181 100644
--- a/llvm/test/Analysis/LoopCacheAnalysis/interchange-refcost-overflow.ll
+++ b/llvm/test/Analysis/LoopCacheAnalysis/interchange-refcost-overflow.ll
@@ -9,8 +9,8 @@
 ;       A[c][d][d] = 0;
 ; }
 
-; CHECK: Loop 'outer.loop' has cost = 9223372036854775807
 ; CHECK: Loop 'inner.loop' has cost = 9223372036854775807
+; CHECK: Loop 'outer.loop' has cost = 10000
 
 @A = local_unnamed_addr global [11 x [11 x [11 x i32]]] zeroinitializer, align 16
 

Comment on lines 11 to 14

; CHECK: Loop 'outer.loop' has cost = 9223372036854775807
; CHECK: Loop 'inner.loop' has cost = 9223372036854775807
; CHECK: Loop 'outer.loop' has cost = 10000

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test was added in #111807. Based on the description of the PR, the test appears to ensure that no assertion errors are triggered, so I believe this change is not particularly significant.

Copy link
Member

@Meinersbur Meinersbur Oct 28, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sjoerdmeijer Can you confirm? Seems that it is basically ceiling the cost number to UINT64_MAX, so inner.loop is still testing that.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for the delay, thanks for the ping, this dropped off my radar.

Hmmm, yeah, this is a bit of an interesting test case change. This change reveals that the test is fragile: apparently the accuracy of the analysis has improved, and it is now able to more bound the cost a lot better. The result is a small cost value, which is not going to overflow. So, from that point of view, the test is no longer testing what it is supposed to test, i.e. it is saturating to UINT_MAX and it is able to hold value 9223372036854775807.

Again, that is a problem with the test, not this change. But just wondering if you'd already looked into the test by any chance. I.e., do you see an easy way to modify that test and keep the behaviour so that it is not able to cost the loop and keep this behaviour?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

do you see an easy way to modify that test and keep the behaviour so that it is not able to cost the loop and keep this behaviour?

No. It seems like it's worth trying. I'll give it a shot. Thanks.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated the test (added one more test). Does it make sense?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! I think it does.

<< "GEP:" << *getLoadStorePointerOperand(&StoreOrLoadInst)
<< "\n";
});
// Drop the last element of Sizes which is the same as ElementSize.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: I think this is self-evident from the assert and line 369, but maybe the more interesting question is why we drop that element, so maybe you can leave a little comment about that.

});
// Drop the last element of Sizes which is the same as ElementSize.
assert(!Sizes.empty() && Sizes.back() == ElementSize &&
"Expecting the last one to be the element size");
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was going leave a nit if we can make the message a little bit more descriptive, but now looking at this, my first question is why we need to pass ElementSize if it is last element in the Sizes list?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we have the following LLVM,

...
%gep = getelementptr i8, ptr %p, i64 %offset
store i32 0, %gep

to delinearize %gep as an i32 array, %offset must be a multiple of 4. We need to tell this information to delinearization function, and it's now passed as ElementSize. For historical reasons, delinearizer appends it to the end of Sizes.

@kasuga-fj kasuga-fj force-pushed the loopcacheanalysis-replace-delin branch from 41a1523 to 3cf3107 Compare November 19, 2025 12:52
Copy link
Collaborator

@sjoerdmeijer sjoerdmeijer left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, thanks, LGTM.

Maybe give @Meinersbur one more chance to look at this before merging it.

@github-actions
Copy link

🐧 Linux x64 Test Results

  • 186380 tests passed
  • 4859 tests skipped

@kasuga-fj
Copy link
Contributor Author

kasuga-fj commented Nov 21, 2025

I'll wait a few days, and if there are no objections, I'll go ahead and merge.

Copy link
Member

@Meinersbur Meinersbur left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

I had a first try removing getIndexExpressionsFromGEP from Polly, only updating tests so far.

@kasuga-fj
Copy link
Contributor Author

Thanks. I'll go ahead and remove tryDelinearizeFixedSizeImpl later.

@kasuga-fj kasuga-fj enabled auto-merge (squash) November 21, 2025 13:31
@kasuga-fj kasuga-fj merged commit 31a552d into llvm:main Nov 21, 2025
9 of 10 checks passed
@kasuga-fj kasuga-fj deleted the loopcacheanalysis-replace-delin branch November 21, 2025 14:06
@mikaelholmen
Copy link
Collaborator

Hello @kasuga-fj

The following starts crashing with this patch:
opt -passes="loop-interchange" bbi-113032.ll -o /dev/null
It crashes like

opt: ../lib/Analysis/LoopCacheAnalysis.cpp:372: bool llvm::IndexedReference::tryDelinearizeFixedSize(const SCEV *, SmallVectorImpl<const SCEV *> &, const SCEV *): Assertion `!Sizes.empty() && Subscripts.size() == Sizes.size() && Sizes.back() == ElementSize && "Unexpected delinearization result"' failed.
PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace and instructions to reproduce the bug.
Stack dump:
0.	Program arguments: build-all/bin/opt -passes=loop-interchange bbi-113032.ll -o /dev/null
1.	Running pass "function(loop(loop-interchange))" on module "bbi-113032.ll"
2.	Running pass "loop(loop-interchange)" on function "test_a2_cm_i16_1"
 #0 0x000055b598230f96 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) (build-all/bin/opt+0x4f43f96)
 #1 0x000055b59822e525 llvm::sys::RunSignalHandlers() (build-all/bin/opt+0x4f41525)
 #2 0x000055b598232119 SignalHandler(int, siginfo_t*, void*) Signals.cpp:0:0
 #3 0x00007f436760c990 __restore_rt (/lib64/libpthread.so.0+0x12990)
 #4 0x00007f4364fac52f raise (/lib64/libc.so.6+0x4e52f)
 #5 0x00007f4364f7fe65 abort (/lib64/libc.so.6+0x21e65)
 #6 0x00007f4364f7fd39 _nl_load_domain.cold.0 (/lib64/libc.so.6+0x21d39)
 #7 0x00007f4364fa4e86 (/lib64/libc.so.6+0x46e86)
 #8 0x000055b599e7dfae llvm::IndexedReference::delinearize(llvm::LoopInfo const&) (build-all/bin/opt+0x6b90fae)
 #9 0x000055b599e7d0c4 llvm::IndexedReference::IndexedReference(llvm::Instruction&, llvm::LoopInfo const&, llvm::ScalarEvolution&) (build-all/bin/opt+0x6b900c4)
#10 0x000055b599e80fef llvm::CacheCost::populateReferenceGroups(llvm::SmallVector<llvm::SmallVector<std::unique_ptr<llvm::IndexedReference, std::default_delete<llvm::IndexedReference>>, 8u>, 8u>&) const (build-all/bin/opt+0x6b93fef)
#11 0x000055b599e80773 llvm::CacheCost::calculateCacheFootprint() (build-all/bin/opt+0x6b93773)
#12 0x000055b599e80c94 llvm::CacheCost::getCacheCost(llvm::Loop&, llvm::LoopStandardAnalysisResults&, llvm::DependenceInfo&, std::optional<unsigned int>) (build-all/bin/opt+0x6b93c94)
#13 0x000055b599e7ac8b (anonymous namespace)::CacheCostManager::computeIfUnitinialized() LoopInterchange.cpp:0:0
#14 0x000055b599e7447e (anonymous namespace)::LoopInterchange::processLoop(llvm::SmallVectorImpl<llvm::Loop*>&, unsigned int, unsigned int, std::vector<std::vector<char, std::allocator<char>>, std::allocator<std::vector<char, std::allocator<char>>>>&, (anonymous namespace)::CacheCostManager&) LoopInterchange.cpp:0:0
#15 0x000055b599e705d9 llvm::LoopInterchangePass::run(llvm::LoopNest&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&) (build-all/bin/opt+0x6b835d9)
#16 0x000055b59974373d llvm::detail::PassModel<llvm::LoopNest, llvm::LoopInterchangePass, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>::run(llvm::LoopNest&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&) PassBuilderPipelines.cpp:0:0
#17 0x000055b5999f4e5d std::optional<llvm::PreservedAnalyses> llvm::PassManager<llvm::Loop, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>::runSinglePass<llvm::LoopNest, std::unique_ptr<llvm::detail::PassConcept<llvm::LoopNest, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>, std::default_delete<llvm::detail::PassConcept<llvm::LoopNest, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>>>>(llvm::LoopNest&, std::unique_ptr<llvm::detail::PassConcept<llvm::LoopNest, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>, std::default_delete<llvm::detail::PassConcept<llvm::LoopNest, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>>>&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&, llvm::PassInstrumentation&) (build-all/bin/opt+0x6707e5d)
#18 0x000055b5999f4155 llvm::PassManager<llvm::Loop, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>::runWithLoopNestPasses(llvm::Loop&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&) (build-all/bin/opt+0x6707155)
#19 0x000055b5999f3cee llvm::PassManager<llvm::Loop, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>::run(llvm::Loop&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&) (build-all/bin/opt+0x6706cee)
#20 0x000055b59973941d llvm::detail::PassModel<llvm::Loop, llvm::PassManager<llvm::Loop, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&>::run(llvm::Loop&, llvm::AnalysisManager<llvm::Loop, llvm::LoopStandardAnalysisResults&>&, llvm::LoopStandardAnalysisResults&, llvm::LPMUpdater&) PassBuilderPipelines.cpp:0:0
#21 0x000055b5999f5aa0 llvm::FunctionToLoopPassAdaptor::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) (build-all/bin/opt+0x6708aa0)
#22 0x000055b59973bf0d llvm::detail::PassModel<llvm::Function, llvm::FunctionToLoopPassAdaptor, llvm::AnalysisManager<llvm::Function>>::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) PassBuilderPipelines.cpp:0:0
#23 0x000055b598454425 llvm::PassManager<llvm::Function, llvm::AnalysisManager<llvm::Function>>::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) (build-all/bin/opt+0x5167425)
#24 0x000055b59973dbed llvm::detail::PassModel<llvm::Function, llvm::PassManager<llvm::Function, llvm::AnalysisManager<llvm::Function>>, llvm::AnalysisManager<llvm::Function>>::run(llvm::Function&, llvm::AnalysisManager<llvm::Function>&) PassBuilderPipelines.cpp:0:0
#25 0x000055b598458d3e llvm::ModuleToFunctionPassAdaptor::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) (build-all/bin/opt+0x516bd3e)
#26 0x000055b5996cca8d llvm::detail::PassModel<llvm::Module, llvm::ModuleToFunctionPassAdaptor, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) NewPMDriver.cpp:0:0
#27 0x000055b5984530e5 llvm::PassManager<llvm::Module, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) (build-all/bin/opt+0x51660e5)
#28 0x000055b5996c4fb4 llvm::runPassPipeline(llvm::StringRef, llvm::Module&, llvm::TargetMachine*, llvm::TargetLibraryInfoImpl*, llvm::RTLIB::RuntimeLibcallsInfo&, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::StringRef, llvm::ArrayRef<llvm::PassPlugin>, llvm::ArrayRef<std::function<void (llvm::PassBuilder&)>>, llvm::opt_tool::OutputKind, llvm::opt_tool::VerifierKind, bool, bool, bool, bool, bool, bool, bool, bool) (build-all/bin/opt+0x63d7fb4)
#29 0x000055b5981d2593 optMain (build-all/bin/opt+0x4ee5593)
#30 0x00007f4364f987e5 __libc_start_main (/lib64/libc.so.6+0x3a7e5)
#31 0x000055b5981cff2e _start (build-all/bin/opt+0x4ee2f2e)
Abort (core dumped)

bbi-113032.ll.gz

https://godbolt.org/z/fWaqYYqej

@kasuga-fj
Copy link
Contributor Author

@mikaelholmen Thanks for the reproducer, I'll take a look.

kasuga-fj added a commit to kasuga-fj/llvm-project that referenced this pull request Nov 25, 2025
aadeshps-mcw pushed a commit to aadeshps-mcw/llvm-project that referenced this pull request Nov 26, 2025
…m#164798)

This patch replaces the delinearization function used in
LoopCacheAnalysis, switching from one that depends on type information
in GEPs to one that does not. Once this patch and
llvm#161822 are landed, we can
delete `tryDelinearizeFixedSize` from Delienarization, which is an
optimization heuristic guided by GEP type information. After Polly
eliminates its use of `getIndexExpressionsFromGEP`, we will be able to
completely delete GEP-driven heuristics from Delinearization.
kasuga-fj added a commit that referenced this pull request Nov 26, 2025
Fix the assertion failure after #164798. The issue is that the
comparison `Sizes.back() == ElementSize` can fail when their types are
different. We should cast them to the wider type before the comparison.
Priyanshu3820 pushed a commit to Priyanshu3820/llvm-project that referenced this pull request Nov 26, 2025
…m#164798)

This patch replaces the delinearization function used in
LoopCacheAnalysis, switching from one that depends on type information
in GEPs to one that does not. Once this patch and
llvm#161822 are landed, we can
delete `tryDelinearizeFixedSize` from Delienarization, which is an
optimization heuristic guided by GEP type information. After Polly
eliminates its use of `getIndexExpressionsFromGEP`, we will be able to
completely delete GEP-driven heuristics from Delinearization.
kasuga-fj added a commit that referenced this pull request Nov 26, 2025
`tryDelinearizeFixedSizeImpl` is a heuristic function relying on GEP's
type information. Using these information to drive an optimization
heuristic is not allowed, so this function should be removed. As #161822
and #164798 have eliminated all calls to this, this patch removes the
function itself.
tanji-dg pushed a commit to tanji-dg/llvm-project that referenced this pull request Nov 27, 2025
Fix the assertion failure after llvm#164798. The issue is that the
comparison `Sizes.back() == ElementSize` can fail when their types are
different. We should cast them to the wider type before the comparison.
tanji-dg pushed a commit to tanji-dg/llvm-project that referenced this pull request Nov 27, 2025
`tryDelinearizeFixedSizeImpl` is a heuristic function relying on GEP's
type information. Using these information to drive an optimization
heuristic is not allowed, so this function should be removed. As llvm#161822
and llvm#164798 have eliminated all calls to this, this patch removes the
function itself.
GeneraluseAI pushed a commit to GeneraluseAI/llvm-project that referenced this pull request Nov 27, 2025
Fix the assertion failure after llvm#164798. The issue is that the
comparison `Sizes.back() == ElementSize` can fail when their types are
different. We should cast them to the wider type before the comparison.
GeneraluseAI pushed a commit to GeneraluseAI/llvm-project that referenced this pull request Nov 27, 2025
`tryDelinearizeFixedSizeImpl` is a heuristic function relying on GEP's
type information. Using these information to drive an optimization
heuristic is not allowed, so this function should be removed. As llvm#161822
and llvm#164798 have eliminated all calls to this, this patch removes the
function itself.
augusto2112 pushed a commit to augusto2112/llvm-project that referenced this pull request Dec 3, 2025
…m#164798)

This patch replaces the delinearization function used in
LoopCacheAnalysis, switching from one that depends on type information
in GEPs to one that does not. Once this patch and
llvm#161822 are landed, we can
delete `tryDelinearizeFixedSize` from Delienarization, which is an
optimization heuristic guided by GEP type information. After Polly
eliminates its use of `getIndexExpressionsFromGEP`, we will be able to
completely delete GEP-driven heuristics from Delinearization.
augusto2112 pushed a commit to augusto2112/llvm-project that referenced this pull request Dec 3, 2025
Fix the assertion failure after llvm#164798. The issue is that the
comparison `Sizes.back() == ElementSize` can fail when their types are
different. We should cast them to the wider type before the comparison.
augusto2112 pushed a commit to augusto2112/llvm-project that referenced this pull request Dec 3, 2025
`tryDelinearizeFixedSizeImpl` is a heuristic function relying on GEP's
type information. Using these information to drive an optimization
heuristic is not allowed, so this function should be removed. As llvm#161822
and llvm#164798 have eliminated all calls to this, this patch removes the
function itself.
kcloudy0717 pushed a commit to kcloudy0717/llvm-project that referenced this pull request Dec 4, 2025
Fix the assertion failure after llvm#164798. The issue is that the
comparison `Sizes.back() == ElementSize` can fail when their types are
different. We should cast them to the wider type before the comparison.
kcloudy0717 pushed a commit to kcloudy0717/llvm-project that referenced this pull request Dec 4, 2025
`tryDelinearizeFixedSizeImpl` is a heuristic function relying on GEP's
type information. Using these information to drive an optimization
heuristic is not allowed, so this function should be removed. As llvm#161822
and llvm#164798 have eliminated all calls to this, this patch removes the
function itself.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

llvm:analysis Includes value tracking, cost tables and constant folding llvm:transforms

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants