[ORC] Add std::tuple support to SimplePackedSerialization.
[llvm-project.git] / llvm / test / CodeGen / Thumb2 / mve-tailpred-loopinvariant.ll
blobce79c46a32c291225b57899c17511ac182c0de67
1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc -mtriple=thumbv8.1m.main-none-none-eabi -mattr=+mve -verify-machineinstrs %s -o - | FileCheck %s
4 ; This test has an instruction that gets sunk into the loop, that is a
5 ; active.lane.mask operand. (%exitcount.ptrcnt.to.int = ptrtoint). We
6 ; need to make sure it is loop invariant.
8 define i32 @a(i32* readnone %b, i8* %c) {
9 ; CHECK-LABEL: a:
10 ; CHECK:       @ %bb.0: @ %entry
11 ; CHECK-NEXT:    .save {r4, lr}
12 ; CHECK-NEXT:    push {r4, lr}
13 ; CHECK-NEXT:    cmp r0, r1
14 ; CHECK-NEXT:    it ls
15 ; CHECK-NEXT:    popls {r4, pc}
16 ; CHECK-NEXT:  .LBB0_1: @ %while.body.preheader
17 ; CHECK-NEXT:    subs r4, r0, r1
18 ; CHECK-NEXT:    movs r2, #0
19 ; CHECK-NEXT:    mov r3, r1
20 ; CHECK-NEXT:    dlstp.8 lr, r4
21 ; CHECK-NEXT:  .LBB0_2: @ %vector.body
22 ; CHECK-NEXT:    @ =>This Inner Loop Header: Depth=1
23 ; CHECK-NEXT:    adds r0, r1, r2
24 ; CHECK-NEXT:    adds r2, #16
25 ; CHECK-NEXT:    vidup.u8 q0, r0, #1
26 ; CHECK-NEXT:    vstrb.8 q0, [r3], #16
27 ; CHECK-NEXT:    letp lr, .LBB0_2
28 ; CHECK-NEXT:  @ %bb.3: @ %while.end
29 ; CHECK-NEXT:    pop {r4, pc}
30 entry:
31   %0 = bitcast i32* %b to i8*
32   %cmp3 = icmp ugt i8* %0, %c
33   br i1 %cmp3, label %while.body.preheader, label %while.end
35 while.body.preheader:                             ; preds = %entry
36   %c5 = ptrtoint i8* %c to i32
37   %1 = sub i32 0, %c5
38   %uglygep = getelementptr i8, i8* %0, i32 %1
39   %exitcount.ptrcnt.to.int = ptrtoint i8* %uglygep to i32
40   %n.rnd.up = add i32 %exitcount.ptrcnt.to.int, 15
41   %n.vec = and i32 %n.rnd.up, -16
42   br label %vector.body
44 vector.body:                                      ; preds = %vector.body, %while.body.preheader
45   %index = phi i32 [ 0, %while.body.preheader ], [ %index.next, %vector.body ]
46   %next.gep = getelementptr i8, i8* %c, i32 %index
47   %2 = or i32 %index, 1
48   %next.gep7 = getelementptr i8, i8* %c, i32 %2
49   %3 = or i32 %index, 2
50   %next.gep8 = getelementptr i8, i8* %c, i32 %3
51   %4 = or i32 %index, 3
52   %next.gep9 = getelementptr i8, i8* %c, i32 %4
53   %5 = or i32 %index, 4
54   %next.gep10 = getelementptr i8, i8* %c, i32 %5
55   %6 = or i32 %index, 5
56   %next.gep11 = getelementptr i8, i8* %c, i32 %6
57   %7 = or i32 %index, 6
58   %next.gep12 = getelementptr i8, i8* %c, i32 %7
59   %8 = or i32 %index, 7
60   %next.gep13 = getelementptr i8, i8* %c, i32 %8
61   %9 = or i32 %index, 8
62   %next.gep14 = getelementptr i8, i8* %c, i32 %9
63   %10 = or i32 %index, 9
64   %next.gep15 = getelementptr i8, i8* %c, i32 %10
65   %11 = or i32 %index, 10
66   %next.gep16 = getelementptr i8, i8* %c, i32 %11
67   %12 = or i32 %index, 11
68   %next.gep17 = getelementptr i8, i8* %c, i32 %12
69   %13 = or i32 %index, 12
70   %next.gep18 = getelementptr i8, i8* %c, i32 %13
71   %14 = or i32 %index, 13
72   %next.gep19 = getelementptr i8, i8* %c, i32 %14
73   %15 = or i32 %index, 14
74   %next.gep20 = getelementptr i8, i8* %c, i32 %15
75   %16 = or i32 %index, 15
76   %next.gep21 = getelementptr i8, i8* %c, i32 %16
77   %17 = insertelement <16 x i8*> poison, i8* %next.gep, i32 0
78   %18 = insertelement <16 x i8*> %17, i8* %next.gep7, i32 1
79   %19 = insertelement <16 x i8*> %18, i8* %next.gep8, i32 2
80   %20 = insertelement <16 x i8*> %19, i8* %next.gep9, i32 3
81   %21 = insertelement <16 x i8*> %20, i8* %next.gep10, i32 4
82   %22 = insertelement <16 x i8*> %21, i8* %next.gep11, i32 5
83   %23 = insertelement <16 x i8*> %22, i8* %next.gep12, i32 6
84   %24 = insertelement <16 x i8*> %23, i8* %next.gep13, i32 7
85   %25 = insertelement <16 x i8*> %24, i8* %next.gep14, i32 8
86   %26 = insertelement <16 x i8*> %25, i8* %next.gep15, i32 9
87   %27 = insertelement <16 x i8*> %26, i8* %next.gep16, i32 10
88   %28 = insertelement <16 x i8*> %27, i8* %next.gep17, i32 11
89   %29 = insertelement <16 x i8*> %28, i8* %next.gep18, i32 12
90   %30 = insertelement <16 x i8*> %29, i8* %next.gep19, i32 13
91   %31 = insertelement <16 x i8*> %30, i8* %next.gep20, i32 14
92   %32 = insertelement <16 x i8*> %31, i8* %next.gep21, i32 15
93   %active.lane.mask = call <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32 %index, i32 %exitcount.ptrcnt.to.int)
94   %33 = ptrtoint <16 x i8*> %32 to <16 x i32>
95   %34 = trunc <16 x i32> %33 to <16 x i8>
96   %35 = bitcast i8* %next.gep to <16 x i8>*
97   call void @llvm.masked.store.v16i8.p0v16i8(<16 x i8> %34, <16 x i8>* %35, i32 1, <16 x i1> %active.lane.mask)
98   %index.next = add i32 %index, 16
99   %36 = icmp eq i32 %index.next, %n.vec
100   br i1 %36, label %while.end, label %vector.body
102 while.end:                                        ; preds = %vector.body, %entry
103   ret i32 undef
106 declare <16 x i1> @llvm.get.active.lane.mask.v16i1.i32(i32, i32)
107 declare void @llvm.masked.store.v16i8.p0v16i8(<16 x i8>, <16 x i8>*, i32 immarg, <16 x i1>)