Skip to content

Commit 8e9e22f

Browse files
committed
[LoopFlatten] Fix IV increment use count
The add from the IV in the inner loop was always checking for 2 uses, the phi and the compare. The compare could be based on the phi though, leaving one valid use of the compare. In the testcase we could be left with the phi and a lcssa phi as the two users, invalidly allowing flattening where we shouldn't. Fixes 58441 Differential Revision: https://reviews.llvm.org/D138404
1 parent 2d4b998 commit 8e9e22f

File tree

2 files changed

+14
-19
lines changed

2 files changed

+14
-19
lines changed

llvm/lib/Transforms/Scalar/LoopFlatten.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -413,7 +413,8 @@ static bool findLoopComponents(
413413
// increment variable.
414414
Increment =
415415
cast<BinaryOperator>(InductionPHI->getIncomingValueForBlock(Latch));
416-
if (Increment->hasNUsesOrMore(3)) {
416+
if ((Compare->getOperand(0) != Increment || !Increment->hasNUses(2)) &&
417+
!Increment->hasNUses(1)) {
417418
LLVM_DEBUG(dbgs() << "Could not find valid increment\n");
418419
return false;
419420
}

llvm/test/Transforms/LoopFlatten/widen-pr58441.ll

Lines changed: 12 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -8,27 +8,22 @@ target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16
88
define i32 @test() {
99
; CHECK-LABEL: @test(
1010
; CHECK-NEXT: entry:
11-
; CHECK-NEXT: [[FLATTEN_TRIPCOUNT:%.*]] = mul i64 6, 6
1211
; CHECK-NEXT: br label [[FOR_COND1_PREHEADER_I:%.*]]
1312
; CHECK: for.cond1.preheader.i:
14-
; CHECK-NEXT: [[INDVAR1:%.*]] = phi i64 [ [[INDVAR_NEXT2:%.*]], [[FOR_INC5_I:%.*]] ], [ 0, [[ENTRY:%.*]] ]
13+
; CHECK-NEXT: [[L_011_I:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD6_I:%.*]], [[FOR_INC5_I:%.*]] ]
1514
; CHECK-NEXT: br label [[WHILE_COND_I_PREHEADER_I:%.*]]
1615
; CHECK: while.cond.i.preheader.i:
17-
; CHECK-NEXT: [[INDVAR:%.*]] = phi i64 [ 0, [[FOR_COND1_PREHEADER_I]] ]
18-
; CHECK-NEXT: [[STOREMERGE9_I:%.*]] = phi i32 [ 0, [[FOR_COND1_PREHEADER_I]] ]
19-
; CHECK-NEXT: [[INDVAR_NEXT:%.*]] = add i64 [[INDVAR]], 1
20-
; CHECK-NEXT: [[ADD_I:%.*]] = add nuw nsw i32 [[STOREMERGE9_I]], 1
21-
; CHECK-NEXT: [[CMP2_I:%.*]] = icmp ult i64 [[INDVAR]], 5
22-
; CHECK-NEXT: br label [[FOR_INC5_I]]
16+
; CHECK-NEXT: [[STOREMERGE9_I:%.*]] = phi i32 [ 0, [[FOR_COND1_PREHEADER_I]] ], [ [[ADD_I:%.*]], [[WHILE_COND_I_PREHEADER_I]] ]
17+
; CHECK-NEXT: [[ADD_I]] = add nuw nsw i32 [[STOREMERGE9_I]], 1
18+
; CHECK-NEXT: [[CMP2_I:%.*]] = icmp ult i32 [[STOREMERGE9_I]], 5
19+
; CHECK-NEXT: br i1 [[CMP2_I]], label [[WHILE_COND_I_PREHEADER_I]], label [[FOR_INC5_I]]
2320
; CHECK: for.inc5.i:
24-
; CHECK-NEXT: [[ADD_I_LCSSA_WIDE:%.*]] = phi i64 [ [[INDVAR_NEXT]], [[WHILE_COND_I_PREHEADER_I]] ]
2521
; CHECK-NEXT: [[ADD_I_LCSSA:%.*]] = phi i32 [ [[ADD_I]], [[WHILE_COND_I_PREHEADER_I]] ]
26-
; CHECK-NEXT: [[TMP0:%.*]] = trunc i64 [[ADD_I_LCSSA_WIDE]] to i32
27-
; CHECK-NEXT: [[INDVAR_NEXT2]] = add i64 [[INDVAR1]], 1
28-
; CHECK-NEXT: [[EXITCOND_NOT_I:%.*]] = icmp eq i64 [[INDVAR_NEXT2]], [[FLATTEN_TRIPCOUNT]]
22+
; CHECK-NEXT: [[ADD6_I]] = add nuw nsw i32 [[L_011_I]], 1
23+
; CHECK-NEXT: [[EXITCOND_NOT_I:%.*]] = icmp eq i32 [[ADD6_I]], 6
2924
; CHECK-NEXT: br i1 [[EXITCOND_NOT_I]], label [[E_EXIT:%.*]], label [[FOR_COND1_PREHEADER_I]]
3025
; CHECK: e.exit:
31-
; CHECK-NEXT: [[ADD_I_LCSSA_LCSSA:%.*]] = phi i32 [ [[TMP0]], [[FOR_INC5_I]] ]
26+
; CHECK-NEXT: [[ADD_I_LCSSA_LCSSA:%.*]] = phi i32 [ [[ADD_I_LCSSA]], [[FOR_INC5_I]] ]
3227
; CHECK-NEXT: ret i32 [[ADD_I_LCSSA_LCSSA]]
3328
;
3429
entry:
@@ -59,21 +54,20 @@ e.exit: ; preds = %for.inc5.i
5954
define i32 @test64() {
6055
; CHECK-LABEL: @test64(
6156
; CHECK-NEXT: entry:
62-
; CHECK-NEXT: [[FLATTEN_TRIPCOUNT:%.*]] = mul i64 6, 6
6357
; CHECK-NEXT: br label [[FOR_COND1_PREHEADER_I:%.*]]
6458
; CHECK: for.cond1.preheader.i:
6559
; CHECK-NEXT: [[L_011_I:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[ADD6_I:%.*]], [[FOR_INC5_I:%.*]] ]
6660
; CHECK-NEXT: br label [[WHILE_COND_I_PREHEADER_I:%.*]]
6761
; CHECK: while.cond.i.preheader.i:
68-
; CHECK-NEXT: [[STOREMERGE9_I:%.*]] = phi i64 [ 0, [[FOR_COND1_PREHEADER_I]] ]
69-
; CHECK-NEXT: [[ADD_I:%.*]] = add nuw nsw i64 [[STOREMERGE9_I]], 1
62+
; CHECK-NEXT: [[STOREMERGE9_I:%.*]] = phi i64 [ 0, [[FOR_COND1_PREHEADER_I]] ], [ [[ADD_I:%.*]], [[WHILE_COND_I_PREHEADER_I]] ]
63+
; CHECK-NEXT: [[ADD_I]] = add nuw nsw i64 [[STOREMERGE9_I]], 1
7064
; CHECK-NEXT: [[CMP2_I:%.*]] = icmp ult i64 [[STOREMERGE9_I]], 5
71-
; CHECK-NEXT: br label [[FOR_INC5_I]]
65+
; CHECK-NEXT: br i1 [[CMP2_I]], label [[WHILE_COND_I_PREHEADER_I]], label [[FOR_INC5_I]]
7266
; CHECK: for.inc5.i:
7367
; CHECK-NEXT: [[ADD_I_LCSSA_WIDEN:%.*]] = phi i64 [ [[ADD_I]], [[WHILE_COND_I_PREHEADER_I]] ]
7468
; CHECK-NEXT: [[ADD_I_LCSSA:%.*]] = trunc i64 [[ADD_I_LCSSA_WIDEN]] to i32
7569
; CHECK-NEXT: [[ADD6_I]] = add nuw nsw i64 [[L_011_I]], 1
76-
; CHECK-NEXT: [[EXITCOND_NOT_I:%.*]] = icmp eq i64 [[ADD6_I]], [[FLATTEN_TRIPCOUNT]]
70+
; CHECK-NEXT: [[EXITCOND_NOT_I:%.*]] = icmp eq i64 [[ADD6_I]], 6
7771
; CHECK-NEXT: br i1 [[EXITCOND_NOT_I]], label [[E_EXIT:%.*]], label [[FOR_COND1_PREHEADER_I]]
7872
; CHECK: e.exit:
7973
; CHECK-NEXT: [[ADD_I_LCSSA_LCSSA:%.*]] = phi i32 [ [[ADD_I_LCSSA]], [[FOR_INC5_I]] ]

0 commit comments

Comments
 (0)