1 ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2 ; RUN: opt < %s -instcombine -S | FileCheck %s
4 define i32 @fold(i32 %x) {
6 ; CHECK-NEXT: [[Y:%.*]] = freeze i32 [[X:%.*]]
7 ; CHECK-NEXT: ret i32 [[Y]]
14 define i32 @make_const() {
15 ; CHECK-LABEL: @make_const(
16 ; CHECK-NEXT: ret i32 10
22 define i32 @and_freeze_undef(i32 %x) {
23 ; CHECK-LABEL: @and_freeze_undef(
24 ; CHECK-NEXT: ret i32 0
31 declare void @use_i32(i32)
33 define i32 @and_freeze_undef_multipleuses(i32 %x) {
34 ; CHECK-LABEL: @and_freeze_undef_multipleuses(
35 ; CHECK-NEXT: call void @use_i32(i32 0)
36 ; CHECK-NEXT: ret i32 0
40 call void @use_i32(i32 %f)
44 define i32 @or_freeze_undef(i32 %x) {
45 ; CHECK-LABEL: @or_freeze_undef(
46 ; CHECK-NEXT: ret i32 -1
53 define i32 @or_freeze_undef_multipleuses(i32 %x) {
54 ; CHECK-LABEL: @or_freeze_undef_multipleuses(
55 ; CHECK-NEXT: call void @use_i32(i32 0)
56 ; CHECK-NEXT: ret i32 [[X:%.*]]
60 call void @use_i32(i32 %f)
64 declare void @use_i32_i1(i32, i1)
66 define void @or_select_multipleuses(i32 %x, i1 %y) {
67 ; CHECK-LABEL: @or_select_multipleuses(
68 ; CHECK-NEXT: call void @use_i32_i1(i32 32, i1 [[Y:%.*]])
69 ; CHECK-NEXT: ret void
72 %a = select i1 %f, i32 %x, i32 32 ; prefers %f to be false
73 %b = or i1 %f, %y ; prefers %f to be true
74 call void @use_i32_i1(i32 %a, i1 %b)
78 define void @or_select_multipleuses_logical(i32 %x, i1 %y) {
79 ; CHECK-LABEL: @or_select_multipleuses_logical(
80 ; CHECK-NEXT: call void @use_i32_i1(i32 32, i1 [[Y:%.*]])
81 ; CHECK-NEXT: ret void
84 %a = select i1 %f, i32 %x, i32 32 ; prefers %f to be false
85 %b = select i1 %f, i1 true, i1 %y ; prefers %f to be true
86 call void @use_i32_i1(i32 %a, i1 %b)
90 ; Move the freeze forward to prevent poison from spreading.
92 define i32 @early_freeze_test1(i32 %x, i32 %y) {
93 ; CHECK-LABEL: @early_freeze_test1(
94 ; CHECK-NEXT: [[V1:%.*]] = add i32 [[X:%.*]], [[Y:%.*]]
95 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1]]
96 ; CHECK-NEXT: [[V2:%.*]] = shl i32 [[V1_FR]], 1
97 ; CHECK-NEXT: [[V3:%.*]] = and i32 [[V2]], 2
98 ; CHECK-NEXT: ret i32 [[V3]]
103 %v3.fr = freeze i32 %v3
107 define i1 @early_freeze_test2(i32* %ptr) {
108 ; CHECK-LABEL: @early_freeze_test2(
109 ; CHECK-NEXT: [[V1:%.*]] = load i32, i32* [[PTR:%.*]], align 4
110 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1]]
111 ; CHECK-NEXT: [[V2:%.*]] = and i32 [[V1_FR]], 1
112 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[V2]], 0
113 ; CHECK-NEXT: ret i1 [[COND]]
115 %v1 = load i32, i32* %ptr
117 %cond = icmp eq i32 %v2, 0
118 %cond.fr = freeze i1 %cond
122 define i32 @early_freeze_test3(i32 %v1) {
123 ; CHECK-LABEL: @early_freeze_test3(
124 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1:%.*]]
125 ; CHECK-NEXT: [[V2:%.*]] = shl i32 [[V1_FR]], 1
126 ; CHECK-NEXT: [[V3:%.*]] = add i32 [[V2]], 2
127 ; CHECK-NEXT: [[V4:%.*]] = or i32 [[V3]], 1
128 ; CHECK-NEXT: ret i32 [[V4]]
131 %v3 = add nuw i32 %v2, 2
133 %v4.fr = freeze i32 %v4
137 ; If replace all dominated uses of v to freeze(v).
139 define void @freeze_dominated_uses_test1(i32 %v) {
140 ; CHECK-LABEL: @freeze_dominated_uses_test1(
141 ; CHECK-NEXT: [[V_FR:%.*]] = freeze i32 [[V:%.*]]
142 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR]])
143 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR]])
144 ; CHECK-NEXT: ret void
146 %v.fr = freeze i32 %v
147 call void @use_i32(i32 %v)
148 call void @use_i32(i32 %v.fr)
152 define void @freeze_dominated_uses_test2(i32 %v) {
153 ; CHECK-LABEL: @freeze_dominated_uses_test2(
155 ; CHECK-NEXT: call void @use_i32(i32 [[V:%.*]])
156 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[V]], 0
157 ; CHECK-NEXT: br i1 [[COND]], label [[BB0:%.*]], label [[BB1:%.*]]
159 ; CHECK-NEXT: [[V_FR:%.*]] = freeze i32 [[V]]
160 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR]])
161 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR]])
162 ; CHECK-NEXT: br label [[END:%.*]]
164 ; CHECK-NEXT: call void @use_i32(i32 [[V]])
165 ; CHECK-NEXT: br label [[END]]
167 ; CHECK-NEXT: ret void
170 call void @use_i32(i32 %v)
171 %cond = icmp eq i32 %v, 0
172 br i1 %cond, label %bb0, label %bb1
175 %v.fr = freeze i32 %v
176 call void @use_i32(i32 %v.fr)
177 call void @use_i32(i32 %v)
181 call void @use_i32(i32 %v)
188 ; If there is a duplicate freeze, it will be removed.
190 define void @freeze_dominated_uses_test3(i32 %v, i1 %cond) {
191 ; CHECK-LABEL: @freeze_dominated_uses_test3(
193 ; CHECK-NEXT: [[V_FR1:%.*]] = freeze i32 [[V:%.*]]
194 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR1]])
195 ; CHECK-NEXT: br i1 [[COND:%.*]], label [[BB0:%.*]], label [[BB1:%.*]]
197 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR1]])
198 ; CHECK-NEXT: br label [[END:%.*]]
200 ; CHECK-NEXT: call void @use_i32(i32 [[V_FR1]])
201 ; CHECK-NEXT: br label [[END]]
203 ; CHECK-NEXT: ret void
206 %v.fr1 = freeze i32 %v
207 call void @use_i32(i32 %v.fr1)
208 br i1 %cond, label %bb0, label %bb1
211 %v.fr2 = freeze i32 %v
212 call void @use_i32(i32 %v.fr2)
216 call void @use_i32(i32 %v)
224 define i32 @propagate_drop_flags_add(i32 %arg) {
225 ; CHECK-LABEL: @propagate_drop_flags_add(
226 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
227 ; CHECK-NEXT: [[V1:%.*]] = add i32 [[ARG_FR]], 2
228 ; CHECK-NEXT: ret i32 [[V1]]
230 %v1 = add nsw nuw i32 %arg, 2
231 %v1.fr = freeze i32 %v1
235 define i32 @propagate_drop_flags_add_foldaway(i32 noundef %arg) {
236 ; CHECK-LABEL: @propagate_drop_flags_add_foldaway(
237 ; CHECK-NEXT: [[V1:%.*]] = add i32 [[ARG:%.*]], 2
238 ; CHECK-NEXT: ret i32 [[V1]]
240 %v1 = add nsw nuw i32 %arg, 2
241 %v1.fr = freeze i32 %v1
245 define i32 @propagate_drop_flags_sub(i32 %arg) {
246 ; CHECK-LABEL: @propagate_drop_flags_sub(
247 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
248 ; CHECK-NEXT: [[V1:%.*]] = add i32 [[ARG_FR]], -2
249 ; CHECK-NEXT: ret i32 [[V1]]
251 %v1 = sub nsw nuw i32 %arg, 2
252 %v1.fr = freeze i32 %v1
256 define i32 @propagate_drop_flags_mul(i32 %arg) {
257 ; CHECK-LABEL: @propagate_drop_flags_mul(
258 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
259 ; CHECK-NEXT: [[V1:%.*]] = shl i32 [[ARG_FR]], 1
260 ; CHECK-NEXT: ret i32 [[V1]]
262 %v1 = mul nsw nuw i32 %arg, 2
263 %v1.fr = freeze i32 %v1
267 define i32 @propagate_drop_flags_udiv(i32 %arg) {
268 ; CHECK-LABEL: @propagate_drop_flags_udiv(
269 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
270 ; CHECK-NEXT: [[V1:%.*]] = lshr i32 [[ARG_FR]], 1
271 ; CHECK-NEXT: ret i32 [[V1]]
273 %v1 = udiv exact i32 %arg, 2
274 %v1.fr = freeze i32 %v1
278 define i32 @propagate_drop_flags_sdiv(i32 %arg) {
279 ; CHECK-LABEL: @propagate_drop_flags_sdiv(
280 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
281 ; CHECK-NEXT: [[V1:%.*]] = ashr i32 [[ARG_FR]], 1
282 ; CHECK-NEXT: ret i32 [[V1]]
284 %v1 = sdiv exact i32 %arg, 2
285 %v1.fr = freeze i32 %v1
289 define i32 @propagate_drop_shl1(i32 %arg) {
290 ; CHECK-LABEL: @propagate_drop_shl1(
291 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
292 ; CHECK-NEXT: [[V1:%.*]] = shl i32 [[ARG_FR]], 2
293 ; CHECK-NEXT: ret i32 [[V1]]
295 %v1 = shl nsw nuw i32 %arg, 2
296 %v1.fr = freeze i32 %v1
300 define i32 @propagate_drop_shl2(i32 %arg, i32 %unknown) {
301 ; CHECK-LABEL: @propagate_drop_shl2(
302 ; CHECK-NEXT: [[V1:%.*]] = shl nuw nsw i32 [[ARG:%.*]], [[UNKNOWN:%.*]]
303 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1]]
304 ; CHECK-NEXT: ret i32 [[V1_FR]]
306 %v1 = shl nsw nuw i32 %arg, %unknown
307 %v1.fr = freeze i32 %v1
311 define i32 @propagate_drop_ashr1(i32 %arg) {
312 ; CHECK-LABEL: @propagate_drop_ashr1(
313 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
314 ; CHECK-NEXT: [[V1:%.*]] = ashr i32 [[ARG_FR]], 2
315 ; CHECK-NEXT: ret i32 [[V1]]
317 %v1 = ashr exact i32 %arg, 2
318 %v1.fr = freeze i32 %v1
322 define i32 @propagate_drop_ashr2(i32 %arg, i32 %unknown) {
323 ; CHECK-LABEL: @propagate_drop_ashr2(
324 ; CHECK-NEXT: [[V1:%.*]] = ashr exact i32 [[ARG:%.*]], [[UNKNOWN:%.*]]
325 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1]]
326 ; CHECK-NEXT: ret i32 [[V1_FR]]
328 %v1 = ashr exact i32 %arg, %unknown
329 %v1.fr = freeze i32 %v1
333 define i32 @propagate_drop_lshr1(i32 %arg) {
334 ; CHECK-LABEL: @propagate_drop_lshr1(
335 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i32 [[ARG:%.*]]
336 ; CHECK-NEXT: [[V1:%.*]] = lshr i32 [[ARG_FR]], 2
337 ; CHECK-NEXT: ret i32 [[V1]]
339 %v1 = lshr exact i32 %arg, 2
340 %v1.fr = freeze i32 %v1
344 define i32 @propagate_drop_lshr2(i32 %arg, i32 %unknown) {
345 ; CHECK-LABEL: @propagate_drop_lshr2(
346 ; CHECK-NEXT: [[V1:%.*]] = lshr exact i32 [[ARG:%.*]], [[UNKNOWN:%.*]]
347 ; CHECK-NEXT: [[V1_FR:%.*]] = freeze i32 [[V1]]
348 ; CHECK-NEXT: ret i32 [[V1_FR]]
350 %v1 = lshr exact i32 %arg, %unknown
351 %v1.fr = freeze i32 %v1
355 define i8* @propagate_drop_gep1(i8* %arg) {
356 ; CHECK-LABEL: @propagate_drop_gep1(
357 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i8* [[ARG:%.*]]
358 ; CHECK-NEXT: [[V1:%.*]] = getelementptr i8, i8* [[ARG_FR]], i64 16
359 ; CHECK-NEXT: ret i8* [[V1]]
361 %v1 = getelementptr inbounds i8, i8* %arg, i64 16
362 %v1.fr = freeze i8* %v1
366 define float @propagate_drop_fneg(float %arg) {
367 ; CHECK-LABEL: @propagate_drop_fneg(
368 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
369 ; CHECK-NEXT: [[V1:%.*]] = fneg float [[ARG_FR]]
370 ; CHECK-NEXT: ret float [[V1]]
372 %v1 = fneg ninf nnan float %arg
373 %v1.fr = freeze float %v1
378 define float @propagate_drop_fadd(float %arg) {
379 ; CHECK-LABEL: @propagate_drop_fadd(
380 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
381 ; CHECK-NEXT: [[V1:%.*]] = fadd float [[ARG_FR]], 2.000000e+00
382 ; CHECK-NEXT: ret float [[V1]]
384 %v1 = fadd ninf nnan float %arg, 2.0
385 %v1.fr = freeze float %v1
389 define float @propagate_drop_fsub(float %arg) {
390 ; CHECK-LABEL: @propagate_drop_fsub(
391 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
392 ; CHECK-NEXT: [[V1:%.*]] = fadd float [[ARG_FR]], -2.000000e+00
393 ; CHECK-NEXT: ret float [[V1]]
395 %v1 = fsub ninf nnan float %arg, 2.0
396 %v1.fr = freeze float %v1
400 define float @propagate_drop_fmul(float %arg) {
401 ; CHECK-LABEL: @propagate_drop_fmul(
402 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
403 ; CHECK-NEXT: [[V1:%.*]] = fmul float [[ARG_FR]], 2.000000e+00
404 ; CHECK-NEXT: ret float [[V1]]
406 %v1 = fmul ninf nnan float %arg, 2.0
407 %v1.fr = freeze float %v1
411 define float @propagate_drop_fdiv(float %arg) {
412 ; CHECK-LABEL: @propagate_drop_fdiv(
413 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
414 ; CHECK-NEXT: [[V1:%.*]] = fmul float [[ARG_FR]], 5.000000e-01
415 ; CHECK-NEXT: ret float [[V1]]
417 %v1 = fdiv ninf nnan float %arg, 2.0
418 %v1.fr = freeze float %v1
422 define float @propagate_drop_frem(float %arg) {
423 ; CHECK-LABEL: @propagate_drop_frem(
424 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
425 ; CHECK-NEXT: [[V1:%.*]] = frem float [[ARG_FR]], 2.000000e+00
426 ; CHECK-NEXT: ret float [[V1]]
428 %v1 = frem ninf nnan float %arg, 2.0
429 %v1.fr = freeze float %v1
433 define i1 @propagate_drop_fcmp(float %arg) {
434 ; CHECK-LABEL: @propagate_drop_fcmp(
435 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze float [[ARG:%.*]]
436 ; CHECK-NEXT: [[V1:%.*]] = fcmp une float [[ARG_FR]], 2.000000e+00
437 ; CHECK-NEXT: ret i1 [[V1]]
439 %v1 = fcmp ninf nnan une float %arg, 2.0
440 %v1.fr = freeze i1 %v1
444 define float @propagate_drop_fmath_select(i1 %arg) {
445 ; CHECK-LABEL: @propagate_drop_fmath_select(
446 ; CHECK-NEXT: [[ARG_FR:%.*]] = freeze i1 [[ARG:%.*]]
447 ; CHECK-NEXT: [[V1:%.*]] = select i1 [[ARG_FR]], float 1.000000e+00, float -1.000000e+00
448 ; CHECK-NEXT: ret float [[V1]]
450 %v1 = select ninf nnan i1 %arg, float 1.0, float -1.0
451 %v1.fr = freeze float %v1
455 define void @fold_phi_noop(i32 noundef %init, i32 %n) {
456 ; CHECK-LABEL: @fold_phi_noop(
458 ; CHECK-NEXT: br label [[LOOP:%.*]]
460 ; CHECK-NEXT: [[I:%.*]] = phi i32 [ [[INIT:%.*]], [[ENTRY:%.*]] ], [ [[I_NEXT:%.*]], [[LOOP]] ]
461 ; CHECK-NEXT: [[I_NEXT]] = add i32 [[I]], 1
462 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[I_NEXT]], [[N:%.*]]
463 ; CHECK-NEXT: br i1 [[COND]], label [[LOOP]], label [[EXIT:%.*]]
465 ; CHECK-NEXT: ret void
470 loop: ; preds = %loop, %entry
471 %i = phi i32 [ %init, %entry ], [ %i.next, %loop ]
472 %i.fr = freeze i32 %i
473 %i.next = add i32 %i.fr, 1
474 %cond = icmp eq i32 %i.next, %n
475 br i1 %cond, label %loop, label %exit
477 exit: ; preds = %loop
481 define void @fold_phi_through(i32 %init, i32 %n) {
482 ; CHECK-LABEL: @fold_phi_through(
484 ; CHECK-NEXT: [[PHI_FR:%.*]] = freeze i32 [[INIT:%.*]]
485 ; CHECK-NEXT: br label [[LOOP:%.*]]
487 ; CHECK-NEXT: [[I:%.*]] = phi i32 [ [[PHI_FR]], [[ENTRY:%.*]] ], [ [[I_NEXT:%.*]], [[LOOP]] ]
488 ; CHECK-NEXT: [[I_NEXT]] = add i32 [[I]], 1
489 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[I_NEXT]], [[N:%.*]]
490 ; CHECK-NEXT: br i1 [[COND]], label [[LOOP]], label [[EXIT:%.*]]
492 ; CHECK-NEXT: ret void
497 loop: ; preds = %loop, %entry
498 %i = phi i32 [ %init, %entry ], [ %i.next, %loop ]
499 %i.fr = freeze i32 %i
500 %i.next = add i32 %i.fr, 1
501 %cond = icmp eq i32 %i.next, %n
502 br i1 %cond, label %loop, label %exit
504 exit: ; preds = %loop
508 define void @fold_phi_neg_flags(i32 %init, i32 %n) {
509 ; CHECK-LABEL: @fold_phi_neg_flags(
511 ; CHECK-NEXT: br label [[LOOP:%.*]]
513 ; CHECK-NEXT: [[I:%.*]] = phi i32 [ [[INIT:%.*]], [[ENTRY:%.*]] ], [ [[I_NEXT:%.*]], [[LOOP]] ]
514 ; CHECK-NEXT: [[I_FR:%.*]] = freeze i32 [[I]]
515 ; CHECK-NEXT: [[I_NEXT]] = add nuw nsw i32 [[I_FR]], 1
516 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[I_NEXT]], [[N:%.*]]
517 ; CHECK-NEXT: br i1 [[COND]], label [[LOOP]], label [[EXIT:%.*]]
519 ; CHECK-NEXT: ret void
524 loop: ; preds = %loop, %entry
525 %i = phi i32 [ %init, %entry ], [ %i.next, %loop ]
526 %i.fr = freeze i32 %i
527 %i.next = add nsw nuw i32 %i.fr, 1
528 %cond = icmp eq i32 %i.next, %n
529 br i1 %cond, label %loop, label %exit
531 exit: ; preds = %loop
535 define void @fold_phi_non_add(i32 %init, i32 %n) {
536 ; CHECK-LABEL: @fold_phi_non_add(
538 ; CHECK-NEXT: [[PHI_FR:%.*]] = freeze i32 [[INIT:%.*]]
539 ; CHECK-NEXT: br label [[LOOP:%.*]]
541 ; CHECK-NEXT: [[I:%.*]] = phi i32 [ [[PHI_FR]], [[ENTRY:%.*]] ], [ [[I_NEXT:%.*]], [[LOOP]] ]
542 ; CHECK-NEXT: [[I_NEXT]] = shl i32 [[I]], 1
543 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i32 [[I_NEXT]], [[N:%.*]]
544 ; CHECK-NEXT: br i1 [[COND]], label [[LOOP]], label [[EXIT:%.*]]
546 ; CHECK-NEXT: ret void
551 loop: ; preds = %loop, %entry
552 %i = phi i32 [ %init, %entry ], [ %i.next, %loop ]
553 %i.fr = freeze i32 %i
554 %i.next = shl i32 %i.fr, 1
555 %cond = icmp eq i32 %i.next, %n
556 br i1 %cond, label %loop, label %exit
558 exit: ; preds = %loop
562 define void @fold_phi_gep(i8* %init, i8* %end) {
563 ; CHECK-LABEL: @fold_phi_gep(
565 ; CHECK-NEXT: [[PHI_FR:%.*]] = freeze i8* [[INIT:%.*]]
566 ; CHECK-NEXT: br label [[LOOP:%.*]]
568 ; CHECK-NEXT: [[I:%.*]] = phi i8* [ [[PHI_FR]], [[ENTRY:%.*]] ], [ [[I_NEXT:%.*]], [[LOOP]] ]
569 ; CHECK-NEXT: [[I_NEXT]] = getelementptr i8, i8* [[I]], i64 1
570 ; CHECK-NEXT: [[COND:%.*]] = icmp eq i8* [[I_NEXT]], [[END:%.*]]
571 ; CHECK-NEXT: br i1 [[COND]], label [[LOOP]], label [[EXIT:%.*]]
573 ; CHECK-NEXT: ret void
578 loop: ; preds = %loop, %entry
579 %i = phi i8* [ %init, %entry ], [ %i.next, %loop ]
580 %i.fr = freeze i8* %i
581 %i.next = getelementptr i8, i8* %i.fr, i64 1
582 %cond = icmp eq i8* %i.next, %end
583 br i1 %cond, label %loop, label %exit
585 exit: ; preds = %loop