Skip to content

Commit 5ae5069

Browse files
authored
LAA: strip unnecessary getUniqueCastUse (#92119)
733b8b2 ([LAA] Simplify identification of speculatable strides [nfc]) refactored getStrideFromPointer() to compute directly on SCEVs, and return an SCEV expression instead of a Value. However, it left behind a call to getUniqueCastUse(), which is completely unnecessary. Remove this, showing a positive test update, and simplify the surrounding program logic.
1 parent 687d6fb commit 5ae5069

File tree

2 files changed

+17
-32
lines changed

2 files changed

+17
-32
lines changed

llvm/lib/Analysis/LoopAccessAnalysis.cpp

Lines changed: 6 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -2848,21 +2848,6 @@ static Value *stripGetElementPtr(Value *Ptr, ScalarEvolution *SE, Loop *Lp) {
28482848
return GEP->getOperand(InductionOperand);
28492849
}
28502850

2851-
/// If a value has only one user that is a CastInst, return it.
2852-
static Value *getUniqueCastUse(Value *Ptr, Loop *Lp, Type *Ty) {
2853-
Value *UniqueCast = nullptr;
2854-
for (User *U : Ptr->users()) {
2855-
CastInst *CI = dyn_cast<CastInst>(U);
2856-
if (CI && CI->getType() == Ty) {
2857-
if (!UniqueCast)
2858-
UniqueCast = CI;
2859-
else
2860-
return nullptr;
2861-
}
2862-
}
2863-
return UniqueCast;
2864-
}
2865-
28662851
/// Get the stride of a pointer access in a loop. Looks for symbolic
28672852
/// strides "a[i*stride]". Returns the symbolic stride, or null otherwise.
28682853
static const SCEV *getStrideFromPointer(Value *Ptr, ScalarEvolution *SE, Loop *Lp) {
@@ -2925,21 +2910,14 @@ static const SCEV *getStrideFromPointer(Value *Ptr, ScalarEvolution *SE, Loop *L
29252910
return nullptr;
29262911

29272912
// Look for the loop invariant symbolic value.
2928-
const SCEVUnknown *U = dyn_cast<SCEVUnknown>(V);
2929-
if (!U) {
2930-
const auto *C = dyn_cast<SCEVIntegralCastExpr>(V);
2931-
if (!C)
2932-
return nullptr;
2933-
U = dyn_cast<SCEVUnknown>(C->getOperand());
2934-
if (!U)
2935-
return nullptr;
2913+
if (isa<SCEVUnknown>(V))
2914+
return V;
29362915

2937-
// Match legacy behavior - this is not needed for correctness
2938-
if (!getUniqueCastUse(U->getValue(), Lp, V->getType()))
2939-
return nullptr;
2940-
}
2916+
if (const auto *C = dyn_cast<SCEVIntegralCastExpr>(V))
2917+
if (isa<SCEVUnknown>(C->getOperand()))
2918+
return V;
29412919

2942-
return V;
2920+
return nullptr;
29432921
}
29442922

29452923
void LoopAccessInfo::collectStridedAccess(Value *MemAccess) {

llvm/test/Analysis/LoopAccessAnalysis/symbolic-stride.ll

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -170,16 +170,23 @@ define void @single_stride_castexpr_multiuse(i32 %offset, ptr %src, ptr %dst, i1
170170
; CHECK-NEXT: %gep.src = getelementptr inbounds i32, ptr %src, i64 %iv.3
171171
; CHECK-NEXT: Grouped accesses:
172172
; CHECK-NEXT: Group [[GRP3]]:
173-
; CHECK-NEXT: (Low: (((4 * %iv.1) + %dst) umin ((4 * %iv.1) + (4 * (sext i32 %offset to i64) * (200 + (-1 * (zext i32 %offset to i64))<nsw>)<nsw>) + %dst)) High: (4 + (((4 * %iv.1) + %dst) umax ((4 * %iv.1) + (4 * (sext i32 %offset to i64) * (200 + (-1 * (zext i32 %offset to i64))<nsw>)<nsw>) + %dst))))
174-
; CHECK-NEXT: Member: {((4 * %iv.1) + %dst),+,(4 * (sext i32 %offset to i64))<nsw>}<%inner.loop>
173+
; CHECK-NEXT: (Low: ((4 * %iv.1) + %dst) High: (804 + (4 * %iv.1) + (-4 * (zext i32 %offset to i64))<nsw> + %dst))
174+
; CHECK-NEXT: Member: {((4 * %iv.1) + %dst),+,4}<%inner.loop>
175175
; CHECK-NEXT: Group [[GRP4]]:
176-
; CHECK-NEXT: (Low: ((4 * (zext i32 %offset to i64))<nuw><nsw> + %src) High: (804 + %src))
177-
; CHECK-NEXT: Member: {((4 * (zext i32 %offset to i64))<nuw><nsw> + %src),+,4}<%inner.loop>
176+
; CHECK-NEXT: (Low: (4 + %src) High: (808 + (-4 * (zext i32 %offset to i64))<nsw> + %src))
177+
; CHECK-NEXT: Member: {(4 + %src),+,4}<%inner.loop>
178178
; CHECK-EMPTY:
179179
; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop.
180180
; CHECK-NEXT: SCEV assumptions:
181+
; CHECK-NEXT: Equal predicate: %offset == 1
181182
; CHECK-EMPTY:
182183
; CHECK-NEXT: Expressions re-written:
184+
; CHECK-NEXT: [PSE] %gep.src = getelementptr inbounds i32, ptr %src, i64 %iv.3:
185+
; CHECK-NEXT: {((4 * (zext i32 %offset to i64))<nuw><nsw> + %src),+,4}<%inner.loop>
186+
; CHECK-NEXT: --> {(4 + %src),+,4}<%inner.loop>
187+
; CHECK-NEXT: [PSE] %gep.dst = getelementptr i32, ptr %dst, i64 %iv.2:
188+
; CHECK-NEXT: {((4 * %iv.1) + %dst),+,(4 * (sext i32 %offset to i64))<nsw>}<%inner.loop>
189+
; CHECK-NEXT: --> {((4 * %iv.1) + %dst),+,4}<%inner.loop>
183190
; CHECK-NEXT: outer.header:
184191
; CHECK-NEXT: Report: loop is not the innermost loop
185192
; CHECK-NEXT: Dependences:

0 commit comments

Comments
 (0)