[llvm-branch-commits] [llvm] 86d6f7e - Precommit tests requested for D93725
Philip Reames via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Sun Jan 10 12:34:36 PST 2021
Author: Philip Reames
Date: 2021-01-10T12:29:34-08:00
New Revision: 86d6f7e90a1deab93e357b8f356e29d4a24fa3ac
URL: https://github.com/llvm/llvm-project/commit/86d6f7e90a1deab93e357b8f356e29d4a24fa3ac
DIFF: https://github.com/llvm/llvm-project/commit/86d6f7e90a1deab93e357b8f356e29d4a24fa3ac.diff
LOG: Precommit tests requested for D93725
Added:
Modified:
llvm/test/Transforms/LoopVectorize/first-order-recurrence-complex.ll
llvm/test/Transforms/LoopVectorize/loop-form.ll
Removed:
################################################################################
diff --git a/llvm/test/Transforms/LoopVectorize/first-order-recurrence-complex.ll b/llvm/test/Transforms/LoopVectorize/first-order-recurrence-complex.ll
index 208e1a219be8..ef3d3e659e5a 100644
--- a/llvm/test/Transforms/LoopVectorize/first-order-recurrence-complex.ll
+++ b/llvm/test/Transforms/LoopVectorize/first-order-recurrence-complex.ll
@@ -432,3 +432,94 @@ loop.latch: ; preds = %if.then122, %for.b
exit:
ret void
}
+
+; A recurrence in a multiple exit loop.
+define i16 @multiple_exit(i16* %p, i32 %n) {
+; CHECK-LABEL: @multiple_exit(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: br label [[FOR_COND:%.*]]
+; CHECK: for.cond:
+; CHECK-NEXT: [[I:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[INC:%.*]], [[FOR_BODY:%.*]] ]
+; CHECK-NEXT: [[REC:%.*]] = phi i16 [ 0, [[ENTRY]] ], [ [[REC_NEXT:%.*]], [[FOR_BODY]] ]
+; CHECK-NEXT: [[IPROM:%.*]] = sext i32 [[I]] to i64
+; CHECK-NEXT: [[B:%.*]] = getelementptr inbounds i16, i16* [[P:%.*]], i64 [[IPROM]]
+; CHECK-NEXT: [[REC_NEXT]] = load i16, i16* [[B]], align 2
+; CHECK-NEXT: [[CMP:%.*]] = icmp slt i32 [[I]], [[N:%.*]]
+; CHECK-NEXT: br i1 [[CMP]], label [[FOR_BODY]], label [[IF_END:%.*]]
+; CHECK: for.body:
+; CHECK-NEXT: store i16 [[REC]], i16* [[B]], align 4
+; CHECK-NEXT: [[INC]] = add nsw i32 [[I]], 1
+; CHECK-NEXT: [[CMP2:%.*]] = icmp slt i32 [[I]], 2096
+; CHECK-NEXT: br i1 [[CMP2]], label [[FOR_COND]], label [[IF_END]]
+; CHECK: if.end:
+; CHECK-NEXT: [[REC_LCSSA:%.*]] = phi i16 [ [[REC]], [[FOR_BODY]] ], [ [[REC]], [[FOR_COND]] ]
+; CHECK-NEXT: ret i16 [[REC_LCSSA]]
+;
+entry:
+ br label %for.cond
+
+for.cond:
+ %i = phi i32 [ 0, %entry ], [ %inc, %for.body ]
+ %rec = phi i16 [0, %entry], [ %rec.next, %for.body ]
+ %iprom = sext i32 %i to i64
+ %b = getelementptr inbounds i16, i16* %p, i64 %iprom
+ %rec.next = load i16, i16* %b
+ %cmp = icmp slt i32 %i, %n
+ br i1 %cmp, label %for.body, label %if.end
+
+for.body:
+ store i16 %rec , i16* %b, align 4
+ %inc = add nsw i32 %i, 1
+ %cmp2 = icmp slt i32 %i, 2096
+ br i1 %cmp2, label %for.cond, label %if.end
+
+if.end:
+ ret i16 %rec
+}
+
+
+; A multiple exit case where one of the exiting edges involves a value
+; from the recurrence and one does not.
+define i16 @multiple_exit2(i16* %p, i32 %n) {
+; CHECK-LABEL: @multiple_exit2(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: br label [[FOR_COND:%.*]]
+; CHECK: for.cond:
+; CHECK-NEXT: [[I:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[INC:%.*]], [[FOR_BODY:%.*]] ]
+; CHECK-NEXT: [[REC:%.*]] = phi i16 [ 0, [[ENTRY]] ], [ [[REC_NEXT:%.*]], [[FOR_BODY]] ]
+; CHECK-NEXT: [[IPROM:%.*]] = sext i32 [[I]] to i64
+; CHECK-NEXT: [[B:%.*]] = getelementptr inbounds i16, i16* [[P:%.*]], i64 [[IPROM]]
+; CHECK-NEXT: [[REC_NEXT]] = load i16, i16* [[B]], align 2
+; CHECK-NEXT: [[CMP:%.*]] = icmp slt i32 [[I]], [[N:%.*]]
+; CHECK-NEXT: br i1 [[CMP]], label [[FOR_BODY]], label [[IF_END:%.*]]
+; CHECK: for.body:
+; CHECK-NEXT: store i16 [[REC]], i16* [[B]], align 4
+; CHECK-NEXT: [[INC]] = add nsw i32 [[I]], 1
+; CHECK-NEXT: [[CMP2:%.*]] = icmp slt i32 [[I]], 2096
+; CHECK-NEXT: br i1 [[CMP2]], label [[FOR_COND]], label [[IF_END]]
+; CHECK: if.end:
+; CHECK-NEXT: [[REC_LCSSA:%.*]] = phi i16 [ [[REC]], [[FOR_COND]] ], [ 10, [[FOR_BODY]] ]
+; CHECK-NEXT: ret i16 [[REC_LCSSA]]
+;
+entry:
+ br label %for.cond
+
+for.cond:
+ %i = phi i32 [ 0, %entry ], [ %inc, %for.body ]
+ %rec = phi i16 [0, %entry], [ %rec.next, %for.body ]
+ %iprom = sext i32 %i to i64
+ %b = getelementptr inbounds i16, i16* %p, i64 %iprom
+ %rec.next = load i16, i16* %b
+ %cmp = icmp slt i32 %i, %n
+ br i1 %cmp, label %for.body, label %if.end
+
+for.body:
+ store i16 %rec , i16* %b, align 4
+ %inc = add nsw i32 %i, 1
+ %cmp2 = icmp slt i32 %i, 2096
+ br i1 %cmp2, label %for.cond, label %if.end
+
+if.end:
+ %rec.lcssa = phi i16 [ %rec, %for.cond ], [ 10, %for.body ]
+ ret i16 %rec.lcssa
+}
diff --git a/llvm/test/Transforms/LoopVectorize/loop-form.ll b/llvm/test/Transforms/LoopVectorize/loop-form.ll
index f93c038de6bb..bf94505aec2c 100644
--- a/llvm/test/Transforms/LoopVectorize/loop-form.ll
+++ b/llvm/test/Transforms/LoopVectorize/loop-form.ll
@@ -869,3 +869,126 @@ loop.latch:
exit:
ret void
}
+
+define i32 @reduction(i32* %addr) {
+; CHECK-LABEL: @reduction(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: br label [[LOOP_HEADER:%.*]]
+; CHECK: loop.header:
+; CHECK-NEXT: [[IV:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ]
+; CHECK-NEXT: [[ACCUM:%.*]] = phi i32 [ 0, [[ENTRY]] ], [ [[ACCUM_NEXT:%.*]], [[LOOP_LATCH]] ]
+; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[ADDR:%.*]], i64 [[IV]]
+; CHECK-NEXT: [[EXITCOND_NOT:%.*]] = icmp eq i64 [[IV]], 200
+; CHECK-NEXT: br i1 [[EXITCOND_NOT]], label [[EXIT:%.*]], label [[LOOP_LATCH]]
+; CHECK: loop.latch:
+; CHECK-NEXT: [[TMP0:%.*]] = load i32, i32* [[GEP]], align 4
+; CHECK-NEXT: [[ACCUM_NEXT]] = add i32 [[ACCUM]], [[TMP0]]
+; CHECK-NEXT: [[IV_NEXT]] = add nuw nsw i64 [[IV]], 1
+; CHECK-NEXT: [[EXITCOND2_NOT:%.*]] = icmp eq i64 [[IV]], 400
+; CHECK-NEXT: br i1 [[EXITCOND2_NOT]], label [[EXIT]], label [[LOOP_HEADER]]
+; CHECK: exit:
+; CHECK-NEXT: [[LCSSA:%.*]] = phi i32 [ 0, [[LOOP_HEADER]] ], [ [[ACCUM_NEXT]], [[LOOP_LATCH]] ]
+; CHECK-NEXT: ret i32 [[LCSSA]]
+;
+; TAILFOLD-LABEL: @reduction(
+; TAILFOLD-NEXT: entry:
+; TAILFOLD-NEXT: br label [[LOOP_HEADER:%.*]]
+; TAILFOLD: loop.header:
+; TAILFOLD-NEXT: [[IV:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ]
+; TAILFOLD-NEXT: [[ACCUM:%.*]] = phi i32 [ 0, [[ENTRY]] ], [ [[ACCUM_NEXT:%.*]], [[LOOP_LATCH]] ]
+; TAILFOLD-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[ADDR:%.*]], i64 [[IV]]
+; TAILFOLD-NEXT: [[EXITCOND_NOT:%.*]] = icmp eq i64 [[IV]], 200
+; TAILFOLD-NEXT: br i1 [[EXITCOND_NOT]], label [[EXIT:%.*]], label [[LOOP_LATCH]]
+; TAILFOLD: loop.latch:
+; TAILFOLD-NEXT: [[TMP0:%.*]] = load i32, i32* [[GEP]], align 4
+; TAILFOLD-NEXT: [[ACCUM_NEXT]] = add i32 [[ACCUM]], [[TMP0]]
+; TAILFOLD-NEXT: [[IV_NEXT]] = add nuw nsw i64 [[IV]], 1
+; TAILFOLD-NEXT: [[EXITCOND2_NOT:%.*]] = icmp eq i64 [[IV]], 400
+; TAILFOLD-NEXT: br i1 [[EXITCOND2_NOT]], label [[EXIT]], label [[LOOP_HEADER]]
+; TAILFOLD: exit:
+; TAILFOLD-NEXT: [[LCSSA:%.*]] = phi i32 [ 0, [[LOOP_HEADER]] ], [ [[ACCUM_NEXT]], [[LOOP_LATCH]] ]
+; TAILFOLD-NEXT: ret i32 [[LCSSA]]
+;
+entry:
+ br label %loop.header
+
+loop.header:
+ %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop.latch ]
+ %accum = phi i32 [0, %entry], [%accum.next, %loop.latch]
+ %gep = getelementptr i32, i32* %addr, i64 %iv
+ %exitcond.not = icmp eq i64 %iv, 200
+ br i1 %exitcond.not, label %exit, label %loop.latch
+
+loop.latch:
+ %0 = load i32, i32* %gep, align 4
+ %accum.next = add i32 %accum, %0
+ %iv.next = add nuw nsw i64 %iv, 1
+ %exitcond2.not = icmp eq i64 %iv, 400
+ br i1 %exitcond2.not, label %exit, label %loop.header
+
+exit:
+ %lcssa = phi i32 [0, %loop.header], [%accum.next, %loop.latch]
+ ret i32 %lcssa
+}
+
+; TODO: The current definition of reduction is too strict, we can vectorize
+; this. There's an analogous single exit case where we extract the N-1
+; value of the reduction that we can also handle. If we fix the later, the
+; multiple exit case probably falls out.
+define i32 @reduction2(i32* %addr) {
+; CHECK-LABEL: @reduction2(
+; CHECK-NEXT: entry:
+; CHECK-NEXT: br label [[LOOP_HEADER:%.*]]
+; CHECK: loop.header:
+; CHECK-NEXT: [[IV:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ]
+; CHECK-NEXT: [[ACCUM:%.*]] = phi i32 [ 0, [[ENTRY]] ], [ [[ACCUM_NEXT:%.*]], [[LOOP_LATCH]] ]
+; CHECK-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[ADDR:%.*]], i64 [[IV]]
+; CHECK-NEXT: [[EXITCOND_NOT:%.*]] = icmp eq i64 [[IV]], 200
+; CHECK-NEXT: br i1 [[EXITCOND_NOT]], label [[EXIT:%.*]], label [[LOOP_LATCH]]
+; CHECK: loop.latch:
+; CHECK-NEXT: [[TMP0:%.*]] = load i32, i32* [[GEP]], align 4
+; CHECK-NEXT: [[ACCUM_NEXT]] = add i32 [[ACCUM]], [[TMP0]]
+; CHECK-NEXT: [[IV_NEXT]] = add nuw nsw i64 [[IV]], 1
+; CHECK-NEXT: br label [[LOOP_HEADER]]
+; CHECK: exit:
+; CHECK-NEXT: [[ACCUM_LCSSA:%.*]] = phi i32 [ [[ACCUM]], [[LOOP_HEADER]] ]
+; CHECK-NEXT: ret i32 [[ACCUM_LCSSA]]
+;
+; TAILFOLD-LABEL: @reduction2(
+; TAILFOLD-NEXT: entry:
+; TAILFOLD-NEXT: br label [[LOOP_HEADER:%.*]]
+; TAILFOLD: loop.header:
+; TAILFOLD-NEXT: [[IV:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ]
+; TAILFOLD-NEXT: [[ACCUM:%.*]] = phi i32 [ 0, [[ENTRY]] ], [ [[ACCUM_NEXT:%.*]], [[LOOP_LATCH]] ]
+; TAILFOLD-NEXT: [[GEP:%.*]] = getelementptr i32, i32* [[ADDR:%.*]], i64 [[IV]]
+; TAILFOLD-NEXT: [[EXITCOND_NOT:%.*]] = icmp eq i64 [[IV]], 200
+; TAILFOLD-NEXT: br i1 [[EXITCOND_NOT]], label [[EXIT:%.*]], label [[LOOP_LATCH]]
+; TAILFOLD: loop.latch:
+; TAILFOLD-NEXT: [[TMP0:%.*]] = load i32, i32* [[GEP]], align 4
+; TAILFOLD-NEXT: [[ACCUM_NEXT]] = add i32 [[ACCUM]], [[TMP0]]
+; TAILFOLD-NEXT: [[IV_NEXT]] = add nuw nsw i64 [[IV]], 1
+; TAILFOLD-NEXT: br label [[LOOP_HEADER]]
+; TAILFOLD: exit:
+; TAILFOLD-NEXT: [[ACCUM_LCSSA:%.*]] = phi i32 [ [[ACCUM]], [[LOOP_HEADER]] ]
+; TAILFOLD-NEXT: ret i32 [[ACCUM_LCSSA]]
+;
+entry:
+ br label %loop.header
+
+loop.header:
+ %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop.latch ]
+ %accum = phi i32 [0, %entry], [%accum.next, %loop.latch]
+ %gep = getelementptr i32, i32* %addr, i64 %iv
+ %exitcond.not = icmp eq i64 %iv, 200
+ br i1 %exitcond.not, label %exit, label %loop.latch
+
+loop.latch:
+ %0 = load i32, i32* %gep, align 4
+ %accum.next = add i32 %accum, %0
+ %iv.next = add nuw nsw i64 %iv, 1
+ br label %loop.header
+
+exit:
+ ret i32 %accum
+}
+
More information about the llvm-branch-commits
mailing list