1; RUN: opt -licm -basic-aa < %s -S | FileCheck %s 2; RUN: opt -aa-pipeline=basic-aa -passes='require<aa>,require<targetir>,require<scalar-evolution>,require<opt-remark-emit>,loop(licm)' < %s -S | FileCheck %s 3 4define void @test1(i64 %n) { 5; CHECK-LABEL: @test1 6; CHECK: fence 7; CHECK-LABEL: loop: 8entry: 9 br label %loop 10loop: 11 %iv = phi i64 [0, %entry], [%iv.next, %loop] 12 fence release 13 %iv.next = add i64 %iv, 1 14 %test = icmp slt i64 %iv, %n 15 br i1 %test, label %loop, label %exit 16exit: 17 ret void 18} 19 20define void @test2(i64 %n) { 21; CHECK-LABEL: @test2 22; CHECK: fence 23; CHECK-LABEL: loop: 24entry: 25 br label %loop 26loop: 27 %iv = phi i64 [0, %entry], [%iv.next, %loop] 28 fence acquire 29 %iv.next = add i64 %iv, 1 30 %test = icmp slt i64 %iv, %n 31 br i1 %test, label %loop, label %exit 32exit: 33 ret void 34} 35 36define void @test3(i64 %n) { 37; CHECK-LABEL: @test3 38; CHECK: fence 39; CHECK-LABEL: loop: 40entry: 41 br label %loop 42loop: 43 %iv = phi i64 [0, %entry], [%iv.next, %loop] 44 fence acq_rel 45 %iv.next = add i64 %iv, 1 46 %test = icmp slt i64 %iv, %n 47 br i1 %test, label %loop, label %exit 48exit: 49 ret void 50} 51 52define void @test4(i64 %n) { 53; CHECK-LABEL: @test4 54; CHECK: fence 55; CHECK-LABEL: loop: 56entry: 57 br label %loop 58loop: 59 %iv = phi i64 [0, %entry], [%iv.next, %loop] 60 fence seq_cst 61 %iv.next = add i64 %iv, 1 62 %test = icmp slt i64 %iv, %n 63 br i1 %test, label %loop, label %exit 64exit: 65 ret void 66} 67 68define void @testneg1(i64 %n, i64* %p) { 69; CHECK-LABEL: @testneg1 70; CHECK-LABEL: loop: 71; CHECK: fence 72entry: 73 br label %loop 74loop: 75 %iv = phi i64 [0, %entry], [%iv.next, %loop] 76 store i64 %iv, i64* %p 77 fence release 78 %iv.next = add i64 %iv, 1 79 %test = icmp slt i64 %iv, %n 80 br i1 %test, label %loop, label %exit 81exit: 82 ret void 83} 84 85define void @testneg2(i64* %p) { 86; CHECK-LABEL: @testneg2 87; CHECK-LABEL: loop: 88; CHECK: fence 89entry: 90 br label %loop 91loop: 92 %iv = phi i64 [0, %entry], [%iv.next, %loop] 93 fence acquire 94 %n = load i64, i64* %p 95 %iv.next = add i64 %iv, 1 96 %test = icmp slt i64 %iv, %n 97 br i1 %test, label %loop, label %exit 98exit: 99 ret void 100} 101 102; Note: While a false negative for LICM on it's own, O3 does get this 103; case by combining the fences. 104define void @testfn1(i64 %n, i64* %p) { 105; CHECK-LABEL: @testfn1 106; CHECK-LABEL: loop: 107; CHECK: fence 108entry: 109 br label %loop 110loop: 111 %iv = phi i64 [0, %entry], [%iv.next, %loop] 112 fence release 113 fence release 114 %iv.next = add i64 %iv, 1 115 %test = icmp slt i64 %iv, %n 116 br i1 %test, label %loop, label %exit 117exit: 118 ret void 119} 120 121