ELF: Have __rela_iplt_{start,end} surround .rela.iplt with --pack-dyn-relocs=android.
[llvm-project.git] / llvm / test / CodeGen / LoongArch / ctlz-cttz-ctpop.ll
blob161ed573c81f02ebcef7d2029cb211e83c7ce6b1
1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc --mtriple=loongarch32 -mattr=+d < %s | FileCheck %s --check-prefix=LA32
3 ; RUN: llc --mtriple=loongarch64 -mattr=+d < %s | FileCheck %s --check-prefix=LA64
5 declare i8 @llvm.ctlz.i8(i8, i1)
6 declare i16 @llvm.ctlz.i16(i16, i1)
7 declare i32 @llvm.ctlz.i32(i32, i1)
8 declare i64 @llvm.ctlz.i64(i64, i1)
9 declare i8 @llvm.ctpop.i8(i8)
10 declare i16 @llvm.ctpop.i16(i16)
11 declare i32 @llvm.ctpop.i32(i32)
12 declare i64 @llvm.ctpop.i64(i64)
13 declare i8 @llvm.cttz.i8(i8, i1)
14 declare i16 @llvm.cttz.i16(i16, i1)
15 declare i32 @llvm.cttz.i32(i32, i1)
16 declare i64 @llvm.cttz.i64(i64, i1)
18 define i8 @test_ctlz_i8(i8 %a) nounwind {
19 ; LA32-LABEL: test_ctlz_i8:
20 ; LA32:       # %bb.0:
21 ; LA32-NEXT:    andi $a0, $a0, 255
22 ; LA32-NEXT:    clz.w $a0, $a0
23 ; LA32-NEXT:    addi.w $a0, $a0, -24
24 ; LA32-NEXT:    ret
26 ; LA64-LABEL: test_ctlz_i8:
27 ; LA64:       # %bb.0:
28 ; LA64-NEXT:    andi $a0, $a0, 255
29 ; LA64-NEXT:    clz.d $a0, $a0
30 ; LA64-NEXT:    addi.d $a0, $a0, -56
31 ; LA64-NEXT:    ret
32   %tmp = call i8 @llvm.ctlz.i8(i8 %a, i1 false)
33   ret i8 %tmp
36 define i16 @test_ctlz_i16(i16 %a) nounwind {
37 ; LA32-LABEL: test_ctlz_i16:
38 ; LA32:       # %bb.0:
39 ; LA32-NEXT:    bstrpick.w $a0, $a0, 15, 0
40 ; LA32-NEXT:    clz.w $a0, $a0
41 ; LA32-NEXT:    addi.w $a0, $a0, -16
42 ; LA32-NEXT:    ret
44 ; LA64-LABEL: test_ctlz_i16:
45 ; LA64:       # %bb.0:
46 ; LA64-NEXT:    bstrpick.d $a0, $a0, 15, 0
47 ; LA64-NEXT:    clz.d $a0, $a0
48 ; LA64-NEXT:    addi.d $a0, $a0, -48
49 ; LA64-NEXT:    ret
50   %tmp = call i16 @llvm.ctlz.i16(i16 %a, i1 false)
51   ret i16 %tmp
54 define i32 @test_ctlz_i32(i32 %a) nounwind {
55 ; LA32-LABEL: test_ctlz_i32:
56 ; LA32:       # %bb.0:
57 ; LA32-NEXT:    clz.w $a0, $a0
58 ; LA32-NEXT:    ret
60 ; LA64-LABEL: test_ctlz_i32:
61 ; LA64:       # %bb.0:
62 ; LA64-NEXT:    clz.w $a0, $a0
63 ; LA64-NEXT:    ret
64   %tmp = call i32 @llvm.ctlz.i32(i32 %a, i1 false)
65   ret i32 %tmp
68 define i64 @test_ctlz_i64(i64 %a) nounwind {
69 ; LA32-LABEL: test_ctlz_i64:
70 ; LA32:       # %bb.0:
71 ; LA32-NEXT:    sltu $a2, $zero, $a1
72 ; LA32-NEXT:    clz.w $a1, $a1
73 ; LA32-NEXT:    maskeqz $a1, $a1, $a2
74 ; LA32-NEXT:    clz.w $a0, $a0
75 ; LA32-NEXT:    addi.w $a0, $a0, 32
76 ; LA32-NEXT:    masknez $a0, $a0, $a2
77 ; LA32-NEXT:    or $a0, $a1, $a0
78 ; LA32-NEXT:    move $a1, $zero
79 ; LA32-NEXT:    ret
81 ; LA64-LABEL: test_ctlz_i64:
82 ; LA64:       # %bb.0:
83 ; LA64-NEXT:    clz.d $a0, $a0
84 ; LA64-NEXT:    ret
85   %tmp = call i64 @llvm.ctlz.i64(i64 %a, i1 false)
86   ret i64 %tmp
89 define i8 @test_not_ctlz_i8(i8 %a) nounwind {
90 ; LA32-LABEL: test_not_ctlz_i8:
91 ; LA32:       # %bb.0:
92 ; LA32-NEXT:    slli.w $a0, $a0, 24
93 ; LA32-NEXT:    clo.w $a0, $a0
94 ; LA32-NEXT:    ret
96 ; LA64-LABEL: test_not_ctlz_i8:
97 ; LA64:       # %bb.0:
98 ; LA64-NEXT:    slli.d $a0, $a0, 56
99 ; LA64-NEXT:    clo.d $a0, $a0
100 ; LA64-NEXT:    ret
101   %neg = xor i8 %a, -1
102   %tmp = call i8 @llvm.ctlz.i8(i8 %neg, i1 false)
103   ret i8 %tmp
106 define i16 @test_not_ctlz_i16(i16 %a) nounwind {
107 ; LA32-LABEL: test_not_ctlz_i16:
108 ; LA32:       # %bb.0:
109 ; LA32-NEXT:    slli.w $a0, $a0, 16
110 ; LA32-NEXT:    clo.w $a0, $a0
111 ; LA32-NEXT:    ret
113 ; LA64-LABEL: test_not_ctlz_i16:
114 ; LA64:       # %bb.0:
115 ; LA64-NEXT:    slli.d $a0, $a0, 48
116 ; LA64-NEXT:    clo.d $a0, $a0
117 ; LA64-NEXT:    ret
118   %neg = xor i16 %a, -1
119   %tmp = call i16 @llvm.ctlz.i16(i16 %neg, i1 false)
120   ret i16 %tmp
123 define i32 @test_not_ctlz_i32(i32 %a) nounwind {
124 ; LA32-LABEL: test_not_ctlz_i32:
125 ; LA32:       # %bb.0:
126 ; LA32-NEXT:    clo.w $a0, $a0
127 ; LA32-NEXT:    ret
129 ; LA64-LABEL: test_not_ctlz_i32:
130 ; LA64:       # %bb.0:
131 ; LA64-NEXT:    clo.w $a0, $a0
132 ; LA64-NEXT:    ret
133   %neg = xor i32 %a, -1
134   %tmp = call i32 @llvm.ctlz.i32(i32 %neg, i1 false)
135   ret i32 %tmp
138 define i64 @test_not_ctlz_i64(i64 %a) nounwind {
139 ; LA32-LABEL: test_not_ctlz_i64:
140 ; LA32:       # %bb.0:
141 ; LA32-NEXT:    nor $a2, $a1, $zero
142 ; LA32-NEXT:    sltu $a2, $zero, $a2
143 ; LA32-NEXT:    clo.w $a0, $a0
144 ; LA32-NEXT:    addi.w $a0, $a0, 32
145 ; LA32-NEXT:    masknez $a0, $a0, $a2
146 ; LA32-NEXT:    clo.w $a1, $a1
147 ; LA32-NEXT:    maskeqz $a1, $a1, $a2
148 ; LA32-NEXT:    or $a0, $a1, $a0
149 ; LA32-NEXT:    move $a1, $zero
150 ; LA32-NEXT:    ret
152 ; LA64-LABEL: test_not_ctlz_i64:
153 ; LA64:       # %bb.0:
154 ; LA64-NEXT:    clo.d $a0, $a0
155 ; LA64-NEXT:    ret
156   %neg = xor i64 %a, -1
157   %tmp = call i64 @llvm.ctlz.i64(i64 %neg, i1 false)
158   ret i64 %tmp
161 define i8 @test_ctpop_i8(i8 %a) nounwind {
162 ; LA32-LABEL: test_ctpop_i8:
163 ; LA32:       # %bb.0:
164 ; LA32-NEXT:    srli.w $a1, $a0, 1
165 ; LA32-NEXT:    andi $a1, $a1, 85
166 ; LA32-NEXT:    sub.w $a0, $a0, $a1
167 ; LA32-NEXT:    andi $a1, $a0, 51
168 ; LA32-NEXT:    srli.w $a0, $a0, 2
169 ; LA32-NEXT:    andi $a0, $a0, 51
170 ; LA32-NEXT:    add.w $a0, $a1, $a0
171 ; LA32-NEXT:    srli.w $a1, $a0, 4
172 ; LA32-NEXT:    add.w $a0, $a0, $a1
173 ; LA32-NEXT:    andi $a0, $a0, 15
174 ; LA32-NEXT:    ret
176 ; LA64-LABEL: test_ctpop_i8:
177 ; LA64:       # %bb.0:
178 ; LA64-NEXT:    andi $a0, $a0, 255
179 ; LA64-NEXT:    vldi $vr0, 0
180 ; LA64-NEXT:    vinsgr2vr.d $vr0, $a0, 0
181 ; LA64-NEXT:    vpcnt.d $vr0, $vr0
182 ; LA64-NEXT:    vpickve2gr.d $a0, $vr0, 0
183 ; LA64-NEXT:    ret
184   %1 = call i8 @llvm.ctpop.i8(i8 %a)
185   ret i8 %1
188 define i16 @test_ctpop_i16(i16 %a) nounwind {
189 ; LA32-LABEL: test_ctpop_i16:
190 ; LA32:       # %bb.0:
191 ; LA32-NEXT:    srli.w $a1, $a0, 1
192 ; LA32-NEXT:    lu12i.w $a2, 5
193 ; LA32-NEXT:    ori $a2, $a2, 1365
194 ; LA32-NEXT:    and $a1, $a1, $a2
195 ; LA32-NEXT:    sub.w $a0, $a0, $a1
196 ; LA32-NEXT:    lu12i.w $a1, 3
197 ; LA32-NEXT:    ori $a1, $a1, 819
198 ; LA32-NEXT:    and $a2, $a0, $a1
199 ; LA32-NEXT:    srli.w $a0, $a0, 2
200 ; LA32-NEXT:    and $a0, $a0, $a1
201 ; LA32-NEXT:    add.w $a0, $a2, $a0
202 ; LA32-NEXT:    srli.w $a1, $a0, 4
203 ; LA32-NEXT:    add.w $a0, $a0, $a1
204 ; LA32-NEXT:    bstrpick.w $a1, $a0, 11, 8
205 ; LA32-NEXT:    andi $a0, $a0, 15
206 ; LA32-NEXT:    add.w $a0, $a0, $a1
207 ; LA32-NEXT:    ret
209 ; LA64-LABEL: test_ctpop_i16:
210 ; LA64:       # %bb.0:
211 ; LA64-NEXT:    bstrpick.d $a0, $a0, 15, 0
212 ; LA64-NEXT:    vldi $vr0, 0
213 ; LA64-NEXT:    vinsgr2vr.d $vr0, $a0, 0
214 ; LA64-NEXT:    vpcnt.d $vr0, $vr0
215 ; LA64-NEXT:    vpickve2gr.d $a0, $vr0, 0
216 ; LA64-NEXT:    ret
217   %1 = call i16 @llvm.ctpop.i16(i16 %a)
218   ret i16 %1
221 define i32 @test_ctpop_i32(i32 %a) nounwind {
222 ; LA32-LABEL: test_ctpop_i32:
223 ; LA32:       # %bb.0:
224 ; LA32-NEXT:    srli.w $a1, $a0, 1
225 ; LA32-NEXT:    lu12i.w $a2, 349525
226 ; LA32-NEXT:    ori $a2, $a2, 1365
227 ; LA32-NEXT:    and $a1, $a1, $a2
228 ; LA32-NEXT:    sub.w $a0, $a0, $a1
229 ; LA32-NEXT:    lu12i.w $a1, 209715
230 ; LA32-NEXT:    ori $a1, $a1, 819
231 ; LA32-NEXT:    and $a2, $a0, $a1
232 ; LA32-NEXT:    srli.w $a0, $a0, 2
233 ; LA32-NEXT:    and $a0, $a0, $a1
234 ; LA32-NEXT:    add.w $a0, $a2, $a0
235 ; LA32-NEXT:    srli.w $a1, $a0, 4
236 ; LA32-NEXT:    add.w $a0, $a0, $a1
237 ; LA32-NEXT:    lu12i.w $a1, 61680
238 ; LA32-NEXT:    ori $a1, $a1, 3855
239 ; LA32-NEXT:    and $a0, $a0, $a1
240 ; LA32-NEXT:    lu12i.w $a1, 4112
241 ; LA32-NEXT:    ori $a1, $a1, 257
242 ; LA32-NEXT:    mul.w $a0, $a0, $a1
243 ; LA32-NEXT:    srli.w $a0, $a0, 24
244 ; LA32-NEXT:    ret
246 ; LA64-LABEL: test_ctpop_i32:
247 ; LA64:       # %bb.0:
248 ; LA64-NEXT:    bstrpick.d $a0, $a0, 31, 0
249 ; LA64-NEXT:    vldi $vr0, 0
250 ; LA64-NEXT:    vinsgr2vr.d $vr0, $a0, 0
251 ; LA64-NEXT:    vpcnt.d $vr0, $vr0
252 ; LA64-NEXT:    vpickve2gr.d $a0, $vr0, 0
253 ; LA64-NEXT:    ret
254   %1 = call i32 @llvm.ctpop.i32(i32 %a)
255   ret i32 %1
258 define i64 @test_ctpop_i64(i64 %a) nounwind {
259 ; LA32-LABEL: test_ctpop_i64:
260 ; LA32:       # %bb.0:
261 ; LA32-NEXT:    srli.w $a2, $a1, 1
262 ; LA32-NEXT:    lu12i.w $a3, 349525
263 ; LA32-NEXT:    ori $a3, $a3, 1365
264 ; LA32-NEXT:    and $a2, $a2, $a3
265 ; LA32-NEXT:    sub.w $a1, $a1, $a2
266 ; LA32-NEXT:    lu12i.w $a2, 209715
267 ; LA32-NEXT:    ori $a2, $a2, 819
268 ; LA32-NEXT:    and $a4, $a1, $a2
269 ; LA32-NEXT:    srli.w $a1, $a1, 2
270 ; LA32-NEXT:    and $a1, $a1, $a2
271 ; LA32-NEXT:    add.w $a1, $a4, $a1
272 ; LA32-NEXT:    srli.w $a4, $a1, 4
273 ; LA32-NEXT:    add.w $a1, $a1, $a4
274 ; LA32-NEXT:    lu12i.w $a4, 61680
275 ; LA32-NEXT:    ori $a4, $a4, 3855
276 ; LA32-NEXT:    and $a1, $a1, $a4
277 ; LA32-NEXT:    lu12i.w $a5, 4112
278 ; LA32-NEXT:    ori $a5, $a5, 257
279 ; LA32-NEXT:    mul.w $a1, $a1, $a5
280 ; LA32-NEXT:    srli.w $a1, $a1, 24
281 ; LA32-NEXT:    srli.w $a6, $a0, 1
282 ; LA32-NEXT:    and $a3, $a6, $a3
283 ; LA32-NEXT:    sub.w $a0, $a0, $a3
284 ; LA32-NEXT:    and $a3, $a0, $a2
285 ; LA32-NEXT:    srli.w $a0, $a0, 2
286 ; LA32-NEXT:    and $a0, $a0, $a2
287 ; LA32-NEXT:    add.w $a0, $a3, $a0
288 ; LA32-NEXT:    srli.w $a2, $a0, 4
289 ; LA32-NEXT:    add.w $a0, $a0, $a2
290 ; LA32-NEXT:    and $a0, $a0, $a4
291 ; LA32-NEXT:    mul.w $a0, $a0, $a5
292 ; LA32-NEXT:    srli.w $a0, $a0, 24
293 ; LA32-NEXT:    add.w $a0, $a0, $a1
294 ; LA32-NEXT:    move $a1, $zero
295 ; LA32-NEXT:    ret
297 ; LA64-LABEL: test_ctpop_i64:
298 ; LA64:       # %bb.0:
299 ; LA64-NEXT:    vldi $vr0, 0
300 ; LA64-NEXT:    vinsgr2vr.d $vr0, $a0, 0
301 ; LA64-NEXT:    vpcnt.d $vr0, $vr0
302 ; LA64-NEXT:    vpickve2gr.d $a0, $vr0, 0
303 ; LA64-NEXT:    ret
304   %1 = call i64 @llvm.ctpop.i64(i64 %a)
305   ret i64 %1
308 define i8 @test_cttz_i8(i8 %a) nounwind {
309 ; LA32-LABEL: test_cttz_i8:
310 ; LA32:       # %bb.0:
311 ; LA32-NEXT:    ori $a0, $a0, 256
312 ; LA32-NEXT:    ctz.w $a0, $a0
313 ; LA32-NEXT:    ret
315 ; LA64-LABEL: test_cttz_i8:
316 ; LA64:       # %bb.0:
317 ; LA64-NEXT:    ori $a0, $a0, 256
318 ; LA64-NEXT:    ctz.d $a0, $a0
319 ; LA64-NEXT:    ret
320   %tmp = call i8 @llvm.cttz.i8(i8 %a, i1 false)
321   ret i8 %tmp
324 define i16 @test_cttz_i16(i16 %a) nounwind {
325 ; LA32-LABEL: test_cttz_i16:
326 ; LA32:       # %bb.0:
327 ; LA32-NEXT:    lu12i.w $a1, 16
328 ; LA32-NEXT:    or $a0, $a0, $a1
329 ; LA32-NEXT:    ctz.w $a0, $a0
330 ; LA32-NEXT:    ret
332 ; LA64-LABEL: test_cttz_i16:
333 ; LA64:       # %bb.0:
334 ; LA64-NEXT:    lu12i.w $a1, 16
335 ; LA64-NEXT:    or $a0, $a0, $a1
336 ; LA64-NEXT:    ctz.d $a0, $a0
337 ; LA64-NEXT:    ret
338   %tmp = call i16 @llvm.cttz.i16(i16 %a, i1 false)
339   ret i16 %tmp
342 define i32 @test_cttz_i32(i32 %a) nounwind {
343 ; LA32-LABEL: test_cttz_i32:
344 ; LA32:       # %bb.0:
345 ; LA32-NEXT:    ctz.w $a0, $a0
346 ; LA32-NEXT:    ret
348 ; LA64-LABEL: test_cttz_i32:
349 ; LA64:       # %bb.0:
350 ; LA64-NEXT:    ctz.w $a0, $a0
351 ; LA64-NEXT:    ret
352   %tmp = call i32 @llvm.cttz.i32(i32 %a, i1 false)
353   ret i32 %tmp
356 define i64 @test_cttz_i64(i64 %a) nounwind {
357 ; LA32-LABEL: test_cttz_i64:
358 ; LA32:       # %bb.0:
359 ; LA32-NEXT:    sltu $a2, $zero, $a0
360 ; LA32-NEXT:    ctz.w $a0, $a0
361 ; LA32-NEXT:    maskeqz $a0, $a0, $a2
362 ; LA32-NEXT:    ctz.w $a1, $a1
363 ; LA32-NEXT:    addi.w $a1, $a1, 32
364 ; LA32-NEXT:    masknez $a1, $a1, $a2
365 ; LA32-NEXT:    or $a0, $a0, $a1
366 ; LA32-NEXT:    move $a1, $zero
367 ; LA32-NEXT:    ret
369 ; LA64-LABEL: test_cttz_i64:
370 ; LA64:       # %bb.0:
371 ; LA64-NEXT:    ctz.d $a0, $a0
372 ; LA64-NEXT:    ret
373   %tmp = call i64 @llvm.cttz.i64(i64 %a, i1 false)
374   ret i64 %tmp
377 define i8 @test_not_cttz_i8(i8 %a) nounwind {
378 ; LA32-LABEL: test_not_cttz_i8:
379 ; LA32:       # %bb.0:
380 ; LA32-NEXT:    ori $a1, $zero, 256
381 ; LA32-NEXT:    orn $a0, $a1, $a0
382 ; LA32-NEXT:    ctz.w $a0, $a0
383 ; LA32-NEXT:    ret
385 ; LA64-LABEL: test_not_cttz_i8:
386 ; LA64:       # %bb.0:
387 ; LA64-NEXT:    ori $a1, $zero, 256
388 ; LA64-NEXT:    orn $a0, $a1, $a0
389 ; LA64-NEXT:    ctz.d $a0, $a0
390 ; LA64-NEXT:    ret
391   %neg = xor i8 %a, -1
392   %tmp = call i8 @llvm.cttz.i8(i8 %neg, i1 false)
393   ret i8 %tmp
396 define i16 @test_not_cttz_i16(i16 %a) nounwind {
397 ; LA32-LABEL: test_not_cttz_i16:
398 ; LA32:       # %bb.0:
399 ; LA32-NEXT:    lu12i.w $a1, 16
400 ; LA32-NEXT:    orn $a0, $a1, $a0
401 ; LA32-NEXT:    ctz.w $a0, $a0
402 ; LA32-NEXT:    ret
404 ; LA64-LABEL: test_not_cttz_i16:
405 ; LA64:       # %bb.0:
406 ; LA64-NEXT:    lu12i.w $a1, 16
407 ; LA64-NEXT:    orn $a0, $a1, $a0
408 ; LA64-NEXT:    ctz.d $a0, $a0
409 ; LA64-NEXT:    ret
410   %neg = xor i16 %a, -1
411   %tmp = call i16 @llvm.cttz.i16(i16 %neg, i1 false)
412   ret i16 %tmp
415 define i32 @test_not_cttz_i32(i32 %a) nounwind {
416 ; LA32-LABEL: test_not_cttz_i32:
417 ; LA32:       # %bb.0:
418 ; LA32-NEXT:    cto.w $a0, $a0
419 ; LA32-NEXT:    ret
421 ; LA64-LABEL: test_not_cttz_i32:
422 ; LA64:       # %bb.0:
423 ; LA64-NEXT:    cto.w $a0, $a0
424 ; LA64-NEXT:    ret
425   %neg = xor i32 %a, -1
426   %tmp = call i32 @llvm.cttz.i32(i32 %neg, i1 false)
427   ret i32 %tmp
430 define i64 @test_not_cttz_i64(i64 %a) nounwind {
431 ; LA32-LABEL: test_not_cttz_i64:
432 ; LA32:       # %bb.0:
433 ; LA32-NEXT:    nor $a2, $a0, $zero
434 ; LA32-NEXT:    sltu $a2, $zero, $a2
435 ; LA32-NEXT:    cto.w $a1, $a1
436 ; LA32-NEXT:    addi.w $a1, $a1, 32
437 ; LA32-NEXT:    masknez $a1, $a1, $a2
438 ; LA32-NEXT:    cto.w $a0, $a0
439 ; LA32-NEXT:    maskeqz $a0, $a0, $a2
440 ; LA32-NEXT:    or $a0, $a0, $a1
441 ; LA32-NEXT:    move $a1, $zero
442 ; LA32-NEXT:    ret
444 ; LA64-LABEL: test_not_cttz_i64:
445 ; LA64:       # %bb.0:
446 ; LA64-NEXT:    cto.d $a0, $a0
447 ; LA64-NEXT:    ret
448   %neg = xor i64 %a, -1
449   %tmp = call i64 @llvm.cttz.i64(i64 %neg, i1 false)
450   ret i64 %tmp