2 ; RUN: opt -S -basicaa -licm -ipt-expensive-asserts=true < %s | FileCheck %s
3 ; RUN: opt -aa-pipeline=basic-aa -passes='require<opt-remark-emit>,loop(licm)' -ipt-expensive-asserts=true -S %s | FileCheck %s
4 target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
5 target triple = "x86_64-unknown-linux-gnu"
7 declare void @f() nounwind
8 declare void @llvm.experimental.guard(i1,...)
10 ; constant fold on first ieration
11 define i32 @test1(i32* noalias nocapture readonly %a) nounwind uwtable {
12 ; CHECK-LABEL: @test1(
14 ; CHECK: %i1 = load i32, i32* %a, align 4
15 ; CHECK-NEXT: br label %for.body
19 %iv = phi i32 [ 0, %entry ], [ %inc, %continue ]
20 %acc = phi i32 [ 0, %entry ], [ %add, %continue ]
21 %r.chk = icmp ult i32 %iv, 2000
22 br i1 %r.chk, label %continue, label %fail
24 %i1 = load i32, i32* %a, align 4
25 %add = add nsw i32 %i1, %acc
26 %inc = add nuw nsw i32 %iv, 1
27 %exitcond = icmp eq i32 %inc, 1000
28 br i1 %exitcond, label %for.cond.cleanup, label %for.body
38 ; Same as test1, but with a floating point IR and fcmp
39 define i32 @test_fcmp(i32* noalias nocapture readonly %a) nounwind uwtable {
40 ; CHECK-LABEL: @test_fcmp(
42 ; CHECK: %i1 = load i32, i32* %a, align 4
43 ; CHECK-NEXT: br label %for.body
47 %iv = phi float [ 0.0, %entry ], [ %inc, %continue ]
48 %acc = phi i32 [ 0, %entry ], [ %add, %continue ]
49 %r.chk = fcmp olt float %iv, 2000.0
50 br i1 %r.chk, label %continue, label %fail
52 %i1 = load i32, i32* %a, align 4
53 %add = add nsw i32 %i1, %acc
54 %inc = fadd float %iv, 1.0
55 %exitcond = fcmp ogt float %inc, 1000.0
56 br i1 %exitcond, label %for.cond.cleanup, label %for.body
66 ; Count down from a.length w/entry guard
67 ; TODO: currently unable to prove the following:
68 ; ule i32 (add nsw i32 %len, -1), %len where len is [0, 512]
69 define i32 @test2(i32* noalias nocapture readonly %a) nounwind uwtable {
70 ; CHECK-LABEL: @test2(
72 %len = load i32, i32* %a, align 4, !range !{i32 0, i32 512}
73 %is.non.pos = icmp eq i32 %len, 0
74 br i1 %is.non.pos, label %fail, label %preheader
76 %lenminusone = add nsw i32 %len, -1
79 %iv = phi i32 [ %lenminusone, %preheader ], [ %dec, %continue ]
80 %acc = phi i32 [ 0, %preheader ], [ %add, %continue ]
81 %r.chk = icmp ule i32 %iv, %len
82 br i1 %r.chk, label %continue, label %fail
84 ; CHECK-LABEL: continue
85 ; CHECK: %i1 = load i32, i32* %a, align 4
86 %i1 = load i32, i32* %a, align 4
87 %add = add nsw i32 %i1, %acc
88 %dec = add nsw i32 %iv, -1
89 %exitcond = icmp eq i32 %dec, 0
90 br i1 %exitcond, label %for.cond.cleanup, label %for.body
100 ; trivially true for zero
101 define i32 @test3(i32* noalias nocapture readonly %a) nounwind uwtable {
102 ; CHECK-LABEL: @test3(
104 %len = load i32, i32* %a, align 4, !range !{i32 0, i32 512}
105 %is.zero = icmp eq i32 %len, 0
106 br i1 %is.zero, label %fail, label %preheader
108 ; CHECK: %i1 = load i32, i32* %a, align 4
109 ; CHECK-NEXT: br label %for.body
112 %iv = phi i32 [ 0, %preheader ], [ %inc, %continue ]
113 %acc = phi i32 [ 0, %preheader ], [ %add, %continue ]
114 %r.chk = icmp ule i32 %iv, %len
115 br i1 %r.chk, label %continue, label %fail
117 %i1 = load i32, i32* %a, align 4
118 %add = add nsw i32 %i1, %acc
119 %inc = add nuw nsw i32 %iv, 1
120 %exitcond = icmp eq i32 %inc, 1000
121 br i1 %exitcond, label %for.cond.cleanup, label %for.body
131 ; requires fact length is non-zero
132 ; TODO: IsKnownNonNullFromDominatingConditions is currently only be done for
133 ; pointers; should handle integers too
134 define i32 @test4(i32* noalias nocapture readonly %a) nounwind uwtable {
135 ; CHECK-LABEL: @test4(
137 %len = load i32, i32* %a, align 4, !range !{i32 0, i32 512}
138 %is.zero = icmp eq i32 %len, 0
139 br i1 %is.zero, label %fail, label %preheader
143 %iv = phi i32 [ 0, %preheader ], [ %inc, %continue ]
144 %acc = phi i32 [ 0, %preheader ], [ %add, %continue ]
145 %r.chk = icmp ult i32 %iv, %len
146 br i1 %r.chk, label %continue, label %fail
148 ; CHECK-LABEL: continue
149 ; CHECK: %i1 = load i32, i32* %a, align 4
150 %i1 = load i32, i32* %a, align 4
151 %add = add nsw i32 %i1, %acc
152 %inc = add nuw nsw i32 %iv, 1
153 %exitcond = icmp eq i32 %inc, 1000
154 br i1 %exitcond, label %for.cond.cleanup, label %for.body
164 ; variation on test1 with branch swapped
165 define i32 @test-brswap(i32* noalias nocapture readonly %a) nounwind uwtable {
166 ; CHECK-LABEL: @test-brswap(
168 ; CHECK: %i1 = load i32, i32* %a, align 4
169 ; CHECK-NEXT: br label %for.body
173 %iv = phi i32 [ 0, %entry ], [ %inc, %continue ]
174 %acc = phi i32 [ 0, %entry ], [ %add, %continue ]
175 %r.chk = icmp ugt i32 %iv, 2000
176 br i1 %r.chk, label %fail, label %continue
178 %i1 = load i32, i32* %a, align 4
179 %add = add nsw i32 %i1, %acc
180 %inc = add nuw nsw i32 %iv, 1
181 %exitcond = icmp eq i32 %inc, 1000
182 br i1 %exitcond, label %for.cond.cleanup, label %for.body
192 define i32 @test-nonphi(i32* noalias nocapture readonly %a) nounwind uwtable {
193 ; CHECK-LABEL: @test-nonphi(
198 ; CHECK-LABEL: continue
199 ; CHECK: %i1 = load i32, i32* %a, align 4
200 %iv = phi i32 [ 0, %entry ], [ %inc, %continue ]
201 %acc = phi i32 [ 0, %entry ], [ %add, %continue ]
202 %xor = xor i32 %iv, 72
203 %r.chk = icmp ugt i32 %xor, 2000
204 br i1 %r.chk, label %fail, label %continue
206 %i1 = load i32, i32* %a, align 4
207 %add = add nsw i32 %i1, %acc
208 %inc = add nuw nsw i32 %iv, 1
209 %exitcond = icmp eq i32 %inc, 1000
210 br i1 %exitcond, label %for.cond.cleanup, label %for.body
220 define i32 @test-wrongphi(i32* noalias nocapture readonly %a) nounwind uwtable {
221 ; CHECK-LABEL: @test-wrongphi(
226 %iv = phi i32 [ 0, %entry ], [ %inc, %continue ]
227 %acc = phi i32 [ 0, %entry ], [ %add, %continue ]
228 %cond = icmp ult i32 %iv, 500
229 br i1 %cond, label %dummy_block1, label %dummy_block2
232 br label %dummy_block2
235 %wrongphi = phi i32 [11, %for.body], [12, %dummy_block1]
236 %r.chk = icmp ugt i32 %wrongphi, 2000
237 br i1 %r.chk, label %fail, label %continue
239 ; CHECK-LABEL: continue
240 ; CHECK: %i1 = load i32, i32* %a, align 4
241 %i1 = load i32, i32* %a, align 4
242 %add = add nsw i32 %i1, %acc
243 %inc = add nuw nsw i32 %iv, 1
244 %exitcond = icmp eq i32 %inc, 1000
245 br i1 %exitcond, label %for.cond.cleanup, label %for.body
255 ; This works because loop-simplify is run implicitly, but test for it anyways
256 define i32 @test-multiple-latch(i32* noalias nocapture readonly %a) nounwind uwtable {
257 ; CHECK-LABEL: @test-multiple-latch(
259 ; CHECK: %i1 = load i32, i32* %a, align 4
260 ; CHECK-NEXT: br label %for.body
264 %iv = phi i32 [ 0, %entry ], [ %inc, %continue1 ], [ %inc, %continue2 ]
265 %acc = phi i32 [ 0, %entry ], [ %add, %continue1 ], [ %add, %continue2 ]
266 %r.chk = icmp ult i32 %iv, 2000
267 br i1 %r.chk, label %continue1, label %fail
269 %i1 = load i32, i32* %a, align 4
270 %add = add nsw i32 %i1, %acc
271 %inc = add nuw nsw i32 %iv, 1
272 %cmp = icmp eq i32 %add, 0
273 br i1 %cmp, label %continue2, label %for.body
275 %exitcond = icmp eq i32 %inc, 1000
276 br i1 %exitcond, label %for.cond.cleanup, label %for.body
286 define void @test-hoisting-in-presence-of-guards(i1 %c, i32* %p) {
288 ; CHECK-LABEL: @test-hoisting-in-presence-of-guards
290 ; CHECK: %a = load i32, i32* %p
291 ; CHECK: %invariant_cond = icmp ne i32 %a, 100
298 %iv = phi i32 [ 0, %entry ], [ %iv.next, %loop ]
299 %iv.next = add i32 %iv, 1
300 %a = load i32, i32* %p
301 %invariant_cond = icmp ne i32 %a, 100
302 call void (i1, ...) @llvm.experimental.guard(i1 %invariant_cond) [ "deopt"() ]
303 %loop_cond = icmp slt i32 %iv.next, 1000
304 br i1 %loop_cond, label %loop, label %exit
311 declare void @may_throw() inaccessiblememonly
313 ; Test that we can sink a mustexecute load from loop header even in presence of
314 ; throwing instructions after it.
315 define void @test_hoist_from_header_01(i32* %p, i32 %n) {
317 ; CHECK-LABEL: @test_hoist_from_header_01(
319 ; CHECK-NEXT: %load = load i32, i32* %p
320 ; CHECK-NOT: load i32
326 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
327 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
328 %load = load i32, i32* %p
329 call void @may_throw()
330 %cond = icmp slt i32 %iv, %n
331 br i1 %cond, label %if.true, label %if.false
334 %a = add i32 %iv, %iv
338 %b = mul i32 %iv, %iv
342 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
343 %iv.next = add i32 %iv, %merge
344 %loop.cond = icmp ult i32 %iv.next, %load
345 br i1 %loop.cond, label %loop, label %exit
351 define void @test_hoist_from_header_02(i32* %p, i32 %n) {
353 ; CHECK-LABEL: @test_hoist_from_header_02(
355 ; CHECK-NEXT: %load = load i32, i32* %p
356 ; CHECK-NOT: load i32
362 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
363 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
364 %load = load i32, i32* %p
365 %cond = icmp slt i32 %iv, %n
366 br i1 %cond, label %if.true, label %if.false
369 call void @may_throw()
370 %a = add i32 %iv, %iv
374 %b = mul i32 %iv, %iv
378 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
379 %iv.next = add i32 %iv, %merge
380 %loop.cond = icmp ult i32 %iv.next, %load
381 br i1 %loop.cond, label %loop, label %exit
387 define void @test_hoist_from_header_03(i32* %p, i32 %n) {
389 ; CHECK-LABEL: @test_hoist_from_header_03(
391 ; CHECK-NEXT: %load = load i32, i32* %p
392 ; CHECK-NOT: load i32
398 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
399 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
400 %load = load i32, i32* %p
401 %cond = icmp slt i32 %iv, %n
402 br i1 %cond, label %if.true, label %if.false
405 %a = add i32 %iv, %iv
409 %b = mul i32 %iv, %iv
413 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
414 call void @may_throw()
415 %iv.next = add i32 %iv, %merge
416 %loop.cond = icmp ult i32 %iv.next, %load
417 br i1 %loop.cond, label %loop, label %exit
423 ; Check that a throwing instruction prohibits hoisting across it.
424 define void @test_hoist_from_header_04(i32* %p, i32 %n) {
426 ; CHECK-LABEL: @test_hoist_from_header_04(
429 ; CHECK: %load = load i32, i32* %p
435 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
436 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
437 call void @may_throw()
438 %load = load i32, i32* %p
439 %cond = icmp slt i32 %iv, %n
440 br i1 %cond, label %if.true, label %if.false
443 %a = add i32 %iv, %iv
447 %b = mul i32 %iv, %iv
451 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
452 %iv.next = add i32 %iv, %merge
453 %loop.cond = icmp ult i32 %iv.next, %load
454 br i1 %loop.cond, label %loop, label %exit
460 ; Check that we can hoist a mustexecute load from backedge even if something
462 define void @test_hoist_from_backedge_01(i32* %p, i32 %n) {
464 ; CHECK-LABEL: @test_hoist_from_backedge_01(
466 ; CHECK-NEXT: %load = load i32, i32* %p
467 ; CHECK-NOT: load i32
473 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
474 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
475 %cond = icmp slt i32 %iv, %n
476 br i1 %cond, label %if.true, label %if.false
479 %a = add i32 %iv, %iv
483 %b = mul i32 %iv, %iv
487 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
488 %iv.next = add i32 %iv, %merge
489 %load = load i32, i32* %p
490 call void @may_throw()
491 %loop.cond = icmp ult i32 %iv.next, %load
492 br i1 %loop.cond, label %loop, label %exit
498 ; Check that we don't hoist the load if something before it can throw.
499 define void @test_hoist_from_backedge_02(i32* %p, i32 %n) {
501 ; CHECK-LABEL: @test_hoist_from_backedge_02(
504 ; CHECK: %load = load i32, i32* %p
510 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
511 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
512 %cond = icmp slt i32 %iv, %n
513 br i1 %cond, label %if.true, label %if.false
516 %a = add i32 %iv, %iv
520 %b = mul i32 %iv, %iv
524 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
525 %iv.next = add i32 %iv, %merge
526 call void @may_throw()
527 %load = load i32, i32* %p
528 %loop.cond = icmp ult i32 %iv.next, %load
529 br i1 %loop.cond, label %loop, label %exit
535 define void @test_hoist_from_backedge_03(i32* %p, i32 %n) {
537 ; CHECK-LABEL: @test_hoist_from_backedge_03(
540 ; CHECK: %load = load i32, i32* %p
546 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
547 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
548 %cond = icmp slt i32 %iv, %n
549 br i1 %cond, label %if.true, label %if.false
552 %a = add i32 %iv, %iv
556 %b = mul i32 %iv, %iv
557 call void @may_throw()
561 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
562 %iv.next = add i32 %iv, %merge
563 %load = load i32, i32* %p
564 %loop.cond = icmp ult i32 %iv.next, %load
565 br i1 %loop.cond, label %loop, label %exit
571 define void @test_hoist_from_backedge_04(i32* %p, i32 %n) {
573 ; CHECK-LABEL: @test_hoist_from_backedge_04(
576 ; CHECK: %load = load i32, i32* %p
582 %iv = phi i32 [ 0, %entry ], [ %iv.next, %backedge ]
583 %dummy = phi i32 [ 0, %entry ], [ %merge, %backedge ]
584 call void @may_throw()
585 %cond = icmp slt i32 %iv, %n
586 br i1 %cond, label %if.true, label %if.false
589 %a = add i32 %iv, %iv
593 %b = mul i32 %iv, %iv
597 %merge = phi i32 [ %a, %if.true ], [ %b, %if.false ]
598 %iv.next = add i32 %iv, %merge
599 %load = load i32, i32* %p
600 %loop.cond = icmp ult i32 %iv.next, %load
601 br i1 %loop.cond, label %loop, label %exit