Home | History | Annotate | Download | only in LICM
      1 ; RUN: opt < %s -basicaa -tbaa -licm -S | FileCheck %s
      2 ; RUN: opt -aa-pipeline=type-based-aa,basic-aa -passes='require<aa>,require<targetir>,require<scalar-evolution>,loop(licm)' -S %s | FileCheck %s
      3 target datalayout = "E-p:64:64:64-a0:0:8-f32:32:32-f64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-v64:64:64-v128:128:128"
      4 
      5 @X = global i32 7   ; <i32*> [#uses=4]
      6 
      7 define void @test1(i32 %i) {
      8 Entry:
      9   br label %Loop
     10 ; CHECK-LABEL: @test1(
     11 ; CHECK: Entry:
     12 ; CHECK-NEXT:   load i32, i32* @X
     13 ; CHECK-NEXT:   br label %Loop
     14 
     15 
     16 Loop:   ; preds = %Loop, %0
     17   %j = phi i32 [ 0, %Entry ], [ %Next, %Loop ]    ; <i32> [#uses=1]
     18   %x = load i32, i32* @X   ; <i32> [#uses=1]
     19   %x2 = add i32 %x, 1   ; <i32> [#uses=1]
     20   store i32 %x2, i32* @X
     21   %Next = add i32 %j, 1   ; <i32> [#uses=2]
     22   %cond = icmp eq i32 %Next, 0    ; <i1> [#uses=1]
     23   br i1 %cond, label %Out, label %Loop
     24 
     25 Out:
     26   ret void
     27 ; CHECK: Out:
     28 ; CHECK-NEXT:   %[[LCSSAPHI:.*]] = phi i32 [ %x2
     29 ; CHECK-NEXT:   store i32 %[[LCSSAPHI]], i32* @X
     30 ; CHECK-NEXT:   ret void
     31 
     32 }
     33 
     34 define void @test2(i32 %i) {
     35 Entry:
     36   br label %Loop
     37 ; CHECK-LABEL: @test2(
     38 ; CHECK: Entry:
     39 ; CHECK-NEXT:    %.promoted = load i32, i32* getelementptr inbounds (i32, i32* @X, i64 1)
     40 ; CHECK-NEXT:    br label %Loop
     41 
     42 Loop:   ; preds = %Loop, %0
     43   %X1 = getelementptr i32, i32* @X, i64 1    ; <i32*> [#uses=1]
     44   %A = load i32, i32* %X1    ; <i32> [#uses=1]
     45   %V = add i32 %A, 1    ; <i32> [#uses=1]
     46   %X2 = getelementptr i32, i32* @X, i64 1    ; <i32*> [#uses=1]
     47   store i32 %V, i32* %X2
     48   br i1 false, label %Loop, label %Exit
     49 
     50 Exit:   ; preds = %Loop
     51   ret void
     52 ; CHECK: Exit:
     53 ; CHECK-NEXT:   %[[LCSSAPHI:.*]] = phi i32 [ %V
     54 ; CHECK-NEXT:   store i32 %[[LCSSAPHI]], i32* getelementptr inbounds (i32, i32* @X, i64 1)
     55 ; CHECK-NEXT:   ret void
     56 }
     57 
     58 
     59 
     60 define void @test3(i32 %i) {
     61 ; CHECK-LABEL: @test3(
     62   br label %Loop
     63 Loop:
     64         ; Should not promote this to a register
     65   %x = load volatile i32, i32* @X
     66   %x2 = add i32 %x, 1
     67   store i32 %x2, i32* @X
     68   br i1 true, label %Out, label %Loop
     69 
     70 ; CHECK: Loop:
     71 ; CHECK-NEXT: load volatile
     72 
     73 Out:    ; preds = %Loop
     74   ret void
     75 }
     76 
     77 ; PR8041
     78 define void @test4(i8* %x, i8 %n) {
     79 ; CHECK-LABEL: @test4(
     80   %handle1 = alloca i8*
     81   %handle2 = alloca i8*
     82   store i8* %x, i8** %handle1
     83   br label %loop
     84 
     85 loop:
     86   %tmp = getelementptr i8, i8* %x, i64 8
     87   store i8* %tmp, i8** %handle2
     88   br label %subloop
     89 
     90 subloop:
     91   %count = phi i8 [ 0, %loop ], [ %nextcount, %subloop ]
     92   %offsetx2 = load i8*, i8** %handle2
     93   store i8 %n, i8* %offsetx2
     94   %newoffsetx2 = getelementptr i8, i8* %offsetx2, i64 -1
     95   store i8* %newoffsetx2, i8** %handle2
     96   %nextcount = add i8 %count, 1
     97   %innerexitcond = icmp sge i8 %nextcount, 8
     98   br i1 %innerexitcond, label %innerexit, label %subloop
     99 
    100 ; Should have promoted 'handle2' accesses.
    101 ; CHECK: subloop:
    102 ; CHECK-NEXT: phi i8* [
    103 ; CHECK-NEXT: %count = phi i8 [
    104 ; CHECK-NEXT: store i8 %n
    105 ; CHECK-NOT: store
    106 ; CHECK: br i1
    107 
    108 innerexit:
    109   %offsetx1 = load i8*, i8** %handle1
    110   %val = load i8, i8* %offsetx1
    111   %cond = icmp eq i8 %val, %n
    112   br i1 %cond, label %exit, label %loop
    113 
    114 ; Should not have promoted offsetx1 loads.
    115 ; CHECK: innerexit:
    116 ; CHECK: %val = load i8, i8* %offsetx1
    117 ; CHECK: %cond = icmp eq i8 %val, %n
    118 ; CHECK: br i1 %cond, label %exit, label %loop
    119 
    120 exit:
    121   ret void
    122 }
    123 
    124 define void @test5(i32 %i, i32** noalias %P2) {
    125 Entry:
    126   br label %Loop
    127 ; CHECK-LABEL: @test5(
    128 ; CHECK: Entry:
    129 ; CHECK-NEXT:   load i32, i32* @X
    130 ; CHECK-NEXT:   br label %Loop
    131 
    132 
    133 Loop:   ; preds = %Loop, %0
    134   %j = phi i32 [ 0, %Entry ], [ %Next, %Loop ]    ; <i32> [#uses=1]
    135   %x = load i32, i32* @X   ; <i32> [#uses=1]
    136   %x2 = add i32 %x, 1   ; <i32> [#uses=1]
    137   store i32 %x2, i32* @X
    138 
    139         store atomic i32* @X, i32** %P2 monotonic, align 8
    140 
    141   %Next = add i32 %j, 1   ; <i32> [#uses=2]
    142   %cond = icmp eq i32 %Next, 0    ; <i1> [#uses=1]
    143   br i1 %cond, label %Out, label %Loop
    144 
    145 Out:
    146   ret void
    147 ; CHECK: Out:
    148 ; CHECK-NEXT:   %[[LCSSAPHI:.*]] = phi i32 [ %x2
    149 ; CHECK-NEXT:   store i32 %[[LCSSAPHI]], i32* @X
    150 ; CHECK-NEXT:   ret void
    151 
    152 }
    153 
    154 
    155 ; PR14753 - Preserve TBAA tags when promoting values in a loop.
    156 define void @test6(i32 %n, float* nocapture %a, i32* %gi) {
    157 entry:
    158   store i32 0, i32* %gi, align 4, !tbaa !0
    159   %cmp1 = icmp slt i32 0, %n
    160   br i1 %cmp1, label %for.body.lr.ph, label %for.end
    161 
    162 for.body.lr.ph:                                   ; preds = %entry
    163   br label %for.body
    164 
    165 for.body:                                         ; preds = %for.body.lr.ph, %for.body
    166   %storemerge2 = phi i32 [ 0, %for.body.lr.ph ], [ %inc, %for.body ]
    167   %idxprom = sext i32 %storemerge2 to i64
    168   %arrayidx = getelementptr inbounds float, float* %a, i64 %idxprom
    169   store float 0.000000e+00, float* %arrayidx, align 4, !tbaa !3
    170   %0 = load i32, i32* %gi, align 4, !tbaa !0
    171   %inc = add nsw i32 %0, 1
    172   store i32 %inc, i32* %gi, align 4, !tbaa !0
    173   %cmp = icmp slt i32 %inc, %n
    174   br i1 %cmp, label %for.body, label %for.cond.for.end_crit_edge
    175 
    176 for.cond.for.end_crit_edge:                       ; preds = %for.body
    177   br label %for.end
    178 
    179 for.end:                                          ; preds = %for.cond.for.end_crit_edge, %entry
    180   ret void
    181 
    182 ; CHECK: for.body.lr.ph:
    183 ; CHECK-NEXT:  %gi.promoted = load i32, i32* %gi, align 4, !tbaa !0
    184 ; CHECK: for.cond.for.end_crit_edge:
    185 ; CHECK-NEXT:  %[[LCSSAPHI:.*]] = phi i32 [ %inc
    186 ; CHECK-NEXT:  store i32 %[[LCSSAPHI]], i32* %gi, align 4, !tbaa !0
    187 }
    188 
    189 !0 = !{!4, !4, i64 0}
    190 !1 = !{!"omnipotent char", !2}
    191 !2 = !{!"Simple C/C++ TBAA"}
    192 !3 = !{!5, !5, i64 0}
    193 !4 = !{!"int", !1}
    194 !5 = !{!"float", !1}
    195