Home | History | Annotate | Download | only in llvm2ice_tests
      1 ; Test the the loop nest depth is correctly calculated for basic blocks.
      2 
      3 ; REQUIRES: allow_dump
      4 
      5 ; Single threaded so that the dumps used for checking happen in order.
      6 ; RUN: %p2i --filetype=obj --disassemble -i %s --args -O2 --verbose=loop \
      7 ; RUN:     -log=%t --threads=0 && FileCheck %s < %t
      8 
      9 define internal void @test_single_loop(i32 %a32) {
     10 entry:
     11   %a = trunc i32 %a32 to i1
     12   br label %loop0
     13 
     14 loop0:                               ; <-+
     15   br label %loop1                    ;   |
     16 loop1:                               ;   |
     17   br i1 %a, label %loop0, label %out ; --+
     18 
     19 out:
     20   ret void
     21 }
     22 
     23 ; CHECK-LABEL: After loop analysis
     24 ; CHECK-NEXT: entry:
     25 ; CHECK-NEXT: LoopNestDepth = 0
     26 ; CHECK-NEXT: loop0:
     27 ; CHECK-NEXT: LoopNestDepth = 1
     28 ; CHECK-NEXT: loop1:
     29 ; CHECK-NEXT: LoopNestDepth = 1
     30 ; CHECK-NEXT: out:
     31 ; CHECK-NEXT: LoopNestDepth = 0
     32 ; CHECK-LABEL: Before RMW
     33 
     34 define internal void @test_single_loop_with_continue(i32 %a32, i32 %b32) {
     35 entry:
     36   %a = trunc i32 %a32 to i1
     37   %b = trunc i32 %b32 to i1
     38   br label %loop0
     39 
     40 loop0:                                 ; <-+
     41   br label %loop1                      ;   |
     42 loop1:                                 ;   |
     43   br i1 %a, label %loop0, label %loop2 ; --+
     44 loop2:                                 ;   |
     45   br i1 %b, label %loop0, label %out   ; --+
     46 
     47 out:
     48   ret void
     49 }
     50 
     51 ; CHECK-LABEL: After loop analysis
     52 ; CHECK-NEXT: entry:
     53 ; CHECK-NEXT: LoopNestDepth = 0
     54 ; CHECK-NEXT: loop0:
     55 ; CHECK-NEXT: LoopNestDepth = 1
     56 ; CHECK-NEXT: loop1:
     57 ; CHECK-NEXT: LoopNestDepth = 1
     58 ; CHECK-NEXT: loop2:
     59 ; CHECK-NEXT: LoopNestDepth = 1
     60 ; CHECK-NEXT: out:
     61 ; CHECK-NEXT: LoopNestDepth = 0
     62 ; CHECK-LABEL: Before RMW
     63 
     64 define internal void @test_multiple_exits(i32 %a32, i32 %b32) {
     65 entry:
     66   %a = trunc i32 %a32 to i1
     67   %b = trunc i32 %b32 to i1
     68   br label %loop0
     69 
     70 loop0:                               ; <-+
     71   br label %loop1                    ;   |
     72 loop1:                               ;   |
     73   br i1 %a, label %loop2, label %out ; --+-+
     74 loop2:                               ;   | |
     75   br i1 %b, label %loop0, label %out ; --+ |
     76                                      ;     |
     77 out:                                 ; <---+
     78   ret void
     79 }
     80 
     81 ; CHECK-LABEL: After loop analysis
     82 ; CHECK-NEXT: entry:
     83 ; CHECK-NEXT: LoopNestDepth = 0
     84 ; CHECK-NEXT: loop0:
     85 ; CHECK-NEXT: LoopNestDepth = 1
     86 ; CHECK-NEXT: loop1:
     87 ; CHECK-NEXT: LoopNestDepth = 1
     88 ; CHECK-NEXT: loop2:
     89 ; CHECK-NEXT: LoopNestDepth = 1
     90 ; CHECK-NEXT: out:
     91 ; CHECK-NEXT: LoopNestDepth = 0
     92 ; CHECK-LABEL: Before RMW
     93 
     94 define internal void @test_two_nested_loops(i32 %a32, i32 %b32) {
     95 entry:
     96   %a = trunc i32 %a32 to i1
     97   %b = trunc i32 %b32 to i1
     98   br label %loop0_0
     99 
    100 loop0_0:                                   ; <---+
    101   br label %loop1_0                        ;     |
    102 loop1_0:                                   ; <-+ |
    103   br label %loop1_1                        ;   | |
    104 loop1_1:                                   ;   | |
    105   br i1 %a, label %loop1_0, label %loop0_1 ; --+ |
    106 loop0_1:                                   ;     |
    107   br i1 %b, label %loop0_0, label %out     ; ----+
    108 
    109 out:
    110   ret void
    111 }
    112 
    113 ; CHECK-LABEL: After loop analysis
    114 ; CHECK-NEXT: entry:
    115 ; CHECK-NEXT: LoopNestDepth = 0
    116 ; CHECK-NEXT: loop0_0:
    117 ; CHECK-NEXT: LoopNestDepth = 1
    118 ; CHECK-NEXT: loop1_0:
    119 ; CHECK-NEXT: LoopNestDepth = 2
    120 ; CHECK-NEXT: loop1_1:
    121 ; CHECK-NEXT: LoopNestDepth = 2
    122 ; CHECK-NEXT: loop0_1:
    123 ; CHECK-NEXT: LoopNestDepth = 1
    124 ; CHECK-NEXT: out:
    125 ; CHECK-NEXT: LoopNestDepth = 0
    126 ; CHECK-LABEL: Before RMW
    127 
    128 define internal void @test_two_nested_loops_with_continue(i32 %a32, i32 %b32,
    129                                                           i32 %c32) {
    130 entry:
    131   %a = trunc i32 %a32 to i1
    132   %b = trunc i32 %b32 to i1
    133   %c = trunc i32 %c32 to i1
    134   br label %loop0_0
    135 
    136 loop0_0:                                   ; <---+
    137   br label %loop1_0                        ;     |
    138 loop1_0:                                   ; <-+ |
    139   br label %loop1_1                        ;   | |
    140 loop1_1:                                   ;   | |
    141   br i1 %a, label %loop1_0, label %loop1_2 ; --+ |
    142 loop1_2:                                   ;   | |
    143   br i1 %a, label %loop1_0, label %loop0_1 ; --+ |
    144 loop0_1:                                   ;     |
    145   br i1 %b, label %loop0_0, label %out     ; ----+
    146 
    147 out:
    148   ret void
    149 }
    150 
    151 ; CHECK-LABEL: After loop analysis
    152 ; CHECK-NEXT: entry:
    153 ; CHECK-NEXT: LoopNestDepth = 0
    154 ; CHECK-NEXT: loop0_0:
    155 ; CHECK-NEXT: LoopNestDepth = 1
    156 ; CHECK-NEXT: loop1_0:
    157 ; CHECK-NEXT: LoopNestDepth = 2
    158 ; CHECK-NEXT: loop1_1:
    159 ; CHECK-NEXT: LoopNestDepth = 2
    160 ; CHECK-NEXT: loop1_2:
    161 ; CHECK-NEXT: LoopNestDepth = 2
    162 ; CHECK-NEXT: loop0_1:
    163 ; CHECK-NEXT: LoopNestDepth = 1
    164 ; CHECK-NEXT: out:
    165 ; CHECK-NEXT: LoopNestDepth = 0
    166 ; CHECK-LABEL: Before RMW
    167 
    168 define internal void @test_multiple_nested_loops(i32 %a32, i32 %b32) {
    169 entry:
    170   %a = trunc i32 %a32 to i1
    171   %b = trunc i32 %b32 to i1
    172   br label %loop0_0
    173 
    174 loop0_0:                                   ; <---+
    175   br label %loop1_0                        ;     |
    176 loop1_0:                                   ; <-+ |
    177   br label %loop1_1                        ;   | |
    178 loop1_1:                                   ;   | |
    179   br i1 %a, label %loop1_0, label %loop0_1 ; --+ |
    180 loop0_1:                                   ;     |
    181   br label %loop2_0                        ;     |
    182 loop2_0:                                   ; <-+ |
    183   br label %loop2_1                        ;   | |
    184 loop2_1:                                   ;   | |
    185   br i1 %a, label %loop2_0, label %loop0_2 ; --+ |
    186 loop0_2:                                   ;     |
    187   br i1 %b, label %loop0_0, label %out     ; ----+
    188 
    189 out:
    190   ret void
    191 }
    192 
    193 ; CHECK-LABEL: After loop analysis
    194 ; CHECK-NEXT: entry:
    195 ; CHECK-NEXT: LoopNestDepth = 0
    196 ; CHECK-NEXT: loop0_0:
    197 ; CHECK-NEXT: LoopNestDepth = 1
    198 ; CHECK-NEXT: loop1_0:
    199 ; CHECK-NEXT: LoopNestDepth = 2
    200 ; CHECK-NEXT: loop1_1:
    201 ; CHECK-NEXT: LoopNestDepth = 2
    202 ; CHECK-NEXT: loop0_1:
    203 ; CHECK-NEXT: LoopNestDepth = 1
    204 ; CHECK-NEXT: loop2_0:
    205 ; CHECK-NEXT: LoopNestDepth = 2
    206 ; CHECK-NEXT: loop2_1:
    207 ; CHECK-NEXT: LoopNestDepth = 2
    208 ; CHECK-NEXT: loop0_2:
    209 ; CHECK-NEXT: LoopNestDepth = 1
    210 ; CHECK-NEXT: out:
    211 ; CHECK-NEXT: LoopNestDepth = 0
    212 ; CHECK-LABEL: Before RMW
    213 
    214 define internal void @test_three_nested_loops(i32 %a32, i32 %b32, i32 %c32) {
    215 entry:
    216   %a = trunc i32 %a32 to i1
    217   %b = trunc i32 %b32 to i1
    218   %c = trunc i32 %c32 to i1
    219   br label %loop0_0
    220 
    221 loop0_0:                                   ; <-----+
    222   br label %loop1_0                        ;       |
    223 loop1_0:                                   ; <---+ |
    224   br label %loop2_0                        ;     | |
    225 loop2_0:                                   ; <-+ | |
    226   br label %loop2_1                        ;   | | |
    227 loop2_1:                                   ;   | | |
    228   br i1 %a, label %loop2_0, label %loop1_1 ; --+ | |
    229 loop1_1:                                   ;     | |
    230   br i1 %b, label %loop1_0, label %loop0_1 ; ----+ |
    231 loop0_1:                                   ;       |
    232   br i1 %c, label %loop0_0, label %out     ; ------+
    233 
    234 out:
    235   ret void
    236 }
    237 
    238 ; CHECK-LABEL: After loop analysis
    239 ; CHECK-NEXT: entry:
    240 ; CHECK-NEXT: LoopNestDepth = 0
    241 ; CHECK-NEXT: loop0_0:
    242 ; CHECK-NEXT: LoopNestDepth = 1
    243 ; CHECK-NEXT: loop1_0:
    244 ; CHECK-NEXT: LoopNestDepth = 2
    245 ; CHECK-NEXT: loop2_0:
    246 ; CHECK-NEXT: LoopNestDepth = 3
    247 ; CHECK-NEXT: loop2_1:
    248 ; CHECK-NEXT: LoopNestDepth = 3
    249 ; CHECK-NEXT: loop1_1:
    250 ; CHECK-NEXT: LoopNestDepth = 2
    251 ; CHECK-NEXT: loop0_1:
    252 ; CHECK-NEXT: LoopNestDepth = 1
    253 ; CHECK-NEXT: out:
    254 ; CHECK-NEXT: LoopNestDepth = 0
    255 ; CHECK-LABEL: Before RMW
    256 
    257 define internal void @test_diamond(i32 %a32) {
    258 entry:
    259   %a = trunc i32 %a32 to i1
    260   br i1 %a, label %left, label %right
    261 
    262 left:
    263   br label %out
    264 
    265 right:
    266   br label %out
    267 
    268 out:
    269   ret void
    270 }
    271 
    272 ; CHECK-LABEL: After loop analysis
    273 ; CHECK-NEXT: entry:
    274 ; CHECK-NEXT: LoopNestDepth = 0
    275 ; CHECK-NEXT: left:
    276 ; CHECK-NEXT: LoopNestDepth = 0
    277 ; CHECK-NEXT: right:
    278 ; CHECK-NEXT: LoopNestDepth = 0
    279 ; CHECK-NEXT: out:
    280 ; CHECK-NEXT: LoopNestDepth = 0
    281 ; CHECK-LABEL: Before RMW
    282 
    283 define internal void @test_single_block_loop(i32 %count) {
    284 entry:
    285   br label %body
    286 body:
    287 ;  %i = phi i32 [ 0, %entry ], [ %inc, %body ]
    288 ; A normal loop would have a phi instruction like above for the induction
    289 ; variable, but that may introduce new basic blocks due to phi edge splitting,
    290 ; so we use an alternative definition for %i to make the test more clear.
    291   %i = add i32 %count, 1
    292   %inc = add i32 %i, 1
    293   %cmp = icmp slt i32 %inc, %count
    294   br i1 %cmp, label %body, label %exit
    295 exit:
    296   ret void
    297 }
    298 
    299 ; CHECK-LABEL: After loop analysis
    300 ; CHECK-NEXT: entry:
    301 ; CHECK-NEXT: LoopNestDepth = 0
    302 ; CHECK-NEXT: body:
    303 ; CHECK-NEXT: LoopNestDepth = 1
    304 ; CHECK-NEXT: exit:
    305 ; CHECK-NEXT: LoopNestDepth = 0
    306 ; CHECK-LABEL: Before RMW
    307