3 ; RUN: opt -passes=loop-vectorize -force-vector-width=4 -force-vector-interleave=1 -debug-only=loop-vectorize -disable-output -S %s 2>&1 | FileCheck %s
5 define void @test_chained_first_order_recurrences_1(ptr %ptr) {
6 ; CHECK-LABEL: 'test_chained_first_order_recurrences_1'
7 ; CHECK: VPlan 'Initial VPlan for VF={4},UF>=1' {
8 ; CHECK-NEXT: Live-in vp<[[VFxUF:%.+]]> = VF * UF
9 ; CHECK-NEXT: Live-in vp<[[VTC:%.+]]> = vector-trip-count
10 ; CHECK-NEXT: Live-in ir<1000> = original trip-count
12 ; CHECK-NEXT: ir-bb<entry>:
13 ; CHECK-NEXT: Successor(s): vector.ph
15 ; CHECK-NEXT: vector.ph:
16 ; CHECK-NEXT: Successor(s): vector loop
18 ; CHECK-NEXT: <x1> vector loop: {
19 ; CHECK-NEXT: vector.body:
20 ; CHECK-NEXT: EMIT vp<[[CAN_IV:%.+]]> = CANONICAL-INDUCTION
21 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.1> = phi ir<22>, ir<%for.1.next>
22 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.2> = phi ir<33>, vp<[[FOR1_SPLICE:%.+]]>
23 ; CHECK-NEXT: vp<[[STEPS:%.+]]> = SCALAR-STEPS vp<[[CAN_IV]]>, ir<1>
24 ; CHECK-NEXT: CLONE ir<%gep.ptr> = getelementptr inbounds ir<%ptr>, vp<[[STEPS]]>
25 ; CHECK-NEXT: vp<[[VEC_PTR:%.+]]> = vector-pointer ir<%gep.ptr>
26 ; CHECK-NEXT: WIDEN ir<%for.1.next> = load vp<[[VEC_PTR]]>
27 ; CHECK-NEXT: EMIT vp<[[FOR1_SPLICE]]> = first-order splice ir<%for.1>, ir<%for.1.next>
28 ; CHECK-NEXT: EMIT vp<[[FOR2_SPLICE:%.+]]> = first-order splice ir<%for.2>, vp<[[FOR1_SPLICE]]>
29 ; CHECK-NEXT: WIDEN ir<%add> = add vp<[[FOR1_SPLICE]]>, vp<[[FOR2_SPLICE]]>
30 ; CHECK-NEXT: vp<[[VEC_PTR2:%.+]]> = vector-pointer ir<%gep.ptr>
31 ; CHECK-NEXT: WIDEN store vp<[[VEC_PTR2]]>, ir<%add>
32 ; CHECK-NEXT: EMIT vp<[[CAN_IV_NEXT:%.+]]> = add nuw vp<[[CAN_IV]]>, vp<[[VFxUF]]>
33 ; CHECK-NEXT: EMIT branch-on-count vp<[[CAN_IV_NEXT]]>, vp<[[VTC]]>
34 ; CHECK-NEXT: No successors
36 ; CHECK-NEXT: Successor(s): middle.block
38 ; CHECK-NEXT: middle.block:
39 ; CHECK-NEXT: EMIT vp<[[RESUME_1:%.+]]> = extract-from-end ir<%for.1.next>, ir<1>
40 ; CHECK-NEXT: EMIT vp<[[RESUME_2:%.+]]>.1 = extract-from-end vp<[[FOR1_SPLICE]]>, ir<1>
41 ; CHECK-NEXT: EMIT vp<[[CMP:%.+]]> = icmp eq ir<1000>, vp<[[VTC]]>
42 ; CHECK-NEXT: EMIT branch-on-cond vp<[[CMP]]>
43 ; CHECK-NEXT: Successor(s): ir-bb<exit>, scalar.ph
45 ; CHECK-NEXT: scalar.ph
46 ; CHECK-NEXT: EMIT vp<[[RESUME_1_P:%.*]]> = resume-phi vp<[[RESUME_1]]>, ir<22>
47 ; CHECK-NEXT: EMIT vp<[[RESUME_2_P:%.*]]>.1 = resume-phi vp<[[RESUME_2]]>.1, ir<33>
48 ; CHECK-NEXT: EMIT vp<[[RESUME_IV:%.*]]> = resume-phi vp<[[VTC]]>, ir<0>
49 ; CHECK-NEXT: Successor(s): ir-bb<loop>
51 ; CHECK-NEXT: ir-bb<loop>:
52 ; CHECK-NEXT: IR %for.1 = phi i16 [ 22, %entry ], [ %for.1.next, %loop ] (extra operand: vp<[[RESUME_1_P]]> from scalar.ph)
53 ; CHECK-NEXT: IR %for.2 = phi i16 [ 33, %entry ], [ %for.1, %loop ] (extra operand: vp<[[RESUME_2_P]]>.1 from scalar.ph)
54 ; CHECK-NEXT: IR %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] (extra operand: vp<[[RESUME_IV]]> from scalar.ph)
55 ; CHECK: IR %exitcond.not = icmp eq i64 %iv.next, 1000
56 ; CHECK-NEXT: No successors
58 ; CHECK-NEXT: ir-bb<exit>
59 ; CHECK-NEXT: No successors
66 %for.1 = phi i16 [ 22, %entry ], [ %for.1.next, %loop ]
67 %for.2 = phi i16 [ 33, %entry ], [ %for.1, %loop ]
68 %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ]
69 %iv.next = add nuw nsw i64 %iv, 1
70 %gep.ptr = getelementptr inbounds i16, ptr %ptr, i64 %iv
71 %for.1.next = load i16, ptr %gep.ptr, align 2
72 %add = add i16 %for.1, %for.2
73 store i16 %add, ptr %gep.ptr
74 %exitcond.not = icmp eq i64 %iv.next, 1000
75 br i1 %exitcond.not, label %exit, label %loop
81 define void @test_chained_first_order_recurrences_3(ptr %ptr) {
82 ; CHECK-LABEL: 'test_chained_first_order_recurrences_3'
83 ; CHECK: VPlan 'Initial VPlan for VF={4},UF>=1' {
84 ; CHECK-NEXT: Live-in vp<[[VFxUF:%.+]]> = VF * UF
85 ; CHECK-NEXT: Live-in vp<[[VTC:%.+]]> = vector-trip-count
86 ; CHECK-NEXT: Live-in ir<1000> = original trip-count
88 ; CHECK-NEXT: ir-bb<entry>:
89 ; CHECK-NEXT: Successor(s): vector.ph
91 ; CHECK-NEXT: vector.ph:
92 ; CHECK-NEXT: Successor(s): vector loop
94 ; CHECK-NEXT: <x1> vector loop: {
95 ; CHECK-NEXT: vector.body:
96 ; CHECK-NEXT: EMIT vp<[[CAN_IV:%.+]]> = CANONICAL-INDUCTION
97 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.1> = phi ir<22>, ir<%for.1.next>
98 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.2> = phi ir<33>, vp<[[FOR1_SPLICE:%.+]]>
99 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.3> = phi ir<33>, vp<[[FOR2_SPLICE:%.+]]>
100 ; CHECK-NEXT: vp<[[STEPS:%.+]]> = SCALAR-STEPS vp<[[CAN_IV]]>, ir<1>
101 ; CHECK-NEXT: CLONE ir<%gep.ptr> = getelementptr inbounds ir<%ptr>, vp<[[STEPS]]>
102 ; CHECK-NEXT: vp<[[VEC_PTR:%.+]]> = vector-pointer ir<%gep.ptr>
103 ; CHECK-NEXT: WIDEN ir<%for.1.next> = load vp<[[VEC_PTR]]>
104 ; CHECK-NEXT: EMIT vp<[[FOR1_SPLICE]]> = first-order splice ir<%for.1>, ir<%for.1.next>
105 ; CHECK-NEXT: EMIT vp<[[FOR2_SPLICE]]> = first-order splice ir<%for.2>, vp<[[FOR1_SPLICE]]>
106 ; CHECK-NEXT: EMIT vp<[[FOR3_SPLICE:%.+]]> = first-order splice ir<%for.3>, vp<[[FOR2_SPLICE]]>
107 ; CHECK-NEXT: WIDEN ir<%add.1> = add vp<[[FOR1_SPLICE]]>, vp<[[FOR2_SPLICE]]>
108 ; CHECK-NEXT: WIDEN ir<%add.2> = add ir<%add.1>, vp<[[FOR3_SPLICE]]>
109 ; CHECK-NEXT: vp<[[VEC_PTR2:%.+]]> = vector-pointer ir<%gep.ptr>
110 ; CHECK-NEXT: WIDEN store vp<[[VEC_PTR2]]>, ir<%add.2>
111 ; CHECK-NEXT: EMIT vp<[[CAN_IV_NEXT:%.+]]> = add nuw vp<[[CAN_IV]]>, vp<[[VFxUF]]>
112 ; CHECK-NEXT: EMIT branch-on-count vp<[[CAN_IV_NEXT]]>, vp<[[VTC]]>
113 ; CHECK-NEXT: No successors
115 ; CHECK-NEXT: Successor(s): middle.block
117 ; CHECK-NEXT: middle.block:
118 ; CHECK-NEXT: EMIT vp<[[RESUME_1:%.+]]> = extract-from-end ir<%for.1.next>, ir<1>
119 ; CHECK-NEXT: EMIT vp<[[RESUME_2:%.+]]>.1 = extract-from-end vp<[[FOR1_SPLICE]]>, ir<1>
120 ; CHECK-NEXT: EMIT vp<[[RESUME_3:%.+]]>.2 = extract-from-end vp<[[FOR2_SPLICE]]>, ir<1>
121 ; CHECK-NEXT: EMIT vp<[[CMP:%.+]]> = icmp eq ir<1000>, vp<[[VTC]]>
122 ; CHECK-NEXT: EMIT branch-on-cond vp<[[CMP]]>
123 ; CHECK-NEXT: Successor(s): ir-bb<exit>, scalar.ph
125 ; CHECK-NEXT: scalar.ph
126 ; CHECK-NEXT: EMIT vp<[[RESUME_1_P:%.*]]> = resume-phi vp<[[RESUME_1]]>, ir<22>
127 ; CHECK-NEXT: EMIT vp<[[RESUME_2_P:%.*]]>.1 = resume-phi vp<[[RESUME_2]]>.1, ir<33>
128 ; CHECK-NEXT: EMIT vp<[[RESUME_3_P:%.*]]>.2 = resume-phi vp<[[RESUME_3]]>.2, ir<33>
129 ; CHECK-NEXT: EMIT vp<[[RESUME_IV:%.*]]> = resume-phi vp<[[VTC]]>, ir<0>
130 ; CHECK-NEXT: Successor(s): ir-bb<loop>
132 ; CHECK-NEXT: ir-bb<loop>:
133 ; CHECK-NEXT: IR %for.1 = phi i16 [ 22, %entry ], [ %for.1.next, %loop ] (extra operand: vp<[[RESUME_1_P]]> from scalar.ph)
134 ; CHECK-NEXT: IR %for.2 = phi i16 [ 33, %entry ], [ %for.1, %loop ] (extra operand: vp<[[RESUME_2_P]]>.1 from scalar.ph)
135 ; CHECK-NEXT: IR %for.3 = phi i16 [ 33, %entry ], [ %for.2, %loop ] (extra operand: vp<[[RESUME_3_P]]>.2 from scalar.ph)
136 ; CHECK-NEXT: IR %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ] (extra operand: vp<[[RESUME_IV]]> from scalar.ph)
137 ; CHECK: IR %exitcond.not = icmp eq i64 %iv.next, 1000
138 ; CHECK-NEXT: No successors
140 ; CHECK-NEXT: ir-bb<exit>
141 ; CHECK-NEXT: No successors
148 %for.1 = phi i16 [ 22, %entry ], [ %for.1.next, %loop ]
149 %for.2 = phi i16 [ 33, %entry ], [ %for.1, %loop ]
150 %for.3 = phi i16 [ 33, %entry ], [ %for.2, %loop ]
151 %iv = phi i64 [ 0, %entry ], [ %iv.next, %loop ]
152 %iv.next = add nuw nsw i64 %iv, 1
153 %gep.ptr = getelementptr inbounds i16, ptr %ptr, i64 %iv
154 %for.1.next = load i16, ptr %gep.ptr, align 2
155 %add.1 = add i16 %for.1, %for.2
156 %add.2 = add i16 %add.1, %for.3
157 store i16 %add.2, ptr %gep.ptr
158 %exitcond.not = icmp eq i64 %iv.next, 1000
159 br i1 %exitcond.not, label %exit, label %loop
165 ; This test has two FORs (for.x and for.y) where incoming value from the previous
166 ; iteration (for.x.prev) of one FOR (for.y) depends on another FOR (for.x).
167 ; Sinking would require moving a recipe with side effects (store). Instead,
168 ; for.x.next can be hoisted.
169 define i32 @test_chained_first_order_recurrences_4(ptr %base, i64 %x) {
170 ; CHECK-LABEL: 'test_chained_first_order_recurrences_4'
171 ; CHECK: VPlan 'Initial VPlan for VF={4},UF>=1' {
172 ; CHECK-NEXT: Live-in vp<[[VFxUF:%.+]]> = VF * UF
173 ; CHECK-NEXT: Live-in vp<[[VTC:%.+]]> = vector-trip-count
174 ; CHECK-NEXT: Live-in ir<4098> = original trip-count
176 ; CHECK-NEXT: ir-bb<entry>:
177 ; CHECK-NEXT: Successor(s): vector.ph
179 ; CHECK-NEXT: vector.ph:
180 ; CHECK-NEXT: WIDEN ir<%for.x.next> = mul ir<%x>, ir<2>
181 ; CHECK-NEXT: Successor(s): vector loop
183 ; CHECK-NEXT: <x1> vector loop: {
184 ; CHECK-NEXT: vector.body:
185 ; CHECK-NEXT: EMIT vp<[[CAN_IV:%.+]]> = CANONICAL-INDUCTION ir<0>, vp<[[CAN_IV_NEXT:%.+]]>
186 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.x> = phi ir<0>, ir<%for.x.next>
187 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.y> = phi ir<0>, ir<%for.x.prev>
188 ; CHECK-NEXT: vp<[[SCALAR_STEPS:%.+]]> = SCALAR-STEPS vp<[[CAN_IV]]>, ir<1>
189 ; CHECK-NEXT: CLONE ir<%gep> = getelementptr ir<%base>, vp<[[SCALAR_STEPS]]>
190 ; CHECK-NEXT: EMIT vp<[[SPLICE_X:%.]]> = first-order splice ir<%for.x>, ir<%for.x.next>
191 ; CHECK-NEXT: WIDEN-CAST ir<%for.x.prev> = trunc vp<[[SPLICE_X]]> to i32
192 ; CHECK-NEXT: EMIT vp<[[SPLICE_Y:%.+]]> = first-order splice ir<%for.y>, ir<%for.x.prev>
193 ; CHECK-NEXT: WIDEN-CAST ir<%for.y.i64> = sext vp<[[SPLICE_Y]]> to i64
194 ; CHECK-NEXT: vp<[[VEC_PTR:%.+]]> = vector-pointer ir<%gep>
195 ; CHECK-NEXT: WIDEN store vp<[[VEC_PTR]]>, ir<%for.y.i64>
196 ; CHECK-NEXT: EMIT vp<[[CAN_IV_NEXT]]> = add nuw vp<[[CAN_IV]]>, vp<[[VFxUF]]>
197 ; CHECK-NEXT: EMIT branch-on-count vp<[[CAN_IV_NEXT]]>, vp<[[VTC]]>
198 ; CHECK-NEXT: No successors
200 ; CHECK-NEXT: Successor(s): middle.block
202 ; CHECK-NEXT: middle.block:
203 ; CHECK-NEXT: EMIT vp<[[EXT_X:%.+]]> = extract-from-end ir<%for.x.next>, ir<1>
204 ; CHECK-NEXT: EMIT vp<[[EXT_Y:%.+]]>.1 = extract-from-end ir<%for.x.prev>, ir<1>
205 ; CHECK-NEXT: EMIT vp<[[MIDDLE_C:%.+]]> = icmp eq ir<4098>, vp<[[VTC]]>
206 ; CHECK-NEXT: EMIT branch-on-cond vp<[[MIDDLE_C]]>
207 ; CHECK-NEXT: Successor(s): ir-bb<ret>, scalar.ph
209 ; CHECK-NEXT: scalar.ph:
210 ; CHECK-NEXT: EMIT vp<[[RESUME_IV:%.*]]> = resume-phi vp<[[VTC]]>, ir<0>
211 ; CHECK-NEXT: EMIT vp<[[RESUME_X:%.+]]> = resume-phi vp<[[EXT_X]]>, ir<0>
212 ; CHECK-NEXT: EMIT vp<[[RESUME_Y:%.+]]>.1 = resume-phi vp<[[EXT_Y]]>.1, ir<0>
213 ; CHECK-NEXT: Successor(s): ir-bb<loop>
215 ; CHECK-NEXT: ir-bb<loop>:
216 ; CHECK-NEXT: IR %iv = phi i64 [ %iv.next, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_IV]]> from scalar.ph)
217 ; CHECK-NEXT: IR %for.x = phi i64 [ %for.x.next, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_X]]> from scalar.ph)
218 ; CHECK-NEXT: IR %for.y = phi i32 [ %for.x.prev, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_Y]]>.1 from scalar.ph)
219 ; CHECK: No successors
221 ; CHECK-NEXT: ir-bb<ret>:
222 ; CHECK-NEXT: No successors
229 %iv = phi i64 [ %iv.next, %loop ], [ 0, %entry ]
230 %for.x = phi i64 [ %for.x.next, %loop ], [ 0, %entry ]
231 %for.y = phi i32 [ %for.x.prev, %loop ], [ 0, %entry ]
232 %iv.next = add i64 %iv, 1
233 %gep = getelementptr i64, ptr %base, i64 %iv
234 %for.x.prev = trunc i64 %for.x to i32
235 %for.y.i64 = sext i32 %for.y to i64
236 store i64 %for.y.i64, ptr %gep
237 %for.x.next = mul i64 %x, 2
238 %icmp = icmp ugt i64 %iv, 4096
239 br i1 %icmp, label %ret, label %loop
245 define i32 @test_chained_first_order_recurrences_5_hoist_to_load(ptr %base) {
246 ; CHECK-LABEL: 'test_chained_first_order_recurrences_5_hoist_to_load'
247 ; CHECK: VPlan 'Initial VPlan for VF={4},UF>=1' {
248 ; CHECK-NEXT: Live-in vp<[[VFxUF:%.+]]> = VF * UF
249 ; CHECK-NEXT: Live-in vp<[[VTC:%.+]]> = vector-trip-count
250 ; CHECK-NEXT: Live-in ir<4098> = original trip-count
252 ; CHECK-NEXT: ir-bb<entry>:
253 ; CHECK-NEXT: Successor(s): vector.ph
255 ; CHECK-NEXT: vector.ph:
256 ; CHECK-NEXT: Successor(s): vector loop
258 ; CHECK-NEXT: <x1> vector loop: {
259 ; CHECK-NEXT: vector.body:
260 ; CHECK-NEXT: EMIT vp<[[CAN_IV:%.+]]> = CANONICAL-INDUCTION ir<0>, vp<[[CAN_IV_NEXT:%.+]]>
261 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.x> = phi ir<0>, ir<%for.x.next>
262 ; CHECK-NEXT: FIRST-ORDER-RECURRENCE-PHI ir<%for.y> = phi ir<0>, ir<%for.x.prev>
263 ; CHECK-NEXT: vp<[[SCALAR_STEPS:%.+]]> = SCALAR-STEPS vp<[[CAN_IV]]>, ir<1>
264 ; CHECK-NEXT: CLONE ir<%gep> = getelementptr ir<%base>, vp<[[SCALAR_STEPS]]>
265 ; CHECK-NEXT: vp<[[VEC_PTR:%.+]]> = vector-pointer ir<%gep>
266 ; CHECK-NEXT: WIDEN ir<%l> = load vp<[[VEC_PTR]]>
267 ; CHECK-NEXT: WIDEN ir<%for.x.next> = mul ir<%l>, ir<2>
268 ; CHECK-NEXT: EMIT vp<[[SPLICE_X:%.]]> = first-order splice ir<%for.x>, ir<%for.x.next>
269 ; CHECK-NEXT: WIDEN-CAST ir<%for.x.prev> = trunc vp<[[SPLICE_X]]> to i32
270 ; CHECK-NEXT: EMIT vp<[[SPLICE_Y:%.+]]> = first-order splice ir<%for.y>, ir<%for.x.prev>
271 ; CHECK-NEXT: WIDEN-CAST ir<%for.y.i64> = sext vp<[[SPLICE_Y]]> to i64
272 ; CHECK-NEXT: vp<[[VEC_PTR:%.+]]> = vector-pointer ir<%gep>
273 ; CHECK-NEXT: WIDEN store vp<[[VEC_PTR]]>, ir<%for.y.i64>
274 ; CHECK-NEXT: EMIT vp<[[CAN_IV_NEXT]]> = add nuw vp<[[CAN_IV]]>, vp<[[VFxUF]]>
275 ; CHECK-NEXT: EMIT branch-on-count vp<[[CAN_IV_NEXT]]>, vp<[[VTC]]>
276 ; CHECK-NEXT: No successors
278 ; CHECK-NEXT: Successor(s): middle.block
280 ; CHECK-NEXT: middle.block:
281 ; CHECK-NEXT: EMIT vp<[[EXT_X:%.+]]> = extract-from-end ir<%for.x.next>, ir<1>
282 ; CHECK-NEXT: EMIT vp<[[EXT_Y:%.+]]>.1 = extract-from-end ir<%for.x.prev>, ir<1>
283 ; CHECK-NEXT: EMIT vp<[[MIDDLE_C:%.+]]> = icmp eq ir<4098>, vp<[[VTC]]>
284 ; CHECK-NEXT: EMIT branch-on-cond vp<[[MIDDLE_C]]>
285 ; CHECK-NEXT: Successor(s): ir-bb<ret>, scalar.ph
287 ; CHECK-NEXT: scalar.ph:
288 ; CHECK-NEXT: EMIT vp<[[RESUME_IV:%.*]]> = resume-phi vp<[[VTC]]>, ir<0>
289 ; CHECK-NEXT: EMIT vp<[[RESUME_X:%.+]]> = resume-phi vp<[[EXT_X]]>, ir<0>
290 ; CHECK-NEXT: EMIT vp<[[RESUME_Y:%.+]]>.1 = resume-phi vp<[[EXT_Y]]>.1, ir<0>
291 ; CHECK-NEXT: Successor(s): ir-bb<loop>
293 ; CHECK-NEXT: ir-bb<loop>:
294 ; CHECK-NEXT: IR %iv = phi i64 [ %iv.next, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_IV]]> from scalar.ph)
295 ; CHECK-NEXT: IR %for.x = phi i64 [ %for.x.next, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_X]]> from scalar.ph)
296 ; CHECK-NEXT: IR %for.y = phi i32 [ %for.x.prev, %loop ], [ 0, %entry ] (extra operand: vp<[[RESUME_Y]]>.1 from scalar.ph)
297 ; CHECK: No successors
299 ; CHECK-NEXT: ir-bb<ret>:
300 ; CHECK-NEXT: No successors
307 %iv = phi i64 [ %iv.next, %loop ], [ 0, %entry ]
308 %for.x = phi i64 [ %for.x.next, %loop ], [ 0, %entry ]
309 %for.y = phi i32 [ %for.x.prev, %loop ], [ 0, %entry ]
310 %iv.next = add i64 %iv, 1
311 %gep = getelementptr i64, ptr %base, i64 %iv
312 %l = load i64, ptr %gep
313 %for.x.prev = trunc i64 %for.x to i32
314 %for.y.i64 = sext i32 %for.y to i64
315 store i64 %for.y.i64, ptr %gep
316 %for.x.next = mul i64 %l, 2
317 %icmp = icmp ugt i64 %iv, 4096
318 br i1 %icmp, label %ret, label %loop