xref: /llvm-project/llvm/test/Transforms/LoopFlatten/loop-flatten.ll (revision 055fb7795aa219a3d274d280ec9129784f169f56)
172482c51SRoman Lebedev; RUN: opt < %s -S -passes='loop(loop-flatten),verify' -verify-loop-info -verify-dom-info -verify-scev | FileCheck %s
2d53b4beeSSjoerd Meijer
3d53b4beeSSjoerd Meijertarget datalayout = "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"
4d53b4beeSSjoerd Meijer
5d53b4beeSSjoerd Meijer; CHECK-LABEL: test1
6d53b4beeSSjoerd Meijer; Simple loop where the IV's is constant
7*055fb779SNikita Popovdefine i32 @test1(i32 %val, ptr nocapture %A) {
8d53b4beeSSjoerd Meijerentry:
9d53b4beeSSjoerd Meijer  br label %for.body
10d53b4beeSSjoerd Meijer; CHECK: entry:
11d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 20, 10
12d53b4beeSSjoerd Meijer; CHECK:   br label %for.body
13d53b4beeSSjoerd Meijer
14d53b4beeSSjoerd Meijerfor.body:                                         ; preds = %entry, %for.inc6
15d53b4beeSSjoerd Meijer  %i.018 = phi i32 [ 0, %entry ], [ %inc7, %for.inc6 ]
16d53b4beeSSjoerd Meijer  %mul = mul nuw nsw i32 %i.018, 20
17d53b4beeSSjoerd Meijer  br label %for.body3
18d53b4beeSSjoerd Meijer; CHECK: for.body:
19d53b4beeSSjoerd Meijer; CHECK:   %i.018 = phi i32 [ 0, %entry ], [ %inc7, %for.inc6 ]
20d53b4beeSSjoerd Meijer; CHECK:   %mul = mul nuw nsw i32 %i.018, 20
21d53b4beeSSjoerd Meijer; CHECK:   br label %for.body3
22d53b4beeSSjoerd Meijer
23d53b4beeSSjoerd Meijerfor.body3:                                        ; preds = %for.body, %for.body3
24d53b4beeSSjoerd Meijer  %j.017 = phi i32 [ 0, %for.body ], [ %inc, %for.body3 ]
25d53b4beeSSjoerd Meijer  %add = add nuw nsw i32 %j.017, %mul
26*055fb779SNikita Popov  %arrayidx = getelementptr inbounds i16, ptr %A, i32 %add
27*055fb779SNikita Popov  %0 = load i16, ptr %arrayidx, align 2
28d53b4beeSSjoerd Meijer  %conv16 = zext i16 %0 to i32
29d53b4beeSSjoerd Meijer  %add4 = add i32 %conv16, %val
30d53b4beeSSjoerd Meijer  %conv5 = trunc i32 %add4 to i16
31*055fb779SNikita Popov  store i16 %conv5, ptr %arrayidx, align 2
32d53b4beeSSjoerd Meijer  %inc = add nuw nsw i32 %j.017, 1
33d53b4beeSSjoerd Meijer  %exitcond = icmp ne i32 %inc, 20
34d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.body3, label %for.inc6
35d53b4beeSSjoerd Meijer; CHECK: for.body3:
36d53b4beeSSjoerd Meijer; CHECK:   %j.017 = phi i32 [ 0, %for.body ]
37d53b4beeSSjoerd Meijer; CHECK:   %add = add nuw nsw i32 %j.017, %mul
38*055fb779SNikita Popov; CHECK:   %arrayidx = getelementptr inbounds i16, ptr %A, i32 %i.018
39*055fb779SNikita Popov; CHECK:   %0 = load i16, ptr %arrayidx, align 2
40d53b4beeSSjoerd Meijer; CHECK:   %conv16 = zext i16 %0 to i32
41d53b4beeSSjoerd Meijer; CHECK:   %add4 = add i32 %conv16, %val
42d53b4beeSSjoerd Meijer; CHECK:   %conv5 = trunc i32 %add4 to i16
43*055fb779SNikita Popov; CHECK:   store i16 %conv5, ptr %arrayidx, align 2
44d53b4beeSSjoerd Meijer; CHECK:   %inc = add nuw nsw i32 %j.017, 1
45d53b4beeSSjoerd Meijer; CHECK:   %exitcond = icmp ne i32 %inc, 20
46d53b4beeSSjoerd Meijer; CHECK:   br label %for.inc6
47d53b4beeSSjoerd Meijer
48d53b4beeSSjoerd Meijerfor.inc6:                                         ; preds = %for.body3
49d53b4beeSSjoerd Meijer  %inc7 = add nuw nsw i32 %i.018, 1
50d53b4beeSSjoerd Meijer  %exitcond19 = icmp ne i32 %inc7, 10
51d53b4beeSSjoerd Meijer  br i1 %exitcond19, label %for.body, label %for.end8
52d53b4beeSSjoerd Meijer; CHECK: for.inc6:
53d53b4beeSSjoerd Meijer; CHECK:   %inc7 = add nuw nsw i32 %i.018, 1
54d53b4beeSSjoerd Meijer; CHECK:   %exitcond19 = icmp ne i32 %inc7, %flatten.tripcount
55d53b4beeSSjoerd Meijer; CHECK:   br i1 %exitcond19, label %for.body, label %for.end8
56d53b4beeSSjoerd Meijer
57d53b4beeSSjoerd Meijerfor.end8:                                         ; preds = %for.inc6
58d53b4beeSSjoerd Meijer  ret i32 10
59d53b4beeSSjoerd Meijer}
60d53b4beeSSjoerd Meijer
61d53b4beeSSjoerd Meijer
62d53b4beeSSjoerd Meijer; CHECK-LABEL: test2
63d53b4beeSSjoerd Meijer; Same as above but non constant IV (which still cannot overflow)
64*055fb779SNikita Popovdefine i32 @test2(i8 zeroext %I, i32 %val, ptr nocapture %A) {
65d53b4beeSSjoerd Meijerentry:
66d53b4beeSSjoerd Meijer  %conv = zext i8 %I to i32
67d53b4beeSSjoerd Meijer  %cmp26 = icmp eq i8 %I, 0
68d53b4beeSSjoerd Meijer  br i1 %cmp26, label %for.end13, label %for.body.lr.ph.split.us
69d53b4beeSSjoerd Meijer
70d53b4beeSSjoerd Meijerfor.body.lr.ph.split.us:                          ; preds = %entry
71d53b4beeSSjoerd Meijer  br label %for.body.us
72d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph.split.us:
73d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 %conv, %conv
74d53b4beeSSjoerd Meijer; CHECK:   br label %for.body.us
75d53b4beeSSjoerd Meijer
76d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond2.for.inc11_crit_edge.us, %for.body.lr.ph.split.us
77d53b4beeSSjoerd Meijer  %i.027.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc12.us, %for.cond2.for.inc11_crit_edge.us ]
78d53b4beeSSjoerd Meijer  %mul.us = mul nuw nsw i32 %i.027.us, %conv
79d53b4beeSSjoerd Meijer  br label %for.body6.us
80d53b4beeSSjoerd Meijer; CHECK: for.body.us:
81d53b4beeSSjoerd Meijer; CHECK:   %i.027.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc12.us, %for.cond2.for.inc11_crit_edge.us ]
82d53b4beeSSjoerd Meijer; CHECK:   %mul.us = mul nuw nsw i32 %i.027.us, %conv
83d53b4beeSSjoerd Meijer; CHECK:   br label %for.body6.us
84d53b4beeSSjoerd Meijer
85d53b4beeSSjoerd Meijerfor.body6.us:                                     ; preds = %for.body.us, %for.body6.us
86d53b4beeSSjoerd Meijer  %j.025.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %for.body6.us ]
87d53b4beeSSjoerd Meijer  %add.us = add nuw nsw i32 %j.025.us, %mul.us
88*055fb779SNikita Popov  %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %add.us
89*055fb779SNikita Popov  %0 = load i16, ptr %arrayidx.us, align 2
90d53b4beeSSjoerd Meijer  %conv823.us = zext i16 %0 to i32
91d53b4beeSSjoerd Meijer  %add9.us = add i32 %conv823.us, %val
92d53b4beeSSjoerd Meijer  %conv10.us = trunc i32 %add9.us to i16
93*055fb779SNikita Popov  store i16 %conv10.us, ptr %arrayidx.us, align 2
94d53b4beeSSjoerd Meijer  %inc.us = add nuw nsw i32 %j.025.us, 1
95d53b4beeSSjoerd Meijer  %exitcond = icmp ne i32 %inc.us, %conv
96d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.body6.us, label %for.cond2.for.inc11_crit_edge.us
97d53b4beeSSjoerd Meijer; CHECK: for.body6.us:
98d53b4beeSSjoerd Meijer; CHECK:   %j.025.us = phi i32 [ 0, %for.body.us ]
99d53b4beeSSjoerd Meijer; CHECK:   %add.us = add nuw nsw i32 %j.025.us, %mul.us
100*055fb779SNikita Popov; CHECK:   %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %i.027.us
101*055fb779SNikita Popov; CHECK:   %0 = load i16, ptr %arrayidx.us, align 2
102d53b4beeSSjoerd Meijer; CHECK:   %conv823.us = zext i16 %0 to i32
103d53b4beeSSjoerd Meijer; CHECK:   %add9.us = add i32 %conv823.us, %val
104d53b4beeSSjoerd Meijer; CHECK:   %conv10.us = trunc i32 %add9.us to i16
105*055fb779SNikita Popov; CHECK:   store i16 %conv10.us, ptr %arrayidx.us, align 2
106d53b4beeSSjoerd Meijer; CHECK:   %inc.us = add nuw nsw i32 %j.025.us, 1
107d53b4beeSSjoerd Meijer; CHECK:   %exitcond = icmp ne i32 %inc.us, %conv
108d53b4beeSSjoerd Meijer; CHECK:   br label %for.cond2.for.inc11_crit_edge.us
109d53b4beeSSjoerd Meijer
110d53b4beeSSjoerd Meijerfor.cond2.for.inc11_crit_edge.us:                 ; preds = %for.body6.us
111d53b4beeSSjoerd Meijer  %inc12.us = add nuw nsw i32 %i.027.us, 1
112d53b4beeSSjoerd Meijer  %exitcond28 = icmp ne i32 %inc12.us, %conv
113d53b4beeSSjoerd Meijer  br i1 %exitcond28, label %for.body.us, label %for.end13.loopexit
114d53b4beeSSjoerd Meijer; CHECK: for.cond2.for.inc11_crit_edge.us:                 ; preds = %for.body6.us
115d53b4beeSSjoerd Meijer; CHECK:   %inc12.us = add nuw nsw i32 %i.027.us, 1
116d53b4beeSSjoerd Meijer; CHECK:   %exitcond28 = icmp ne i32 %inc12.us, %flatten.tripcount
117d53b4beeSSjoerd Meijer; CHECK:   br i1 %exitcond28, label %for.body.us, label %for.end13.loopexit
118d53b4beeSSjoerd Meijer
119d53b4beeSSjoerd Meijerfor.end13.loopexit:                               ; preds = %for.cond2.for.inc11_crit_edge.us
120d53b4beeSSjoerd Meijer  br label %for.end13
121d53b4beeSSjoerd Meijer
122d53b4beeSSjoerd Meijerfor.end13:                                        ; preds = %for.end13.loopexit, %entry
123d53b4beeSSjoerd Meijer  %i.0.lcssa = phi i32 [ 0, %entry ], [ %conv, %for.end13.loopexit ]
124d53b4beeSSjoerd Meijer  ret i32 %i.0.lcssa
125d53b4beeSSjoerd Meijer}
126d53b4beeSSjoerd Meijer
127d53b4beeSSjoerd Meijer
128d53b4beeSSjoerd Meijer; CHECK-LABEL: test3
129d53b4beeSSjoerd Meijer; Same as above, uses load to determine it can't overflow
130*055fb779SNikita Popovdefine i32 @test3(i32 %N, i32 %val, ptr nocapture %A) local_unnamed_addr #0 {
131d53b4beeSSjoerd Meijerentry:
132d53b4beeSSjoerd Meijer  %cmp21 = icmp eq i32 %N, 0
133d53b4beeSSjoerd Meijer  br i1 %cmp21, label %for.end8, label %for.body.lr.ph.split.us
134d53b4beeSSjoerd Meijer
135d53b4beeSSjoerd Meijerfor.body.lr.ph.split.us:                          ; preds = %entry
136d53b4beeSSjoerd Meijer  br label %for.body.us
137d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph.split.us:
138d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 %N, %N
139d53b4beeSSjoerd Meijer; CHECK:   br label %for.body.us
140d53b4beeSSjoerd Meijer
141d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond1.for.inc6_crit_edge.us, %for.body.lr.ph.split.us
142d53b4beeSSjoerd Meijer  %i.022.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc7.us, %for.cond1.for.inc6_crit_edge.us ]
143d53b4beeSSjoerd Meijer  %mul.us = mul i32 %i.022.us, %N
144d53b4beeSSjoerd Meijer  br label %for.body3.us
145d53b4beeSSjoerd Meijer; CHECK: for.body.us:
146d53b4beeSSjoerd Meijer; CHECK:   %i.022.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc7.us, %for.cond1.for.inc6_crit_edge.us ]
147d53b4beeSSjoerd Meijer; CHECK:   %mul.us = mul i32 %i.022.us, %N
148d53b4beeSSjoerd Meijer; CHECK:   br label %for.body3.us
149d53b4beeSSjoerd Meijer
150d53b4beeSSjoerd Meijerfor.body3.us:                                     ; preds = %for.body.us, %for.body3.us
151d53b4beeSSjoerd Meijer  %j.020.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %for.body3.us ]
152d53b4beeSSjoerd Meijer  %add.us = add i32 %j.020.us, %mul.us
153*055fb779SNikita Popov  %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %add.us
154*055fb779SNikita Popov  %0 = load i16, ptr %arrayidx.us, align 2
155d53b4beeSSjoerd Meijer  %conv18.us = zext i16 %0 to i32
156d53b4beeSSjoerd Meijer  %add4.us = add i32 %conv18.us, %val
157d53b4beeSSjoerd Meijer  %conv5.us = trunc i32 %add4.us to i16
158*055fb779SNikita Popov  store i16 %conv5.us, ptr %arrayidx.us, align 2
159d53b4beeSSjoerd Meijer  %inc.us = add nuw i32 %j.020.us, 1
160d53b4beeSSjoerd Meijer  %exitcond = icmp ne i32 %inc.us, %N
161d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.body3.us, label %for.cond1.for.inc6_crit_edge.us
162d53b4beeSSjoerd Meijer; CHECK: for.body3.us:
163d53b4beeSSjoerd Meijer; CHECK:   %j.020.us = phi i32 [ 0, %for.body.us ]
164d53b4beeSSjoerd Meijer; CHECK:   %add.us = add i32 %j.020.us, %mul.us
165*055fb779SNikita Popov; CHECK:   %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %i.022.us
166*055fb779SNikita Popov; CHECK:   %0 = load i16, ptr %arrayidx.us, align 2
167d53b4beeSSjoerd Meijer; CHECK:   %conv18.us = zext i16 %0 to i32
168d53b4beeSSjoerd Meijer; CHECK:   %add4.us = add i32 %conv18.us, %val
169d53b4beeSSjoerd Meijer; CHECK:   %conv5.us = trunc i32 %add4.us to i16
170*055fb779SNikita Popov; CHECK:   store i16 %conv5.us, ptr %arrayidx.us, align 2
171d53b4beeSSjoerd Meijer; CHECK:   %inc.us = add nuw i32 %j.020.us, 1
172d53b4beeSSjoerd Meijer; CHECK:   %exitcond = icmp ne i32 %inc.us, %N
173d53b4beeSSjoerd Meijer; CHECK:   br label %for.cond1.for.inc6_crit_edge.us
174d53b4beeSSjoerd Meijer
175d53b4beeSSjoerd Meijerfor.cond1.for.inc6_crit_edge.us:                  ; preds = %for.body3.us
176d53b4beeSSjoerd Meijer  %inc7.us = add nuw i32 %i.022.us, 1
177d53b4beeSSjoerd Meijer  %exitcond23 = icmp ne i32 %inc7.us, %N
178d53b4beeSSjoerd Meijer  br i1 %exitcond23, label %for.body.us, label %for.end8.loopexit
179d53b4beeSSjoerd Meijer; CHECK: for.cond1.for.inc6_crit_edge.us:
180d53b4beeSSjoerd Meijer; CHECK:   %inc7.us = add nuw i32 %i.022.us, 1
181d53b4beeSSjoerd Meijer; CHECK:   %exitcond23 = icmp ne i32 %inc7.us, %flatten.tripcount
182d53b4beeSSjoerd Meijer; CHECK:   br i1 %exitcond23, label %for.body.us, label %for.end8.loopexit
183d53b4beeSSjoerd Meijer
184d53b4beeSSjoerd Meijerfor.end8.loopexit:                                ; preds = %for.cond1.for.inc6_crit_edge.us
185d53b4beeSSjoerd Meijer  br label %for.end8
186d53b4beeSSjoerd Meijer
187d53b4beeSSjoerd Meijerfor.end8:                                         ; preds = %for.end8.loopexit, %entry
188d53b4beeSSjoerd Meijer  %i.0.lcssa = phi i32 [ 0, %entry ], [ %N, %for.end8.loopexit ]
189d53b4beeSSjoerd Meijer  ret i32 %i.0.lcssa
190d53b4beeSSjoerd Meijer}
191d53b4beeSSjoerd Meijer
192d53b4beeSSjoerd Meijer
193d53b4beeSSjoerd Meijer; CHECK-LABEL: test4
194d53b4beeSSjoerd Meijer; Multiplication cannot overflow, so we can replace the original loop.
195*055fb779SNikita Popovdefine void @test4(i16 zeroext %N, ptr nocapture %C, ptr nocapture readonly %A, i32 %scale) {
196d53b4beeSSjoerd Meijerentry:
197d53b4beeSSjoerd Meijer  %conv = zext i16 %N to i32
198d53b4beeSSjoerd Meijer  %cmp30 = icmp eq i16 %N, 0
199d53b4beeSSjoerd Meijer  br i1 %cmp30, label %for.cond.cleanup, label %for.body.lr.ph.split.us
200d53b4beeSSjoerd Meijer; CHECK: entry:
201d53b4beeSSjoerd Meijer; CHECK: %[[LIMIT:.*]] = zext i16 %N to i32
202d53b4beeSSjoerd Meijer; CHECK: br i1 %{{.*}} label %for.cond.cleanup, label %for.body.lr.ph.split.us
203d53b4beeSSjoerd Meijer
204d53b4beeSSjoerd Meijerfor.body.lr.ph.split.us:                          ; preds = %entry
205d53b4beeSSjoerd Meijer  br label %for.body.us
206d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph.split.us:
207d53b4beeSSjoerd Meijer; CHECK: %[[TRIPCOUNT:.*]] = mul i32 %[[LIMIT]], %[[LIMIT]]
208d53b4beeSSjoerd Meijer; CHECK: br label %for.body.us
209d53b4beeSSjoerd Meijer
210d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond2.for.cond.cleanup6_crit_edge.us, %for.body.lr.ph.split.us
211d53b4beeSSjoerd Meijer  %i.031.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc15.us, %for.cond2.for.cond.cleanup6_crit_edge.us ]
212d53b4beeSSjoerd Meijer  %mul.us = mul nuw nsw i32 %i.031.us, %conv
213d53b4beeSSjoerd Meijer  br label %for.body7.us
214d53b4beeSSjoerd Meijer; CHECK: for.body.us:
215d53b4beeSSjoerd Meijer; CHECK: %[[OUTER_IV:.*]] = phi i32
216d53b4beeSSjoerd Meijer; CHECK: br label %for.body7.us
217d53b4beeSSjoerd Meijer
218d53b4beeSSjoerd Meijerfor.body7.us:                                     ; preds = %for.body.us, %for.body7.us
219d53b4beeSSjoerd Meijer; CHECK: for.body7.us:
220d53b4beeSSjoerd Meijer  %j.029.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %for.body7.us ]
221d53b4beeSSjoerd Meijer  %add.us = add nuw nsw i32 %j.029.us, %mul.us
222*055fb779SNikita Popov  %arrayidx.us = getelementptr inbounds i32, ptr %A, i32 %add.us
223*055fb779SNikita Popov; CHECK: getelementptr inbounds i32, ptr %A, i32 %[[OUTER_IV]]
224*055fb779SNikita Popov  %0 = load i32, ptr %arrayidx.us, align 4
225d53b4beeSSjoerd Meijer  %mul9.us = mul nsw i32 %0, %scale
226*055fb779SNikita Popov; CHECK: getelementptr inbounds i32, ptr %C, i32 %[[OUTER_IV]]
227*055fb779SNikita Popov  %arrayidx13.us = getelementptr inbounds i32, ptr %C, i32 %add.us
228*055fb779SNikita Popov  store i32 %mul9.us, ptr %arrayidx13.us, align 4
229d53b4beeSSjoerd Meijer  %inc.us = add nuw nsw i32 %j.029.us, 1
230d53b4beeSSjoerd Meijer  %exitcond = icmp ne i32 %inc.us, %conv
231d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.body7.us, label %for.cond2.for.cond.cleanup6_crit_edge.us
232d53b4beeSSjoerd Meijer; CHECK: br label %for.cond2.for.cond.cleanup6_crit_edge.us
233d53b4beeSSjoerd Meijer
234d53b4beeSSjoerd Meijerfor.cond2.for.cond.cleanup6_crit_edge.us:         ; preds = %for.body7.us
235d53b4beeSSjoerd Meijer  %inc15.us = add nuw nsw i32 %i.031.us, 1
236d53b4beeSSjoerd Meijer  %exitcond32 = icmp ne i32 %inc15.us, %conv
237d53b4beeSSjoerd Meijer  br i1 %exitcond32, label %for.body.us, label %for.cond.cleanup.loopexit
238d53b4beeSSjoerd Meijer; CHECK: for.cond2.for.cond.cleanup6_crit_edge.us:
239d53b4beeSSjoerd Meijer; CHECK: br i1 %exitcond32, label %for.body.us, label %for.cond.cleanup.loopexit
240d53b4beeSSjoerd Meijer
241d53b4beeSSjoerd Meijerfor.cond.cleanup.loopexit:                        ; preds = %for.cond2.for.cond.cleanup6_crit_edge.us
242d53b4beeSSjoerd Meijer  br label %for.cond.cleanup
243d53b4beeSSjoerd Meijer; CHECK: for.cond.cleanup.loopexit:
244d53b4beeSSjoerd Meijer; CHECK: br label %for.cond.cleanup
245d53b4beeSSjoerd Meijer
246d53b4beeSSjoerd Meijerfor.cond.cleanup:                                 ; preds = %for.cond.cleanup.loopexit, %entry
247d53b4beeSSjoerd Meijer  ret void
248d53b4beeSSjoerd Meijer; CHECK: for.cond.cleanup:
249d53b4beeSSjoerd Meijer; CHECK: ret void
250d53b4beeSSjoerd Meijer}
251d53b4beeSSjoerd Meijer
252d53b4beeSSjoerd Meijer
253d53b4beeSSjoerd Meijer; CHECK-LABEL: test5
254d53b4beeSSjoerd Meijerdefine i32 @test5(i8 zeroext %I, i16 zeroext %J) {
255d53b4beeSSjoerd Meijerentry:
256d53b4beeSSjoerd Meijer  %0 = lshr i8 %I, 1
257d53b4beeSSjoerd Meijer  %div = zext i8 %0 to i32
258d53b4beeSSjoerd Meijer  %cmp30 = icmp eq i8 %0, 0
259d53b4beeSSjoerd Meijer  br i1 %cmp30, label %for.cond.cleanup, label %for.body.lr.ph
260d53b4beeSSjoerd Meijer
261d53b4beeSSjoerd Meijerfor.body.lr.ph:                                   ; preds = %entry
262d53b4beeSSjoerd Meijer  %1 = lshr i16 %J, 1
263d53b4beeSSjoerd Meijer  %div5 = zext i16 %1 to i32
264d53b4beeSSjoerd Meijer  %cmp627 = icmp eq i16 %1, 0
265d53b4beeSSjoerd Meijer  br i1 %cmp627, label %for.body.lr.ph.split, label %for.body.lr.ph.split.us
266d53b4beeSSjoerd Meijer
267d53b4beeSSjoerd Meijerfor.body.lr.ph.split.us:                          ; preds = %for.body.lr.ph
268d53b4beeSSjoerd Meijer  br label %for.body.us
269d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph.split.us:
270d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 %div5, %div
271d53b4beeSSjoerd Meijer; CHECK:   br label %for.body.us
272d53b4beeSSjoerd Meijer
273d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond3.for.cond.cleanup8_crit_edge.us, %for.body.lr.ph.split.us
274d53b4beeSSjoerd Meijer  %i.032.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc13.us, %for.cond3.for.cond.cleanup8_crit_edge.us ]
275d53b4beeSSjoerd Meijer  %x.031.us = phi i32 [ 1, %for.body.lr.ph.split.us ], [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
276d53b4beeSSjoerd Meijer  br label %for.body9.us
277d53b4beeSSjoerd Meijer; CHECK: for.body.us:
278d53b4beeSSjoerd Meijer; CHECK:   %i.032.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc13.us, %for.cond3.for.cond.cleanup8_crit_edge.us ]
279d53b4beeSSjoerd Meijer; CHECK:   %x.031.us = phi i32 [ 1, %for.body.lr.ph.split.us ], [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
280d53b4beeSSjoerd Meijer; CHECK:   br label %for.body9.us
281d53b4beeSSjoerd Meijer
282d53b4beeSSjoerd Meijerfor.body9.us:                                     ; preds = %for.body.us, %for.body9.us
283d53b4beeSSjoerd Meijer  %j.029.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %for.body9.us ]
284d53b4beeSSjoerd Meijer  %x.128.us = phi i32 [ %x.031.us, %for.body.us ], [ %xor.us, %for.body9.us ]
285d53b4beeSSjoerd Meijer  %call.us = tail call i32 @func(i32 1)
286d53b4beeSSjoerd Meijer  %sub.us = sub nsw i32 %call.us, %x.128.us
287d53b4beeSSjoerd Meijer  %xor.us = xor i32 %sub.us, %x.128.us
288d53b4beeSSjoerd Meijer  %inc.us = add nuw nsw i32 %j.029.us, 1
289d53b4beeSSjoerd Meijer  %cmp6.us = icmp ult i32 %inc.us, %div5
290d53b4beeSSjoerd Meijer  br i1 %cmp6.us, label %for.body9.us, label %for.cond3.for.cond.cleanup8_crit_edge.us
291d53b4beeSSjoerd Meijer; CHECK: for.body9.us:
292d53b4beeSSjoerd Meijer; CHECK:   %j.029.us = phi i32 [ 0, %for.body.us ]
293d53b4beeSSjoerd Meijer; CHECK:   %x.128.us = phi i32 [ %x.031.us, %for.body.us ]
294d53b4beeSSjoerd Meijer; CHECK:   %call.us = tail call i32 @func(i32 1)
295d53b4beeSSjoerd Meijer; CHECK:   %sub.us = sub nsw i32 %call.us, %x.128.us
296d53b4beeSSjoerd Meijer; CHECK:   %xor.us = xor i32 %sub.us, %x.128.us
297d53b4beeSSjoerd Meijer; CHECK:   %inc.us = add nuw nsw i32 %j.029.us, 1
298d53b4beeSSjoerd Meijer; CHECK:   %cmp6.us = icmp ult i32 %inc.us, %div5
299d53b4beeSSjoerd Meijer; CHECK:   br label %for.cond3.for.cond.cleanup8_crit_edge.us
300d53b4beeSSjoerd Meijer
301d53b4beeSSjoerd Meijerfor.cond3.for.cond.cleanup8_crit_edge.us:         ; preds = %for.body9.us
302d53b4beeSSjoerd Meijer  %xor.us.lcssa = phi i32 [ %xor.us, %for.body9.us ]
303d53b4beeSSjoerd Meijer  %inc13.us = add nuw nsw i32 %i.032.us, 1
304d53b4beeSSjoerd Meijer  %cmp.us = icmp ult i32 %inc13.us, %div
305d53b4beeSSjoerd Meijer  br i1 %cmp.us, label %for.body.us, label %for.cond.cleanup.loopexit
306d53b4beeSSjoerd Meijer; CHECK: for.cond3.for.cond.cleanup8_crit_edge.us:
307d53b4beeSSjoerd Meijer; CHECK:   %xor.us.lcssa = phi i32 [ %xor.us, %for.body9.us ]
308d53b4beeSSjoerd Meijer; CHECK:   %inc13.us = add nuw nsw i32 %i.032.us, 1
309d53b4beeSSjoerd Meijer; CHECK:   %cmp.us = icmp ult i32 %inc13.us, %flatten.tripcount
310d53b4beeSSjoerd Meijer; CHECK:   br i1 %cmp.us, label %for.body.us, label %for.cond.cleanup.loopexit
311d53b4beeSSjoerd Meijer
312d53b4beeSSjoerd Meijerfor.body.lr.ph.split:                             ; preds = %for.body.lr.ph
313d53b4beeSSjoerd Meijer  br label %for.body
314d53b4beeSSjoerd Meijer
315d53b4beeSSjoerd Meijerfor.cond.cleanup.loopexit:                        ; preds = %for.cond3.for.cond.cleanup8_crit_edge.us
316d53b4beeSSjoerd Meijer  %xor.us.lcssa.lcssa = phi i32 [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
317d53b4beeSSjoerd Meijer  br label %for.cond.cleanup
318d53b4beeSSjoerd Meijer
319d53b4beeSSjoerd Meijerfor.cond.cleanup.loopexit34:                      ; preds = %for.body
320d53b4beeSSjoerd Meijer  br label %for.cond.cleanup
321d53b4beeSSjoerd Meijer
322d53b4beeSSjoerd Meijerfor.cond.cleanup:                                 ; preds = %for.cond.cleanup.loopexit34, %for.cond.cleanup.loopexit, %entry
323d53b4beeSSjoerd Meijer  %x.0.lcssa = phi i32 [ 1, %entry ], [ %xor.us.lcssa.lcssa, %for.cond.cleanup.loopexit ], [ 1, %for.cond.cleanup.loopexit34 ]
324d53b4beeSSjoerd Meijer  ret i32 %x.0.lcssa
325d53b4beeSSjoerd Meijer
326d53b4beeSSjoerd Meijerfor.body:                                         ; preds = %for.body.lr.ph.split, %for.body
327d53b4beeSSjoerd Meijer  %i.032 = phi i32 [ 0, %for.body.lr.ph.split ], [ %inc13, %for.body ]
328d53b4beeSSjoerd Meijer  %inc13 = add nuw nsw i32 %i.032, 1
329d53b4beeSSjoerd Meijer  %cmp = icmp ult i32 %inc13, %div
330d53b4beeSSjoerd Meijer  br i1 %cmp, label %for.body, label %for.cond.cleanup.loopexit34
331d53b4beeSSjoerd Meijer}
332d53b4beeSSjoerd Meijer
333d53b4beeSSjoerd Meijer
334d53b4beeSSjoerd Meijer; CHECK-LABEL: test6
335d53b4beeSSjoerd Meijerdefine i32 @test6(i8 zeroext %I, i16 zeroext %J) {
336d53b4beeSSjoerd Meijerentry:
337d53b4beeSSjoerd Meijer  %0 = lshr i8 %I, 1
338d53b4beeSSjoerd Meijer  %div = zext i8 %0 to i32
339d53b4beeSSjoerd Meijer  %cmp30 = icmp eq i8 %0, 0
340d53b4beeSSjoerd Meijer  br i1 %cmp30, label %for.cond.cleanup, label %for.body.lr.ph
341d53b4beeSSjoerd Meijer
342d53b4beeSSjoerd Meijerfor.body.lr.ph:                                   ; preds = %entry
343d53b4beeSSjoerd Meijer  %1 = lshr i16 %J, 1
344d53b4beeSSjoerd Meijer  %div5 = zext i16 %1 to i32
345d53b4beeSSjoerd Meijer  %cmp627 = icmp eq i16 %1, 0
346d53b4beeSSjoerd Meijer  br i1 %cmp627, label %for.body.lr.ph.split, label %for.body.lr.ph.split.us
347d53b4beeSSjoerd Meijer
348d53b4beeSSjoerd Meijerfor.body.lr.ph.split.us:                          ; preds = %for.body.lr.ph
349d53b4beeSSjoerd Meijer  br label %for.body.us
350d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph.split.us:
351d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 %div5, %div
352d53b4beeSSjoerd Meijer; CHECK:   br label %for.body.us
353d53b4beeSSjoerd Meijer
354d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond3.for.cond.cleanup8_crit_edge.us, %for.body.lr.ph.split.us
355d53b4beeSSjoerd Meijer  %i.032.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc13.us, %for.cond3.for.cond.cleanup8_crit_edge.us ]
356d53b4beeSSjoerd Meijer  %x.031.us = phi i32 [ 1, %for.body.lr.ph.split.us ], [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
357d53b4beeSSjoerd Meijer  %mul.us = mul nuw nsw i32 %i.032.us, %div5
358d53b4beeSSjoerd Meijer  br label %for.body9.us
359d53b4beeSSjoerd Meijer; CHECK: for.body.us:
360d53b4beeSSjoerd Meijer; CHECK:   %i.032.us = phi i32 [ 0, %for.body.lr.ph.split.us ], [ %inc13.us, %for.cond3.for.cond.cleanup8_crit_edge.us ]
361d53b4beeSSjoerd Meijer; CHECK:   %x.031.us = phi i32 [ 1, %for.body.lr.ph.split.us ], [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
362d53b4beeSSjoerd Meijer; CHECK:   %mul.us = mul nuw nsw i32 %i.032.us, %div5
363d53b4beeSSjoerd Meijer; CHECK:   br label %for.body9.us
364d53b4beeSSjoerd Meijer
365d53b4beeSSjoerd Meijerfor.body9.us:                                     ; preds = %for.body.us, %for.body9.us
366d53b4beeSSjoerd Meijer  %j.029.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %for.body9.us ]
367d53b4beeSSjoerd Meijer  %x.128.us = phi i32 [ %x.031.us, %for.body.us ], [ %xor.us, %for.body9.us ]
368d53b4beeSSjoerd Meijer  %add.us = add nuw nsw i32 %j.029.us, %mul.us
369d53b4beeSSjoerd Meijer  %call.us = tail call i32 @func(i32 %add.us)
370d53b4beeSSjoerd Meijer  %sub.us = sub nsw i32 %call.us, %x.128.us
371d53b4beeSSjoerd Meijer  %xor.us = xor i32 %sub.us, %x.128.us
372d53b4beeSSjoerd Meijer  %inc.us = add nuw nsw i32 %j.029.us, 1
373d53b4beeSSjoerd Meijer  %cmp6.us = icmp ult i32 %inc.us, %div5
374d53b4beeSSjoerd Meijer  br i1 %cmp6.us, label %for.body9.us, label %for.cond3.for.cond.cleanup8_crit_edge.us
375d53b4beeSSjoerd Meijer; CHECK: for.body9.us:
376d53b4beeSSjoerd Meijer; CHECK:   %j.029.us = phi i32 [ 0, %for.body.us ]
377d53b4beeSSjoerd Meijer; CHECK:   %x.128.us = phi i32 [ %x.031.us, %for.body.us ]
378d53b4beeSSjoerd Meijer; CHECK:   %add.us = add nuw nsw i32 %j.029.us, %mul.us
379d53b4beeSSjoerd Meijer; CHECK:   %call.us = tail call i32 @func(i32 %i.032.us)
380d53b4beeSSjoerd Meijer; CHECK:   %sub.us = sub nsw i32 %call.us, %x.128.us
381d53b4beeSSjoerd Meijer; CHECK:   %xor.us = xor i32 %sub.us, %x.128.us
382d53b4beeSSjoerd Meijer; CHECK:   %inc.us = add nuw nsw i32 %j.029.us, 1
383d53b4beeSSjoerd Meijer; CHECK:   %cmp6.us = icmp ult i32 %inc.us, %div5
384d53b4beeSSjoerd Meijer; CHECK:   br label %for.cond3.for.cond.cleanup8_crit_edge.us
385d53b4beeSSjoerd Meijer
386d53b4beeSSjoerd Meijerfor.cond3.for.cond.cleanup8_crit_edge.us:         ; preds = %for.body9.us
387d53b4beeSSjoerd Meijer  %xor.us.lcssa = phi i32 [ %xor.us, %for.body9.us ]
388d53b4beeSSjoerd Meijer  %inc13.us = add nuw nsw i32 %i.032.us, 1
389d53b4beeSSjoerd Meijer  %cmp.us = icmp ult i32 %inc13.us, %div
390d53b4beeSSjoerd Meijer  br i1 %cmp.us, label %for.body.us, label %for.cond.cleanup.loopexit
391d53b4beeSSjoerd Meijer; CHECK: for.cond3.for.cond.cleanup8_crit_edge.us:
392d53b4beeSSjoerd Meijer; CHECK:   %xor.us.lcssa = phi i32 [ %xor.us, %for.body9.us ]
393d53b4beeSSjoerd Meijer; CHECK:   %inc13.us = add nuw nsw i32 %i.032.us, 1
394d53b4beeSSjoerd Meijer; CHECK:   %cmp.us = icmp ult i32 %inc13.us, %flatten.tripcount
395d53b4beeSSjoerd Meijer; CHECK:   br i1 %cmp.us, label %for.body.us, label %for.cond.cleanup.loopexit
396d53b4beeSSjoerd Meijer
397d53b4beeSSjoerd Meijerfor.body.lr.ph.split:                             ; preds = %for.body.lr.ph
398d53b4beeSSjoerd Meijer  br label %for.body
399d53b4beeSSjoerd Meijer
400d53b4beeSSjoerd Meijerfor.cond.cleanup.loopexit:                        ; preds = %for.cond3.for.cond.cleanup8_crit_edge.us
401d53b4beeSSjoerd Meijer  %xor.us.lcssa.lcssa = phi i32 [ %xor.us.lcssa, %for.cond3.for.cond.cleanup8_crit_edge.us ]
402d53b4beeSSjoerd Meijer  br label %for.cond.cleanup
403d53b4beeSSjoerd Meijer
404d53b4beeSSjoerd Meijerfor.cond.cleanup.loopexit34:                      ; preds = %for.body
405d53b4beeSSjoerd Meijer  br label %for.cond.cleanup
406d53b4beeSSjoerd Meijer
407d53b4beeSSjoerd Meijerfor.cond.cleanup:                                 ; preds = %for.cond.cleanup.loopexit34, %for.cond.cleanup.loopexit, %entry
408d53b4beeSSjoerd Meijer  %x.0.lcssa = phi i32 [ 1, %entry ], [ %xor.us.lcssa.lcssa, %for.cond.cleanup.loopexit ], [ 1, %for.cond.cleanup.loopexit34 ]
409d53b4beeSSjoerd Meijer  ret i32 %x.0.lcssa
410d53b4beeSSjoerd Meijer
411d53b4beeSSjoerd Meijerfor.body:                                         ; preds = %for.body.lr.ph.split, %for.body
412d53b4beeSSjoerd Meijer  %i.032 = phi i32 [ 0, %for.body.lr.ph.split ], [ %inc13, %for.body ]
413d53b4beeSSjoerd Meijer  %inc13 = add nuw nsw i32 %i.032, 1
414d53b4beeSSjoerd Meijer  %cmp = icmp ult i32 %inc13, %div
415d53b4beeSSjoerd Meijer  br i1 %cmp, label %for.body, label %for.cond.cleanup.loopexit34
416d53b4beeSSjoerd Meijer}
417d53b4beeSSjoerd Meijer
418d53b4beeSSjoerd Meijer; CHECK-LABEL: test7
419d53b4beeSSjoerd Meijer; Various inner phis and conditions which we can still work with
420*055fb779SNikita Popovdefine signext i16 @test7(i32 %I, i32 %J, ptr nocapture readonly %C, i16 signext %limit) {
421d53b4beeSSjoerd Meijerentry:
422d53b4beeSSjoerd Meijer  %cmp43 = icmp eq i32 %J, 0
423d53b4beeSSjoerd Meijer  br i1 %cmp43, label %for.end17, label %for.body.lr.ph
424d53b4beeSSjoerd Meijer
425d53b4beeSSjoerd Meijerfor.body.lr.ph:                                   ; preds = %entry
426d53b4beeSSjoerd Meijer  %conv = sext i16 %limit to i32
427d53b4beeSSjoerd Meijer  br label %for.body.us
428d53b4beeSSjoerd Meijer; CHECK: for.body.lr.ph:
429d53b4beeSSjoerd Meijer; CHECK:   %conv = sext i16 %limit to i32
430d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 %J, %J
431d53b4beeSSjoerd Meijer; CHECK:   br label %for.body.us
432d53b4beeSSjoerd Meijer
433d53b4beeSSjoerd Meijerfor.body.us:                                      ; preds = %for.cond1.for.inc15_crit_edge.us, %for.body.lr.ph
434d53b4beeSSjoerd Meijer  %i.047.us = phi i32 [ 0, %for.body.lr.ph ], [ %inc16.us, %for.cond1.for.inc15_crit_edge.us ]
435d53b4beeSSjoerd Meijer  %ret.046.us = phi i16 [ 0, %for.body.lr.ph ], [ %ret.2.us.lcssa, %for.cond1.for.inc15_crit_edge.us ]
436d53b4beeSSjoerd Meijer  %prev.045.us = phi i32 [ 0, %for.body.lr.ph ], [ %.lcssa, %for.cond1.for.inc15_crit_edge.us ]
437d53b4beeSSjoerd Meijer  %tmp.044.us = phi i32 [ 0, %for.body.lr.ph ], [ %tmp.2.us.lcssa, %for.cond1.for.inc15_crit_edge.us ]
438d53b4beeSSjoerd Meijer  %mul.us = mul i32 %i.047.us, %J
439d53b4beeSSjoerd Meijer  br label %for.body3.us
440d53b4beeSSjoerd Meijer; CHECK: for.body.us:
441d53b4beeSSjoerd Meijer; CHECK:   %i.047.us = phi i32 [ 0, %for.body.lr.ph ], [ %inc16.us, %for.cond1.for.inc15_crit_edge.us ]
442d53b4beeSSjoerd Meijer; CHECK:   %ret.046.us = phi i16 [ 0, %for.body.lr.ph ], [ %ret.2.us.lcssa, %for.cond1.for.inc15_crit_edge.us ]
443d53b4beeSSjoerd Meijer; CHECK:   %prev.045.us = phi i32 [ 0, %for.body.lr.ph ], [ %.lcssa, %for.cond1.for.inc15_crit_edge.us ]
444d53b4beeSSjoerd Meijer; CHECK:   %tmp.044.us = phi i32 [ 0, %for.body.lr.ph ], [ %tmp.2.us.lcssa, %for.cond1.for.inc15_crit_edge.us ]
445d53b4beeSSjoerd Meijer; CHECK:   %mul.us = mul i32 %i.047.us, %J
446d53b4beeSSjoerd Meijer; CHECK:   br label %for.body3.us
447d53b4beeSSjoerd Meijer
448d53b4beeSSjoerd Meijerfor.body3.us:                                     ; preds = %for.body.us, %if.end.us
449d53b4beeSSjoerd Meijer  %j.040.us = phi i32 [ 0, %for.body.us ], [ %inc.us, %if.end.us ]
450d53b4beeSSjoerd Meijer  %ret.139.us = phi i16 [ %ret.046.us, %for.body.us ], [ %ret.2.us, %if.end.us ]
451d53b4beeSSjoerd Meijer  %prev.138.us = phi i32 [ %prev.045.us, %for.body.us ], [ %0, %if.end.us ]
452d53b4beeSSjoerd Meijer  %tmp.137.us = phi i32 [ %tmp.044.us, %for.body.us ], [ %tmp.2.us, %if.end.us ]
453d53b4beeSSjoerd Meijer  %add.us = add i32 %j.040.us, %mul.us
454*055fb779SNikita Popov  %arrayidx.us = getelementptr inbounds i32, ptr %C, i32 %add.us
455*055fb779SNikita Popov  %0 = load i32, ptr %arrayidx.us, align 4
456d53b4beeSSjoerd Meijer  %add4.us = add nsw i32 %0, %tmp.137.us
457d53b4beeSSjoerd Meijer  %cmp5.us = icmp sgt i32 %add4.us, %conv
458d53b4beeSSjoerd Meijer  br i1 %cmp5.us, label %if.then.us, label %if.else.us
459d53b4beeSSjoerd Meijer; CHECK: for.body3.us:
460d53b4beeSSjoerd Meijer; CHECK:   %j.040.us = phi i32 [ 0, %for.body.us ]
461d53b4beeSSjoerd Meijer; CHECK:   %ret.139.us = phi i16 [ %ret.046.us, %for.body.us ]
462d53b4beeSSjoerd Meijer; CHECK:   %prev.138.us = phi i32 [ %prev.045.us, %for.body.us ]
463d53b4beeSSjoerd Meijer; CHECK:   %tmp.137.us = phi i32 [ %tmp.044.us, %for.body.us ]
464d53b4beeSSjoerd Meijer; CHECK:   %add.us = add i32 %j.040.us, %mul.us
465*055fb779SNikita Popov; CHECK:   %arrayidx.us = getelementptr inbounds i32, ptr %C, i32 %i.047.us
466*055fb779SNikita Popov; CHECK:   %0 = load i32, ptr %arrayidx.us, align 4
467d53b4beeSSjoerd Meijer; CHECK:   %add4.us = add nsw i32 %0, %tmp.137.us
468d53b4beeSSjoerd Meijer; CHECK:   %cmp5.us = icmp sgt i32 %add4.us, %conv
469d53b4beeSSjoerd Meijer; CHECK:   br i1 %cmp5.us, label %if.then.us, label %if.else.us
470d53b4beeSSjoerd Meijer
471d53b4beeSSjoerd Meijerif.else.us:                                       ; preds = %for.body3.us
472d53b4beeSSjoerd Meijer  %cmp10.us = icmp sgt i32 %0, %prev.138.us
473d53b4beeSSjoerd Meijer  %cond.us = zext i1 %cmp10.us to i32
474d53b4beeSSjoerd Meijer  %conv1235.us = zext i16 %ret.139.us to i32
475d53b4beeSSjoerd Meijer  %add13.us = add nuw nsw i32 %cond.us, %conv1235.us
476d53b4beeSSjoerd Meijer  br label %if.end.us
477d53b4beeSSjoerd Meijer; CHECK: if.else.us:
478d53b4beeSSjoerd Meijer; CHECK:   %cmp10.us = icmp sgt i32 %0, %prev.138.us
479d53b4beeSSjoerd Meijer; CHECK:   %cond.us = zext i1 %cmp10.us to i32
480d53b4beeSSjoerd Meijer; CHECK:   %conv1235.us = zext i16 %ret.139.us to i32
481d53b4beeSSjoerd Meijer; CHECK:   %add13.us = add nuw nsw i32 %cond.us, %conv1235.us
482d53b4beeSSjoerd Meijer; CHECK:   br label %if.end.us
483d53b4beeSSjoerd Meijer
484d53b4beeSSjoerd Meijerif.then.us:                                       ; preds = %for.body3.us
485d53b4beeSSjoerd Meijer  %conv7.us = sext i16 %ret.139.us to i32
486d53b4beeSSjoerd Meijer  %add8.us = add nsw i32 %conv7.us, 10
487d53b4beeSSjoerd Meijer  br label %if.end.us
488d53b4beeSSjoerd Meijer; CHECK: if.then.us:
489d53b4beeSSjoerd Meijer; CHECK:   %conv7.us = sext i16 %ret.139.us to i32
490d53b4beeSSjoerd Meijer; CHECK:   %add8.us = add nsw i32 %conv7.us, 10
491d53b4beeSSjoerd Meijer; CHECK:   br label %if.end.us
492d53b4beeSSjoerd Meijer
493d53b4beeSSjoerd Meijerif.end.us:                                        ; preds = %if.then.us, %if.else.us
494d53b4beeSSjoerd Meijer  %tmp.2.us = phi i32 [ 0, %if.then.us ], [ %add4.us, %if.else.us ]
495d53b4beeSSjoerd Meijer  %ret.2.in.us = phi i32 [ %add8.us, %if.then.us ], [ %add13.us, %if.else.us ]
496d53b4beeSSjoerd Meijer  %ret.2.us = trunc i32 %ret.2.in.us to i16
497d53b4beeSSjoerd Meijer  %inc.us = add nuw i32 %j.040.us, 1
498d53b4beeSSjoerd Meijer  %exitcond = icmp ne i32 %inc.us, %J
499d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.body3.us, label %for.cond1.for.inc15_crit_edge.us
500d53b4beeSSjoerd Meijer; CHECK: if.end.us:
501d53b4beeSSjoerd Meijer; CHECK:   %tmp.2.us = phi i32 [ 0, %if.then.us ], [ %add4.us, %if.else.us ]
502d53b4beeSSjoerd Meijer; CHECK:   %ret.2.in.us = phi i32 [ %add8.us, %if.then.us ], [ %add13.us, %if.else.us ]
503d53b4beeSSjoerd Meijer; CHECK:   %ret.2.us = trunc i32 %ret.2.in.us to i16
504d53b4beeSSjoerd Meijer; CHECK:   %inc.us = add nuw i32 %j.040.us, 1
505d53b4beeSSjoerd Meijer; CHECK:   %exitcond = icmp ne i32 %inc.us, %J
506d53b4beeSSjoerd Meijer; CHECK:   br label %for.cond1.for.inc15_crit_edge.us
507d53b4beeSSjoerd Meijer
508d53b4beeSSjoerd Meijerfor.cond1.for.inc15_crit_edge.us:                 ; preds = %if.end.us
509d53b4beeSSjoerd Meijer  %tmp.2.us.lcssa = phi i32 [ %tmp.2.us, %if.end.us ]
510d53b4beeSSjoerd Meijer  %ret.2.us.lcssa = phi i16 [ %ret.2.us, %if.end.us ]
511d53b4beeSSjoerd Meijer  %.lcssa = phi i32 [ %0, %if.end.us ]
512d53b4beeSSjoerd Meijer  %inc16.us = add nuw i32 %i.047.us, 1
513d53b4beeSSjoerd Meijer  %exitcond49 = icmp ne i32 %inc16.us, %J
514d53b4beeSSjoerd Meijer  br i1 %exitcond49, label %for.body.us, label %for.end17.loopexit
515d53b4beeSSjoerd Meijer; CHECK: for.cond1.for.inc15_crit_edge.us:
516d53b4beeSSjoerd Meijer; CHECK:   %tmp.2.us.lcssa = phi i32 [ %tmp.2.us, %if.end.us ]
517d53b4beeSSjoerd Meijer; CHECK:   %ret.2.us.lcssa = phi i16 [ %ret.2.us, %if.end.us ]
518d53b4beeSSjoerd Meijer; CHECK:   %.lcssa = phi i32 [ %0, %if.end.us ]
519d53b4beeSSjoerd Meijer; CHECK:   %inc16.us = add nuw i32 %i.047.us, 1
520d53b4beeSSjoerd Meijer; CHECK:   %exitcond49 = icmp ne i32 %inc16.us, %flatten.tripcount
521d53b4beeSSjoerd Meijer; CHECK:   br i1 %exitcond49, label %for.body.us, label %for.end17.loopexit
522d53b4beeSSjoerd Meijer
523d53b4beeSSjoerd Meijerfor.end17.loopexit:                               ; preds = %for.cond1.for.inc15_crit_edge.us
524d53b4beeSSjoerd Meijer  %ret.2.us.lcssa.lcssa = phi i16 [ %ret.2.us.lcssa, %for.cond1.for.inc15_crit_edge.us ]
525d53b4beeSSjoerd Meijer  br label %for.end17
526d53b4beeSSjoerd Meijer
527d53b4beeSSjoerd Meijerfor.end17:                                        ; preds = %for.end17.loopexit, %entry
528d53b4beeSSjoerd Meijer  %ret.0.lcssa = phi i16 [ 0, %entry ], [ %ret.2.us.lcssa.lcssa, %for.end17.loopexit ]
529d53b4beeSSjoerd Meijer  ret i16 %ret.0.lcssa
530d53b4beeSSjoerd Meijer}
531d53b4beeSSjoerd Meijer
532d53b4beeSSjoerd Meijer; CHECK-LABEL: test8
533d53b4beeSSjoerd Meijer; Same as test1, but with different continue block order
534d53b4beeSSjoerd Meijer; (uses icmp eq and loops on false)
535*055fb779SNikita Popovdefine i32 @test8(i32 %val, ptr nocapture %A) {
536d53b4beeSSjoerd Meijerentry:
537d53b4beeSSjoerd Meijer  br label %for.body
538d53b4beeSSjoerd Meijer; CHECK: entry:
539d53b4beeSSjoerd Meijer; CHECK:   %flatten.tripcount = mul i32 20, 10
540d53b4beeSSjoerd Meijer; CHECK:   br label %for.body
541d53b4beeSSjoerd Meijer
542d53b4beeSSjoerd Meijerfor.body:                                         ; preds = %entry, %for.inc6
543d53b4beeSSjoerd Meijer  %i.018 = phi i32 [ 0, %entry ], [ %inc7, %for.inc6 ]
544d53b4beeSSjoerd Meijer  %mul = mul nuw nsw i32 %i.018, 20
545d53b4beeSSjoerd Meijer  br label %for.body3
546d53b4beeSSjoerd Meijer; CHECK: for.body:
547d53b4beeSSjoerd Meijer; CHECK:   %i.018 = phi i32 [ 0, %entry ], [ %inc7, %for.inc6 ]
548d53b4beeSSjoerd Meijer; CHECK:   %mul = mul nuw nsw i32 %i.018, 20
549d53b4beeSSjoerd Meijer; CHECK:   br label %for.body3
550d53b4beeSSjoerd Meijer
551d53b4beeSSjoerd Meijerfor.body3:                                        ; preds = %for.body, %for.body3
552d53b4beeSSjoerd Meijer  %j.017 = phi i32 [ 0, %for.body ], [ %inc, %for.body3 ]
553d53b4beeSSjoerd Meijer  %add = add nuw nsw i32 %j.017, %mul
554*055fb779SNikita Popov  %arrayidx = getelementptr inbounds i16, ptr %A, i32 %add
555*055fb779SNikita Popov  %0 = load i16, ptr %arrayidx, align 2
556d53b4beeSSjoerd Meijer  %conv16 = zext i16 %0 to i32
557d53b4beeSSjoerd Meijer  %add4 = add i32 %conv16, %val
558d53b4beeSSjoerd Meijer  %conv5 = trunc i32 %add4 to i16
559*055fb779SNikita Popov  store i16 %conv5, ptr %arrayidx, align 2
560d53b4beeSSjoerd Meijer  %inc = add nuw nsw i32 %j.017, 1
561d53b4beeSSjoerd Meijer  %exitcond = icmp eq i32 %inc, 20
562d53b4beeSSjoerd Meijer  br i1 %exitcond, label %for.inc6, label %for.body3
563d53b4beeSSjoerd Meijer; CHECK: for.body3:
564d53b4beeSSjoerd Meijer; CHECK:   %j.017 = phi i32 [ 0, %for.body ]
565d53b4beeSSjoerd Meijer; CHECK:   %add = add nuw nsw i32 %j.017, %mul
566*055fb779SNikita Popov; CHECK:   %arrayidx = getelementptr inbounds i16, ptr %A, i32 %i.018
567*055fb779SNikita Popov; CHECK:   %0 = load i16, ptr %arrayidx, align 2
568d53b4beeSSjoerd Meijer; CHECK:   %conv16 = zext i16 %0 to i32
569d53b4beeSSjoerd Meijer; CHECK:   %add4 = add i32 %conv16, %val
570d53b4beeSSjoerd Meijer; CHECK:   %conv5 = trunc i32 %add4 to i16
571*055fb779SNikita Popov; CHECK:   store i16 %conv5, ptr %arrayidx, align 2
572d53b4beeSSjoerd Meijer; CHECK:   %inc = add nuw nsw i32 %j.017, 1
573d53b4beeSSjoerd Meijer; CHECK:   %exitcond = icmp eq i32 %inc, 20
574d53b4beeSSjoerd Meijer; CHECK:   br label %for.inc6
575d53b4beeSSjoerd Meijer
576d53b4beeSSjoerd Meijerfor.inc6:                                         ; preds = %for.body3
577d53b4beeSSjoerd Meijer  %inc7 = add nuw nsw i32 %i.018, 1
578d53b4beeSSjoerd Meijer  %exitcond19 = icmp eq i32 %inc7, 10
579d53b4beeSSjoerd Meijer  br i1 %exitcond19, label %for.end8, label %for.body
580d53b4beeSSjoerd Meijer; CHECK: for.inc6:
581d53b4beeSSjoerd Meijer; CHECK:   %inc7 = add nuw nsw i32 %i.018, 1
582d53b4beeSSjoerd Meijer; CHECK:   %exitcond19 = icmp eq i32 %inc7, %flatten.tripcount
583d53b4beeSSjoerd Meijer; CHECK:   br i1 %exitcond19, label %for.end8, label %for.body
584d53b4beeSSjoerd Meijer
585d53b4beeSSjoerd Meijerfor.end8:                                         ; preds = %for.inc6
586d53b4beeSSjoerd Meijer  ret i32 10
587d53b4beeSSjoerd Meijer}
588d53b4beeSSjoerd Meijer
589f117ed54SRosie Sumpter; When the inner loop trip count is a constant and the step
590f117ed54SRosie Sumpter; is 1, the InstCombine pass causes the transformation e.g.
591f117ed54SRosie Sumpter; icmp ult i32 %inc, 20 -> icmp ult i32 %j, 19. This doesn't
592f117ed54SRosie Sumpter; match the pattern (OuterPHI * InnerTripCount) + InnerPHI but
593f117ed54SRosie Sumpter; we should still flatten the loop as the compare is removed
594f117ed54SRosie Sumpter; later anyway.
595*055fb779SNikita Popovdefine i32 @test9(ptr nocapture %A) {
596f117ed54SRosie Sumpterentry:
597f117ed54SRosie Sumpter  br label %for.cond1.preheader
598f117ed54SRosie Sumpter; CHECK-LABEL: test9
599f117ed54SRosie Sumpter; CHECK: entry:
600f117ed54SRosie Sumpter; CHECK: %flatten.tripcount = mul i32 20, 11
601f117ed54SRosie Sumpter; CHECK: br label %for.cond1.preheader
602f117ed54SRosie Sumpter
603f117ed54SRosie Sumpterfor.cond1.preheader:
604f117ed54SRosie Sumpter  %i.017 = phi i32 [ 0, %entry ], [ %inc6, %for.cond.cleanup3 ]
605f117ed54SRosie Sumpter  %mul = mul i32 %i.017, 20
606f117ed54SRosie Sumpter  br label %for.body4
607f117ed54SRosie Sumpter; CHECK: for.cond1.preheader:
608f117ed54SRosie Sumpter; CHECK:   %i.017 = phi i32 [ 0, %entry ], [ %inc6, %for.cond.cleanup3 ]
609f117ed54SRosie Sumpter; CHECK:   %mul = mul i32 %i.017, 20
610f117ed54SRosie Sumpter; CHECK:   br label %for.body4
611f117ed54SRosie Sumpter
612f117ed54SRosie Sumpterfor.cond.cleanup3:
613f117ed54SRosie Sumpter  %inc6 = add i32 %i.017, 1
614f117ed54SRosie Sumpter  %cmp = icmp ult i32 %inc6, 11
615f117ed54SRosie Sumpter  br i1 %cmp, label %for.cond1.preheader, label %for.cond.cleanup
616f117ed54SRosie Sumpter; CHECK: for.cond.cleanup3:
617f117ed54SRosie Sumpter; CHECK:   %inc6 = add i32 %i.017, 1
618f117ed54SRosie Sumpter; CHECK:   %cmp = icmp ult i32 %inc6, %flatten.tripcount
619f117ed54SRosie Sumpter; CHECK:   br i1 %cmp, label %for.cond1.preheader, label %for.cond.cleanup
620f117ed54SRosie Sumpter
621f117ed54SRosie Sumpterfor.body4:
622f117ed54SRosie Sumpter  %j.016 = phi i32 [ 0, %for.cond1.preheader ], [ %inc, %for.body4 ]
623f117ed54SRosie Sumpter  %add = add i32 %j.016, %mul
624*055fb779SNikita Popov  %arrayidx = getelementptr inbounds i32, ptr %A, i32 %add
625*055fb779SNikita Popov  store i32 30, ptr %arrayidx, align 4
626f117ed54SRosie Sumpter  %inc = add nuw nsw i32 %j.016, 1
627f117ed54SRosie Sumpter  %cmp2 = icmp ult i32 %j.016, 19
628f117ed54SRosie Sumpter  br i1 %cmp2, label %for.body4, label %for.cond.cleanup3
629f117ed54SRosie Sumpter; CHECK: for.body4
630f117ed54SRosie Sumpter; CHECK:   %j.016 = phi i32 [ 0, %for.cond1.preheader ]
631f117ed54SRosie Sumpter; CHECK:   %add = add i32 %j.016, %mul
632*055fb779SNikita Popov; CHECK:   %arrayidx = getelementptr inbounds i32, ptr %A, i32 %i.017
633*055fb779SNikita Popov; CHECK:   store i32 30, ptr %arrayidx, align 4
634f117ed54SRosie Sumpter; CHECK:   %inc = add nuw nsw i32 %j.016, 1
635f117ed54SRosie Sumpter; CHECK:   %cmp2 = icmp ult i32 %j.016, 19
636f117ed54SRosie Sumpter; CHECK:   br label %for.cond.cleanup3
637f117ed54SRosie Sumpter
638f117ed54SRosie Sumpterfor.cond.cleanup:
639*055fb779SNikita Popov  %0 = load i32, ptr %A, align 4
640f117ed54SRosie Sumpter  ret i32 %0
641f117ed54SRosie Sumpter}
642d53b4beeSSjoerd Meijer
643d53b4beeSSjoerd Meijerdeclare i32 @func(i32)
644d53b4beeSSjoerd Meijer
645