Home | History | Annotate | Download | only in AArch64
      1 ; RUN: llc -mtriple=aarch64 -verify-machineinstrs < %s | FileCheck --check-prefix=CHECK --check-prefix=OPT %s
      2 ; RUN: llc -mtriple=aarch64 -verify-machineinstrs -O0 -fast-isel=0 -global-isel=false < %s | FileCheck --check-prefix=CHECK --check-prefix=NOOPT %s
      3 
      4 declare void @foo()
      5 
      6 ; Check that the inverted or doesn't inhibit the splitting of the
      7 ; complex conditional into three branch instructions.
      8 ; CHECK-LABEL: test_and_not:
      9 ; CHECK:       cbz w0, [[L:\.LBB[0-9_]+]]
     10 ; OPT:         cmp w1, #2
     11 ; NOOPT:       subs w{{[0-9]+}}, w{{[0-9]+}}, #2
     12 ; CHECK:       b.lo [[L]]
     13 ; OPT:         cmp w2, #2
     14 ; NOOPT:       subs w{{[0-9]+}}, w{{[0-9]+}}, #2
     15 ; CHECK:       b.hi [[L]]
     16 define void @test_and_not(i32 %a, i32 %b, i32 %c) {
     17 bb1:
     18   %cmp1 = icmp ult i32 %a, 1
     19   %cmp2 = icmp ult i32 %b, 2
     20   %cmp3 = icmp ult i32 %c, 3
     21   %or = or i1 %cmp1, %cmp2
     22   %not.or = xor i1 %or, -1
     23   %and = and i1 %not.or, %cmp3
     24   br i1 %and, label %bb2, label %bb3
     25 
     26 bb2:
     27   ret void
     28 
     29 bb3:
     30   call void @foo()
     31   ret void
     32 }
     33 
     34 ; Check that non-canonicalized xor not is handled correctly by FindMergedConditions.
     35 ; CHECK-LABEL: test_and_not2:
     36 ; CHECK:       cbz w0, [[L:\.LBB[0-9_]+]]
     37 ; OPT:         cmp w1, #2
     38 ; NOOPT:       subs w{{[0-9]+}}, w{{[0-9]+}}, #2
     39 ; CHECK:       b.lo [[L]]
     40 ; OPT:         cmp w2, #2
     41 ; NOOPT:       subs w{{[0-9]+}}, w{{[0-9]+}}, #2
     42 ; CHECK:       b.hi [[L]]
     43 define void @test_and_not2(i32 %a, i32 %b, i32 %c) {
     44 bb1:
     45   %cmp1 = icmp ult i32 %a, 1
     46   %cmp2 = icmp ult i32 %b, 2
     47   %cmp3 = icmp ult i32 %c, 3
     48   %or = or i1 %cmp1, %cmp2
     49   %not.or = xor i1 -1, %or
     50   %and = and i1 %not.or, %cmp3
     51   br i1 %and, label %bb2, label %bb3
     52 
     53 bb2:
     54   ret void
     55 
     56 bb3:
     57   call void @foo()
     58   ret void
     59 }
     60 
     61 ; Check that cmps in different blocks are handled correctly by FindMergedConditions.
     62 ; CHECK-LABEL: test_cmp_other_block:
     63 ; OPT: cmp w{{[0-9]+}}, #0
     64 ; OPT: b.gt [[L:\.LBB[0-9_]+]]
     65 ; OPT: tbz w1, #0, [[L]]
     66 ;
     67 ; NOOPT: subs w{{[0-9]+}}, w{{[0-9]+}}, #0
     68 ; NOOPT: cset [[R1:w[0-9]+]], gt
     69 ; NOOPT: str w1, [sp, #[[SLOT2:[0-9]+]]]
     70 ; NOOPT: str [[R1]], [sp, #[[SLOT1:[0-9]+]]]
     71 ; NOOPT: b .LBB
     72 ; NOOPT: ldr [[R2:w[0-9]+]], [sp, #[[SLOT1]]]
     73 ; NOOPT: tbnz [[R2]], #0, [[L:\.LBB[0-9_]+]]
     74 ; NOOPT: ldr [[R3:w[0-9]+]], [sp, #[[SLOT2]]]
     75 ; NOOPT: tbz [[R3]], #0, [[L]]
     76 define void @test_cmp_other_block(i32* %p, i1 %c) {
     77 entry:
     78   %l = load i32, i32* %p
     79   %cmp = icmp sgt i32 %l, 0
     80   br label %bb1
     81 
     82 bb1:
     83   %cmp.i = xor i1 %cmp, true
     84   %or.cond1.i = and i1 %cmp.i, %c
     85   br i1 %or.cond1.i, label %bb2, label %bb3
     86 
     87 bb2:
     88   ret void
     89 
     90 bb3:
     91   call void @foo()
     92   ret void
     93 }
     94 
     95