Skip to content

Commit 7078993

Browse files
committed
[IndVars] Check expansion safety during LFTR
Check isSafeToExpand() before expanding the exit count. Otherwise we may incorrectly speculate a udiv. Fixes #66986.
1 parent 24161bc commit 7078993

File tree

2 files changed

+13
-22
lines changed

2 files changed

+13
-22
lines changed

llvm/lib/Transforms/Scalar/IndVarSimplify.cpp

Lines changed: 6 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1997,20 +1997,12 @@ bool IndVarSimplify::run(Loop *L) {
19971997
TTI, PreHeader->getTerminator()))
19981998
continue;
19991999

2000-
// Check preconditions for proper SCEVExpander operation. SCEV does not
2001-
// express SCEVExpander's dependencies, such as LoopSimplify. Instead
2002-
// any pass that uses the SCEVExpander must do it. This does not work
2003-
// well for loop passes because SCEVExpander makes assumptions about
2004-
// all loops, while LoopPassManager only forces the current loop to be
2005-
// simplified.
2006-
//
2007-
// FIXME: SCEV expansion has no way to bail out, so the caller must
2008-
// explicitly check any assumptions made by SCEV. Brittle.
2009-
const SCEVAddRecExpr *AR = dyn_cast<SCEVAddRecExpr>(ExitCount);
2010-
if (!AR || AR->getLoop()->getLoopPreheader())
2011-
Changed |= linearFunctionTestReplace(L, ExitingBB,
2012-
ExitCount, IndVar,
2013-
Rewriter);
2000+
if (!Rewriter.isSafeToExpand(ExitCount))
2001+
continue;
2002+
2003+
Changed |= linearFunctionTestReplace(L, ExitingBB,
2004+
ExitCount, IndVar,
2005+
Rewriter);
20142006
}
20152007
}
20162008
// Clear the rewriter cache, because values that are in the rewriter's cache

llvm/test/Transforms/IndVarSimplify/pr66986.ll

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -3,30 +3,29 @@
33

44
target datalayout = "n8:16:32:64"
55

6-
; FIXME: This is a miscompile.
76
; The udiv should not get hoisted into the preheader (past a conditional).
87
define i32 @test(i1 %c, i32 %arg1, i32 %arg2) {
98
; CHECK-LABEL: define i32 @test(
109
; CHECK-SAME: i1 [[C:%.*]], i32 [[ARG1:%.*]], i32 [[ARG2:%.*]]) {
1110
; CHECK-NEXT: entry:
12-
; CHECK-NEXT: [[TMP0:%.*]] = udiv i32 [[ARG1]], [[ARG2]]
1311
; CHECK-NEXT: br label [[LOOP:%.*]]
1412
; CHECK: loop:
15-
; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i32 [ [[INDVARS_IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ], [ [[TMP0]], [[ENTRY:%.*]] ]
13+
; CHECK-NEXT: [[PHI:%.*]] = phi i32 [ [[ADD9:%.*]], [[LOOP_LATCH:%.*]] ], [ 0, [[ENTRY:%.*]] ]
1614
; CHECK-NEXT: br i1 [[C]], label [[IF:%.*]], label [[LOOP_LATCH]]
1715
; CHECK: if:
16+
; CHECK-NEXT: [[UDIV:%.*]] = udiv i32 [[ARG1]], [[ARG2]]
17+
; CHECK-NEXT: [[ADD:%.*]] = add i32 [[UDIV]], [[PHI]]
18+
; CHECK-NEXT: [[ZEXT:%.*]] = zext i32 [[ADD]] to i64
1819
; CHECK-NEXT: br label [[LOOP2:%.*]]
1920
; CHECK: loop2:
2021
; CHECK-NEXT: [[PHI6:%.*]] = phi i64 [ [[ADD7:%.*]], [[LOOP2]] ], [ 0, [[IF]] ]
2122
; CHECK-NEXT: [[ADD7]] = add nuw nsw i64 [[PHI6]], 1
22-
; CHECK-NEXT: [[TMP1:%.*]] = zext i32 [[INDVARS_IV]] to i64
23-
; CHECK-NEXT: [[TMP2:%.*]] = add nuw nsw i64 [[TMP1]], 1
24-
; CHECK-NEXT: [[EXITCOND:%.*]] = icmp ne i64 [[ADD7]], [[TMP2]]
25-
; CHECK-NEXT: br i1 [[EXITCOND]], label [[LOOP2]], label [[LOOP_LATCH_LOOPEXIT:%.*]]
23+
; CHECK-NEXT: [[ICMP:%.*]] = icmp ult i64 [[PHI6]], [[ZEXT]]
24+
; CHECK-NEXT: br i1 [[ICMP]], label [[LOOP2]], label [[LOOP_LATCH_LOOPEXIT:%.*]]
2625
; CHECK: loop.latch.loopexit:
2726
; CHECK-NEXT: br label [[LOOP_LATCH]]
2827
; CHECK: loop.latch:
29-
; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add i32 [[INDVARS_IV]], 1
28+
; CHECK-NEXT: [[ADD9]] = add i32 [[PHI]], 1
3029
; CHECK-NEXT: br label [[LOOP]]
3130
;
3231
entry:

0 commit comments

Comments
 (0)