1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc < %s -mtriple=aarch64-- | FileCheck %s
4 %struct.anon = type { ptr, ptr }
6 @ptr_wrapper = common global ptr null, align 8
8 define i32 @test_func_i32_two_uses(i32 %in, i32 %bit, i32 %mask) {
9 ; CHECK-LABEL: test_func_i32_two_uses:
10 ; CHECK: // %bb.0: // %entry
11 ; CHECK-NEXT: adrp x8, :got:ptr_wrapper
12 ; CHECK-NEXT: ldr x8, [x8, :got_lo12:ptr_wrapper]
13 ; CHECK-NEXT: ldr x9, [x8]
14 ; CHECK-NEXT: mov w8, wzr
15 ; CHECK-NEXT: b .LBB0_3
16 ; CHECK-NEXT: .LBB0_1: // in Loop: Header=BB0_3 Depth=1
17 ; CHECK-NEXT: str xzr, [x9, #8]
18 ; CHECK-NEXT: .LBB0_2: // in Loop: Header=BB0_3 Depth=1
19 ; CHECK-NEXT: lsl w1, w1, #1
20 ; CHECK-NEXT: cbz w1, .LBB0_6
21 ; CHECK-NEXT: .LBB0_3: // %do.body
22 ; CHECK-NEXT: // =>This Inner Loop Header: Depth=1
23 ; CHECK-NEXT: ands w10, w1, w0
24 ; CHECK-NEXT: and w11, w2, w0
25 ; CHECK-NEXT: cinc w8, w8, ne
26 ; CHECK-NEXT: cmp w10, w11
27 ; CHECK-NEXT: b.eq .LBB0_1
28 ; CHECK-NEXT: // %bb.4: // %do.body
29 ; CHECK-NEXT: // in Loop: Header=BB0_3 Depth=1
30 ; CHECK-NEXT: cbnz w2, .LBB0_1
31 ; CHECK-NEXT: // %bb.5: // %do.body
32 ; CHECK-NEXT: // in Loop: Header=BB0_3 Depth=1
33 ; CHECK-NEXT: cbz w10, .LBB0_2
34 ; CHECK-NEXT: b .LBB0_1
35 ; CHECK-NEXT: .LBB0_6: // %do.end
36 ; CHECK-NEXT: mov w0, w8
39 %0 = load ptr, ptr @ptr_wrapper, align 8
40 %result = getelementptr inbounds %struct.anon, ptr %0, i64 0, i32 1
41 %tobool2 = icmp ne i32 %mask, 0
44 do.body: ; preds = %4, %entry
45 %bit.addr.0 = phi i32 [ %bit, %entry ], [ %shl, %4 ]
46 %retval1.0 = phi i32 [ 0, %entry ], [ %retval1.1, %4 ]
47 %and = and i32 %bit.addr.0, %in
48 %tobool = icmp eq i32 %and, 0
49 %not.tobool = xor i1 %tobool, true
50 %inc = zext i1 %not.tobool to i32
51 %retval1.1 = add nuw nsw i32 %retval1.0, %inc
52 %1 = xor i1 %tobool, true
53 %2 = or i1 %tobool2, %1
54 %dummy = and i32 %mask, %in
55 %use_and = icmp eq i32 %and, %dummy
56 %dummy_or = or i1 %use_and, %2
57 br i1 %dummy_or, label %3, label %4
60 store ptr null, ptr %result, align 8
63 4: ; preds = %do.body, %3
64 %shl = shl i32 %bit.addr.0, 1
65 %tobool6 = icmp eq i32 %shl, 0
66 br i1 %tobool6, label %do.end, label %do.body
72 define i32 @test_func_i64_one_use(i64 %in, i64 %bit, i64 %mask) {
73 ; CHECK-LABEL: test_func_i64_one_use:
74 ; CHECK: // %bb.0: // %entry
75 ; CHECK-NEXT: adrp x8, :got:ptr_wrapper
76 ; CHECK-NEXT: ldr x8, [x8, :got_lo12:ptr_wrapper]
77 ; CHECK-NEXT: ldr x9, [x8]
78 ; CHECK-NEXT: mov w8, wzr
79 ; CHECK-NEXT: b .LBB1_2
80 ; CHECK-NEXT: .LBB1_1: // in Loop: Header=BB1_2 Depth=1
81 ; CHECK-NEXT: lsl x1, x1, #1
82 ; CHECK-NEXT: cbz x1, .LBB1_4
83 ; CHECK-NEXT: .LBB1_2: // %do.body
84 ; CHECK-NEXT: // =>This Inner Loop Header: Depth=1
85 ; CHECK-NEXT: ands x10, x1, x0
86 ; CHECK-NEXT: orr x10, x2, x10
87 ; CHECK-NEXT: cinc w8, w8, ne
88 ; CHECK-NEXT: cbz x10, .LBB1_1
89 ; CHECK-NEXT: // %bb.3: // in Loop: Header=BB1_2 Depth=1
90 ; CHECK-NEXT: str xzr, [x9, #8]
91 ; CHECK-NEXT: b .LBB1_1
92 ; CHECK-NEXT: .LBB1_4: // %do.end
93 ; CHECK-NEXT: mov w0, w8
96 %0 = load ptr, ptr @ptr_wrapper, align 8
97 %result = getelementptr inbounds %struct.anon, ptr %0, i64 0, i32 1
98 %tobool2 = icmp ne i64 %mask, 0
101 do.body: ; preds = %4, %entry
102 %bit.addr.0 = phi i64 [ %bit, %entry ], [ %shl, %4 ]
103 %retval1.0 = phi i32 [ 0, %entry ], [ %retval1.1, %4 ]
104 %and = and i64 %bit.addr.0, %in
105 %tobool = icmp eq i64 %and, 0
106 %not.tobool = xor i1 %tobool, true
107 %inc = zext i1 %not.tobool to i32
108 %retval1.1 = add nuw nsw i32 %retval1.0, %inc
109 %1 = xor i1 %tobool, true
110 %2 = or i1 %tobool2, %1
111 br i1 %2, label %3, label %4
113 3: ; preds = %do.body
114 store ptr null, ptr %result, align 8
117 4: ; preds = %do.body, %3
118 %shl = shl i64 %bit.addr.0, 1
119 %tobool6 = icmp eq i64 %shl, 0
120 br i1 %tobool6, label %do.end, label %do.body
126 define i64 @test_and1(i64 %x, i64 %y) {
127 ; CHECK-LABEL: test_and1:
129 ; CHECK-NEXT: ands x8, x0, #0x3
130 ; CHECK-NEXT: csel x0, x8, x1, eq
133 %c = icmp eq i64 %a, 0
134 %s = select i1 %c, i64 %a, i64 %y
138 define i64 @test_and2(i64 %x, i64 %y) {
139 ; CHECK-LABEL: test_and2:
141 ; CHECK-NEXT: tst x0, #0x3
142 ; CHECK-NEXT: csel x0, x0, x1, eq
145 %c = icmp eq i64 %a, 0
146 %s = select i1 %c, i64 %x, i64 %y
150 define i64 @test_and3(i64 %x, i64 %y) {
151 ; CHECK-LABEL: test_and3:
153 ; CHECK-NEXT: str x30, [sp, #-32]! // 8-byte Folded Spill
154 ; CHECK-NEXT: stp x20, x19, [sp, #16] // 16-byte Folded Spill
155 ; CHECK-NEXT: .cfi_def_cfa_offset 32
156 ; CHECK-NEXT: .cfi_offset w19, -8
157 ; CHECK-NEXT: .cfi_offset w20, -16
158 ; CHECK-NEXT: .cfi_offset w30, -32
159 ; CHECK-NEXT: mov x20, x0
160 ; CHECK-NEXT: mov x0, xzr
161 ; CHECK-NEXT: mov x19, x1
162 ; CHECK-NEXT: bl callee
163 ; CHECK-NEXT: ands x8, x20, #0x3
164 ; CHECK-NEXT: csel x0, x8, x19, eq
165 ; CHECK-NEXT: ldp x20, x19, [sp, #16] // 16-byte Folded Reload
166 ; CHECK-NEXT: ldr x30, [sp], #32 // 8-byte Folded Reload
169 %b = call i64 @callee(i64 0)
170 %c = icmp eq i64 %a, 0
171 %s = select i1 %c, i64 %a, i64 %y
175 define i64 @test_and_4(i64 %x, i64 %y) {
176 ; CHECK-LABEL: test_and_4:
178 ; CHECK-NEXT: stp x30, x19, [sp, #-16]! // 16-byte Folded Spill
179 ; CHECK-NEXT: .cfi_def_cfa_offset 16
180 ; CHECK-NEXT: .cfi_offset w19, -8
181 ; CHECK-NEXT: .cfi_offset w30, -16
182 ; CHECK-NEXT: mov x19, x0
183 ; CHECK-NEXT: ands x0, x0, #0x3
184 ; CHECK-NEXT: bl callee
185 ; CHECK-NEXT: ands x8, x19, #0x3
186 ; CHECK-NEXT: csel x0, x8, x0, eq
187 ; CHECK-NEXT: ldp x30, x19, [sp], #16 // 16-byte Folded Reload
190 %b = call i64 @callee(i64 %a)
191 %c = icmp eq i64 %a, 0
192 %s = select i1 %c, i64 %a, i64 %b
196 define i64 @test_add(i64 %x, i64 %y) {
197 ; CHECK-LABEL: test_add:
199 ; CHECK-NEXT: stp x30, x19, [sp, #-16]! // 16-byte Folded Spill
200 ; CHECK-NEXT: .cfi_def_cfa_offset 16
201 ; CHECK-NEXT: .cfi_offset w19, -8
202 ; CHECK-NEXT: .cfi_offset w30, -16
203 ; CHECK-NEXT: add x19, x0, #3
204 ; CHECK-NEXT: mov x0, xzr
205 ; CHECK-NEXT: bl callee
206 ; CHECK-NEXT: cmp x19, #0
207 ; CHECK-NEXT: csel x0, x19, x0, eq
208 ; CHECK-NEXT: ldp x30, x19, [sp], #16 // 16-byte Folded Reload
211 %b = call i64 @callee(i64 0)
212 %c = icmp eq i64 %a, 0
213 %s = select i1 %c, i64 %a, i64 %b
217 declare i64 @callee(i64)