1+ ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 6
12; RUN: opt -S -passes=indvars < %s | FileCheck %s
23
34target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
45target triple = "x86_64-unknown-linux-gnu"
56
67define void @f_sadd (ptr %a ) {
7- ; CHECK-LABEL: @f_sadd(
8+ ; CHECK-LABEL: define void @f_sadd(
9+ ; CHECK-SAME: ptr [[A:%.*]]) {
10+ ; CHECK-NEXT: [[ENTRY:.*]]:
11+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
12+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
13+ ; CHECK-NEXT: ret void
14+ ; CHECK: [[FOR_BODY]]:
15+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 0, %[[ENTRY]] ]
16+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
17+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
18+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nuw nsw i64 [[INDVARS_IV]], 1
19+ ; CHECK-NEXT: br i1 false, label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0:![0-9]+]]
20+ ; CHECK: [[TRAP]]:
21+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
22+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
23+ ; CHECK: [[CONT]]:
24+ ; CHECK-NEXT: [[EXITCOND:%.*]] = icmp ne i64 [[INDVARS_IV_NEXT]], 16
25+ ; CHECK-NEXT: br i1 [[EXITCOND]], label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
26+ ;
827entry:
928 br label %for.body
1029
@@ -18,9 +37,6 @@ for.body: ; preds = %entry, %cont
1837 store i8 0 , ptr %arrayidx , align 1
1938 %0 = tail call { i32 , i1 } @llvm.sadd.with.overflow.i32 (i32 %i.04 , i32 1 )
2039 %1 = extractvalue { i32 , i1 } %0 , 1
21- ; CHECK: for.body:
22- ; CHECK-NOT: @llvm.sadd.with.overflow
23- ; CHECK: br i1 false, label %trap, label %cont, !nosanitize !0
2440 br i1 %1 , label %trap , label %cont , !nosanitize !{}
2541
2642trap: ; preds = %for.body
@@ -34,7 +50,25 @@ cont: ; preds = %for.body
3450}
3551
3652define void @f_sadd_overflow (ptr %a ) {
37- ; CHECK-LABEL: @f_sadd_overflow(
53+ ; CHECK-LABEL: define void @f_sadd_overflow(
54+ ; CHECK-SAME: ptr [[A:%.*]]) {
55+ ; CHECK-NEXT: [[ENTRY:.*]]:
56+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
57+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
58+ ; CHECK-NEXT: ret void
59+ ; CHECK: [[FOR_BODY]]:
60+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 2147483645, %[[ENTRY]] ]
61+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
62+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
63+ ; CHECK-NEXT: [[EXITCOND:%.*]] = icmp eq i64 [[INDVARS_IV]], 2147483647
64+ ; CHECK-NEXT: br i1 [[EXITCOND]], label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
65+ ; CHECK: [[TRAP]]:
66+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
67+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
68+ ; CHECK: [[CONT]]:
69+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nuw nsw i64 [[INDVARS_IV]], 1
70+ ; CHECK-NEXT: br i1 true, label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
71+ ;
3872entry:
3973 br label %for.body
4074
@@ -48,8 +82,6 @@ for.body: ; preds = %entry, %cont
4882 store i8 0 , ptr %arrayidx , align 1
4983 %0 = tail call { i32 , i1 } @llvm.sadd.with.overflow.i32 (i32 %i.04 , i32 1 )
5084 %1 = extractvalue { i32 , i1 } %0 , 1
51- ; CHECK: cont:
52- ; CHECK: br i1 true, label %for.body, label %for.cond.cleanup
5385 br i1 %1 , label %trap , label %cont , !nosanitize !{}
5486
5587trap: ; preds = %for.body
@@ -63,7 +95,25 @@ cont: ; preds = %for.body
6395}
6496
6597define void @f_uadd (ptr %a ) {
66- ; CHECK-LABEL: @f_uadd(
98+ ; CHECK-LABEL: define void @f_uadd(
99+ ; CHECK-SAME: ptr [[A:%.*]]) {
100+ ; CHECK-NEXT: [[ENTRY:.*]]:
101+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
102+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
103+ ; CHECK-NEXT: ret void
104+ ; CHECK: [[FOR_BODY]]:
105+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 0, %[[ENTRY]] ]
106+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
107+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
108+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nuw nsw i64 [[INDVARS_IV]], 1
109+ ; CHECK-NEXT: br i1 false, label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
110+ ; CHECK: [[TRAP]]:
111+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
112+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
113+ ; CHECK: [[CONT]]:
114+ ; CHECK-NEXT: [[EXITCOND:%.*]] = icmp ne i64 [[INDVARS_IV_NEXT]], 16
115+ ; CHECK-NEXT: br i1 [[EXITCOND]], label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
116+ ;
67117entry:
68118 br label %for.body
69119
@@ -77,9 +127,6 @@ for.body: ; preds = %entry, %cont
77127 store i8 0 , ptr %arrayidx , align 1
78128 %0 = tail call { i32 , i1 } @llvm.uadd.with.overflow.i32 (i32 %i.04 , i32 1 )
79129 %1 = extractvalue { i32 , i1 } %0 , 1
80- ; CHECK: for.body:
81- ; CHECK-NOT: @llvm.uadd.with.overflow
82- ; CHECK: br i1 false, label %trap, label %cont, !nosanitize !0
83130 br i1 %1 , label %trap , label %cont , !nosanitize !{}
84131
85132trap: ; preds = %for.body
@@ -93,7 +140,25 @@ cont: ; preds = %for.body
93140}
94141
95142define void @f_uadd_overflow (ptr %a ) {
96- ; CHECK-LABEL: @f_uadd_overflow(
143+ ; CHECK-LABEL: define void @f_uadd_overflow(
144+ ; CHECK-SAME: ptr [[A:%.*]]) {
145+ ; CHECK-NEXT: [[ENTRY:.*]]:
146+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
147+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
148+ ; CHECK-NEXT: ret void
149+ ; CHECK: [[FOR_BODY]]:
150+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ -6, %[[ENTRY]] ]
151+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
152+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
153+ ; CHECK-NEXT: [[EXITCOND:%.*]] = icmp eq i64 [[INDVARS_IV]], -1
154+ ; CHECK-NEXT: br i1 [[EXITCOND]], label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
155+ ; CHECK: [[TRAP]]:
156+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
157+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
158+ ; CHECK: [[CONT]]:
159+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nsw i64 [[INDVARS_IV]], 1
160+ ; CHECK-NEXT: br i1 true, label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
161+ ;
97162entry:
98163 br label %for.body
99164
@@ -107,8 +172,6 @@ for.body: ; preds = %entry, %cont
107172 store i8 0 , ptr %arrayidx , align 1
108173 %0 = tail call { i32 , i1 } @llvm.uadd.with.overflow.i32 (i32 %i.04 , i32 1 )
109174 %1 = extractvalue { i32 , i1 } %0 , 1
110- ; CHECK: cont:
111- ; CHECK: br i1 true, label %for.body, label %for.cond.cleanup
112175 br i1 %1 , label %trap , label %cont , !nosanitize !{}
113176
114177trap: ; preds = %for.body
@@ -122,7 +185,25 @@ cont: ; preds = %for.body
122185}
123186
124187define void @f_ssub (ptr nocapture %a ) {
125- ; CHECK-LABEL: @f_ssub(
188+ ; CHECK-LABEL: define void @f_ssub(
189+ ; CHECK-SAME: ptr captures(none) [[A:%.*]]) {
190+ ; CHECK-NEXT: [[ENTRY:.*]]:
191+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
192+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
193+ ; CHECK-NEXT: ret void
194+ ; CHECK: [[FOR_BODY]]:
195+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 15, %[[ENTRY]] ]
196+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
197+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
198+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nsw i64 [[INDVARS_IV]], -1
199+ ; CHECK-NEXT: br i1 false, label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
200+ ; CHECK: [[TRAP]]:
201+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
202+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
203+ ; CHECK: [[CONT]]:
204+ ; CHECK-NEXT: [[CMP:%.*]] = icmp sgt i64 [[INDVARS_IV_NEXT]], -1
205+ ; CHECK-NEXT: br i1 [[CMP]], label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
206+ ;
126207entry:
127208 br label %for.body
128209
@@ -136,9 +217,6 @@ for.body: ; preds = %entry, %cont
136217 store i8 0 , ptr %arrayidx , align 1
137218 %0 = tail call { i32 , i1 } @llvm.ssub.with.overflow.i32 (i32 %i.04 , i32 1 )
138219 %1 = extractvalue { i32 , i1 } %0 , 1
139- ; CHECK: for.body:
140- ; CHECK-NOT: @llvm.ssub.with.overflow.i32
141- ; CHECK: br i1 false, label %trap, label %cont, !nosanitize !0
142220 br i1 %1 , label %trap , label %cont , !nosanitize !{}
143221
144222trap: ; preds = %for.body
@@ -152,7 +230,27 @@ cont: ; preds = %for.body
152230}
153231
154232define void @f_ssub_overflow (ptr nocapture %a ) {
155- ; CHECK-LABEL: @f_ssub_overflow(
233+ ; CHECK-LABEL: define void @f_ssub_overflow(
234+ ; CHECK-SAME: ptr captures(none) [[A:%.*]]) {
235+ ; CHECK-NEXT: [[ENTRY:.*]]:
236+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
237+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
238+ ; CHECK-NEXT: ret void
239+ ; CHECK: [[FOR_BODY]]:
240+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ -2147483642, %[[ENTRY]] ]
241+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
242+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
243+ ; CHECK-NEXT: [[TMP0:%.*]] = trunc nsw i64 [[INDVARS_IV]] to i32
244+ ; CHECK-NEXT: [[TMP1:%.*]] = tail call { i32, i1 } @llvm.ssub.with.overflow.i32(i32 [[TMP0]], i32 1)
245+ ; CHECK-NEXT: [[TMP2:%.*]] = extractvalue { i32, i1 } [[TMP1]], 1
246+ ; CHECK-NEXT: br i1 [[TMP2]], label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
247+ ; CHECK: [[TRAP]]:
248+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
249+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
250+ ; CHECK: [[CONT]]:
251+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nsw i64 [[INDVARS_IV]], -1
252+ ; CHECK-NEXT: br i1 true, label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
253+ ;
156254entry:
157255 br label %for.body
158256
@@ -166,10 +264,6 @@ for.body: ; preds = %entry, %cont
166264 store i8 0 , ptr %arrayidx , align 1
167265 %0 = tail call { i32 , i1 } @llvm.ssub.with.overflow.i32 (i32 %i.04 , i32 1 )
168266 %1 = extractvalue { i32 , i1 } %0 , 1
169- ; CHECK: [[COND:%[^ ]+]] = extractvalue { i32, i1 } %1, 1
170- ; CHECK-NEXT: br i1 [[COND]], label %trap, label %cont, !nosanitize !0
171- ; CHECK: cont:
172- ; CHECK: br i1 true, label %for.body, label %for.cond.cleanup
173267 br i1 %1 , label %trap , label %cont , !nosanitize !{}
174268
175269trap: ; preds = %for.body
@@ -183,7 +277,25 @@ cont: ; preds = %for.body
183277}
184278
185279define void @f_usub (ptr nocapture %a ) {
186- ; CHECK-LABEL: @f_usub(
280+ ; CHECK-LABEL: define void @f_usub(
281+ ; CHECK-SAME: ptr captures(none) [[A:%.*]]) {
282+ ; CHECK-NEXT: [[ENTRY:.*]]:
283+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
284+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
285+ ; CHECK-NEXT: ret void
286+ ; CHECK: [[FOR_BODY]]:
287+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 15, %[[ENTRY]] ]
288+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
289+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
290+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nsw i64 [[INDVARS_IV]], -1
291+ ; CHECK-NEXT: br i1 false, label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
292+ ; CHECK: [[TRAP]]:
293+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
294+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
295+ ; CHECK: [[CONT]]:
296+ ; CHECK-NEXT: [[CMP:%.*]] = icmp samesign ugt i64 [[INDVARS_IV_NEXT]], 0
297+ ; CHECK-NEXT: br i1 [[CMP]], label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
298+ ;
187299entry:
188300 br label %for.body
189301
@@ -198,9 +310,6 @@ for.body: ; preds = %entry, %cont
198310 %0 = tail call { i32 , i1 } @llvm.usub.with.overflow.i32 (i32 %i.04 , i32 1 )
199311 %1 = extractvalue { i32 , i1 } %0 , 1
200312
201- ; CHECK: for.body:
202- ; CHECK-NOT: @llvm.usub.with.overflow.i32
203- ; CHECK: br i1 false, label %trap, label %cont, !nosanitize !0
204313 br i1 %1 , label %trap , label %cont , !nosanitize !{}
205314
206315trap: ; preds = %for.body
@@ -214,7 +323,27 @@ cont: ; preds = %for.body
214323}
215324
216325define void @f_usub_overflow (ptr nocapture %a ) {
217- ; CHECK-LABEL: @f_usub_overflow(
326+ ; CHECK-LABEL: define void @f_usub_overflow(
327+ ; CHECK-SAME: ptr captures(none) [[A:%.*]]) {
328+ ; CHECK-NEXT: [[ENTRY:.*]]:
329+ ; CHECK-NEXT: br label %[[FOR_BODY:.*]]
330+ ; CHECK: [[FOR_COND_CLEANUP:.*]]:
331+ ; CHECK-NEXT: ret void
332+ ; CHECK: [[FOR_BODY]]:
333+ ; CHECK-NEXT: [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], %[[CONT:.*]] ], [ 15, %[[ENTRY]] ]
334+ ; CHECK-NEXT: [[ARRAYIDX:%.*]] = getelementptr inbounds i8, ptr [[A]], i64 [[INDVARS_IV]]
335+ ; CHECK-NEXT: store i8 0, ptr [[ARRAYIDX]], align 1
336+ ; CHECK-NEXT: [[TMP0:%.*]] = trunc nuw nsw i64 [[INDVARS_IV]] to i32
337+ ; CHECK-NEXT: [[TMP1:%.*]] = tail call { i32, i1 } @llvm.usub.with.overflow.i32(i32 [[TMP0]], i32 1)
338+ ; CHECK-NEXT: [[TMP2:%.*]] = extractvalue { i32, i1 } [[TMP1]], 1
339+ ; CHECK-NEXT: br i1 [[TMP2]], label %[[TRAP:.*]], label %[[CONT]], !nosanitize [[META0]]
340+ ; CHECK: [[TRAP]]:
341+ ; CHECK-NEXT: tail call void @llvm.trap(), !nosanitize [[META0]]
342+ ; CHECK-NEXT: unreachable, !nosanitize [[META0]]
343+ ; CHECK: [[CONT]]:
344+ ; CHECK-NEXT: [[INDVARS_IV_NEXT]] = add nsw i64 [[INDVARS_IV]], -1
345+ ; CHECK-NEXT: br i1 true, label %[[FOR_BODY]], label %[[FOR_COND_CLEANUP]]
346+ ;
218347entry:
219348 br label %for.body
220349
@@ -232,11 +361,6 @@ for.body: ; preds = %entry, %cont
232361; It is theoretically possible to prove this, but SCEV cannot
233362; represent non-unsigned-wrapping subtraction operations.
234363
235- ; CHECK: for.body:
236- ; CHECK: [[COND:%[^ ]+]] = extractvalue { i32, i1 } %1, 1
237- ; CHECK-NEXT: br i1 [[COND]], label %trap, label %cont, !nosanitize !0
238- ; CHECK: cont:
239- ; CHECK: br i1 true, label %for.body, label %for.cond.cleanup
240364 br i1 %1 , label %trap , label %cont , !nosanitize !{}
241365
242366trap: ; preds = %for.body
@@ -257,3 +381,6 @@ declare { i32, i1 } @llvm.smul.with.overflow.i32(i32, i32) nounwind readnone
257381declare { i32 , i1 } @llvm.umul.with.overflow.i32 (i32 , i32 ) nounwind readnone
258382
259383declare void @llvm.trap () #2
384+ ;.
385+ ; CHECK: [[META0]] = !{}
386+ ;.
0 commit comments