1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc -mtriple=aarch64-unknown-linux-gnu < %s | FileCheck %s
4 ; *Please* keep in sync with test/CodeGen/X86/extract-lowbits.ll
6 ; https://bugs.llvm.org/show_bug.cgi?id=36419
7 ; https://bugs.llvm.org/show_bug.cgi?id=37603
8 ; https://bugs.llvm.org/show_bug.cgi?id=37610
11 ; a) x & (1 << nbits) - 1
12 ; b) x & ~(-1 << nbits)
13 ; c) x & (-1 >> (32 - y))
14 ; d) x << (32 - y) >> (32 - y)
17 ; ---------------------------------------------------------------------------- ;
19 ; ---------------------------------------------------------------------------- ;
21 define i32 @bzhi32_a0(i32 %val, i32 %numlowbits) nounwind {
22 ; CHECK-LABEL: bzhi32_a0:
24 ; CHECK-NEXT: mov w8, #1 // =0x1
25 ; CHECK-NEXT: lsl w8, w8, w1
26 ; CHECK-NEXT: sub w8, w8, #1
27 ; CHECK-NEXT: and w0, w8, w0
29 %onebit = shl i32 1, %numlowbits
30 %mask = add nsw i32 %onebit, -1
31 %masked = and i32 %mask, %val
35 define i32 @bzhi32_a1_indexzext(i32 %val, i8 zeroext %numlowbits) nounwind {
36 ; CHECK-LABEL: bzhi32_a1_indexzext:
38 ; CHECK-NEXT: mov w8, #1 // =0x1
39 ; CHECK-NEXT: lsl w8, w8, w1
40 ; CHECK-NEXT: sub w8, w8, #1
41 ; CHECK-NEXT: and w0, w8, w0
43 %conv = zext i8 %numlowbits to i32
44 %onebit = shl i32 1, %conv
45 %mask = add nsw i32 %onebit, -1
46 %masked = and i32 %mask, %val
50 define i32 @bzhi32_a2_load(ptr %w, i32 %numlowbits) nounwind {
51 ; CHECK-LABEL: bzhi32_a2_load:
53 ; CHECK-NEXT: mov w8, #1 // =0x1
54 ; CHECK-NEXT: ldr w9, [x0]
55 ; CHECK-NEXT: lsl w8, w8, w1
56 ; CHECK-NEXT: sub w8, w8, #1
57 ; CHECK-NEXT: and w0, w8, w9
59 %val = load i32, ptr %w
60 %onebit = shl i32 1, %numlowbits
61 %mask = add nsw i32 %onebit, -1
62 %masked = and i32 %mask, %val
66 define i32 @bzhi32_a3_load_indexzext(ptr %w, i8 zeroext %numlowbits) nounwind {
67 ; CHECK-LABEL: bzhi32_a3_load_indexzext:
69 ; CHECK-NEXT: mov w8, #1 // =0x1
70 ; CHECK-NEXT: ldr w9, [x0]
71 ; CHECK-NEXT: lsl w8, w8, w1
72 ; CHECK-NEXT: sub w8, w8, #1
73 ; CHECK-NEXT: and w0, w8, w9
75 %val = load i32, ptr %w
76 %conv = zext i8 %numlowbits to i32
77 %onebit = shl i32 1, %conv
78 %mask = add nsw i32 %onebit, -1
79 %masked = and i32 %mask, %val
83 define i32 @bzhi32_a4_commutative(i32 %val, i32 %numlowbits) nounwind {
84 ; CHECK-LABEL: bzhi32_a4_commutative:
86 ; CHECK-NEXT: mov w8, #1 // =0x1
87 ; CHECK-NEXT: lsl w8, w8, w1
88 ; CHECK-NEXT: sub w8, w8, #1
89 ; CHECK-NEXT: and w0, w0, w8
91 %onebit = shl i32 1, %numlowbits
92 %mask = add nsw i32 %onebit, -1
93 %masked = and i32 %val, %mask ; swapped order
99 define i64 @bzhi64_a0(i64 %val, i64 %numlowbits) nounwind {
100 ; CHECK-LABEL: bzhi64_a0:
102 ; CHECK-NEXT: mov w8, #1 // =0x1
103 ; CHECK-NEXT: lsl x8, x8, x1
104 ; CHECK-NEXT: sub x8, x8, #1
105 ; CHECK-NEXT: and x0, x8, x0
107 %onebit = shl i64 1, %numlowbits
108 %mask = add nsw i64 %onebit, -1
109 %masked = and i64 %mask, %val
113 ; Check that we don't throw away the vreg_width-1 mask if not using shifts
114 define i64 @bzhi64_a0_masked(i64 %val, i64 %numlowbits) nounwind {
115 ; CHECK-LABEL: bzhi64_a0_masked:
117 ; CHECK-NEXT: mov w8, #1 // =0x1
118 ; CHECK-NEXT: lsl x8, x8, x1
119 ; CHECK-NEXT: sub x8, x8, #1
120 ; CHECK-NEXT: and x0, x8, x0
122 %numlowbits.masked = and i64 %numlowbits, 63
123 %onebit = shl i64 1, %numlowbits.masked
124 %mask = add nsw i64 %onebit, -1
125 %masked = and i64 %mask, %val
129 define i64 @bzhi64_a1_indexzext(i64 %val, i8 zeroext %numlowbits) nounwind {
130 ; CHECK-LABEL: bzhi64_a1_indexzext:
132 ; CHECK-NEXT: mov w8, #1 // =0x1
133 ; CHECK-NEXT: // kill: def $w1 killed $w1 def $x1
134 ; CHECK-NEXT: lsl x8, x8, x1
135 ; CHECK-NEXT: sub x8, x8, #1
136 ; CHECK-NEXT: and x0, x8, x0
138 %conv = zext i8 %numlowbits to i64
139 %onebit = shl i64 1, %conv
140 %mask = add nsw i64 %onebit, -1
141 %masked = and i64 %mask, %val
145 define i64 @bzhi64_a2_load(ptr %w, i64 %numlowbits) nounwind {
146 ; CHECK-LABEL: bzhi64_a2_load:
148 ; CHECK-NEXT: mov w8, #1 // =0x1
149 ; CHECK-NEXT: ldr x9, [x0]
150 ; CHECK-NEXT: lsl x8, x8, x1
151 ; CHECK-NEXT: sub x8, x8, #1
152 ; CHECK-NEXT: and x0, x8, x9
154 %val = load i64, ptr %w
155 %onebit = shl i64 1, %numlowbits
156 %mask = add nsw i64 %onebit, -1
157 %masked = and i64 %mask, %val
161 define i64 @bzhi64_a3_load_indexzext(ptr %w, i8 zeroext %numlowbits) nounwind {
162 ; CHECK-LABEL: bzhi64_a3_load_indexzext:
164 ; CHECK-NEXT: mov w8, #1 // =0x1
165 ; CHECK-NEXT: // kill: def $w1 killed $w1 def $x1
166 ; CHECK-NEXT: ldr x9, [x0]
167 ; CHECK-NEXT: lsl x8, x8, x1
168 ; CHECK-NEXT: sub x8, x8, #1
169 ; CHECK-NEXT: and x0, x8, x9
171 %val = load i64, ptr %w
172 %conv = zext i8 %numlowbits to i64
173 %onebit = shl i64 1, %conv
174 %mask = add nsw i64 %onebit, -1
175 %masked = and i64 %mask, %val
179 define i64 @bzhi64_a4_commutative(i64 %val, i64 %numlowbits) nounwind {
180 ; CHECK-LABEL: bzhi64_a4_commutative:
182 ; CHECK-NEXT: mov w8, #1 // =0x1
183 ; CHECK-NEXT: lsl x8, x8, x1
184 ; CHECK-NEXT: sub x8, x8, #1
185 ; CHECK-NEXT: and x0, x0, x8
187 %onebit = shl i64 1, %numlowbits
188 %mask = add nsw i64 %onebit, -1
189 %masked = and i64 %val, %mask ; swapped order
193 ; ---------------------------------------------------------------------------- ;
195 ; ---------------------------------------------------------------------------- ;
197 define i32 @bzhi32_b0(i32 %val, i32 %numlowbits) nounwind {
198 ; CHECK-LABEL: bzhi32_b0:
200 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
201 ; CHECK-NEXT: lsl w8, w8, w1
202 ; CHECK-NEXT: bic w0, w0, w8
204 %notmask = shl i32 -1, %numlowbits
205 %mask = xor i32 %notmask, -1
206 %masked = and i32 %mask, %val
210 define i32 @bzhi32_b1_indexzext(i32 %val, i8 zeroext %numlowbits) nounwind {
211 ; CHECK-LABEL: bzhi32_b1_indexzext:
213 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
214 ; CHECK-NEXT: lsl w8, w8, w1
215 ; CHECK-NEXT: bic w0, w0, w8
217 %conv = zext i8 %numlowbits to i32
218 %notmask = shl i32 -1, %conv
219 %mask = xor i32 %notmask, -1
220 %masked = and i32 %mask, %val
224 define i32 @bzhi32_b2_load(ptr %w, i32 %numlowbits) nounwind {
225 ; CHECK-LABEL: bzhi32_b2_load:
227 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
228 ; CHECK-NEXT: ldr w9, [x0]
229 ; CHECK-NEXT: lsl w8, w8, w1
230 ; CHECK-NEXT: bic w0, w9, w8
232 %val = load i32, ptr %w
233 %notmask = shl i32 -1, %numlowbits
234 %mask = xor i32 %notmask, -1
235 %masked = and i32 %mask, %val
239 define i32 @bzhi32_b3_load_indexzext(ptr %w, i8 zeroext %numlowbits) nounwind {
240 ; CHECK-LABEL: bzhi32_b3_load_indexzext:
242 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
243 ; CHECK-NEXT: ldr w9, [x0]
244 ; CHECK-NEXT: lsl w8, w8, w1
245 ; CHECK-NEXT: bic w0, w9, w8
247 %val = load i32, ptr %w
248 %conv = zext i8 %numlowbits to i32
249 %notmask = shl i32 -1, %conv
250 %mask = xor i32 %notmask, -1
251 %masked = and i32 %mask, %val
255 define i32 @bzhi32_b4_commutative(i32 %val, i32 %numlowbits) nounwind {
256 ; CHECK-LABEL: bzhi32_b4_commutative:
258 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
259 ; CHECK-NEXT: lsl w8, w8, w1
260 ; CHECK-NEXT: bic w0, w0, w8
262 %notmask = shl i32 -1, %numlowbits
263 %mask = xor i32 %notmask, -1
264 %masked = and i32 %val, %mask ; swapped order
270 define i64 @bzhi64_b0(i64 %val, i64 %numlowbits) nounwind {
271 ; CHECK-LABEL: bzhi64_b0:
273 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
274 ; CHECK-NEXT: lsl x8, x8, x1
275 ; CHECK-NEXT: bic x0, x0, x8
277 %notmask = shl i64 -1, %numlowbits
278 %mask = xor i64 %notmask, -1
279 %masked = and i64 %mask, %val
283 define i64 @bzhi64_b1_indexzext(i64 %val, i8 zeroext %numlowbits) nounwind {
284 ; CHECK-LABEL: bzhi64_b1_indexzext:
286 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
287 ; CHECK-NEXT: // kill: def $w1 killed $w1 def $x1
288 ; CHECK-NEXT: lsl x8, x8, x1
289 ; CHECK-NEXT: bic x0, x0, x8
291 %conv = zext i8 %numlowbits to i64
292 %notmask = shl i64 -1, %conv
293 %mask = xor i64 %notmask, -1
294 %masked = and i64 %mask, %val
298 define i64 @bzhi64_b2_load(ptr %w, i64 %numlowbits) nounwind {
299 ; CHECK-LABEL: bzhi64_b2_load:
301 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
302 ; CHECK-NEXT: ldr x9, [x0]
303 ; CHECK-NEXT: lsl x8, x8, x1
304 ; CHECK-NEXT: bic x0, x9, x8
306 %val = load i64, ptr %w
307 %notmask = shl i64 -1, %numlowbits
308 %mask = xor i64 %notmask, -1
309 %masked = and i64 %mask, %val
313 define i64 @bzhi64_b3_load_indexzext(ptr %w, i8 zeroext %numlowbits) nounwind {
314 ; CHECK-LABEL: bzhi64_b3_load_indexzext:
316 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
317 ; CHECK-NEXT: // kill: def $w1 killed $w1 def $x1
318 ; CHECK-NEXT: ldr x9, [x0]
319 ; CHECK-NEXT: lsl x8, x8, x1
320 ; CHECK-NEXT: bic x0, x9, x8
322 %val = load i64, ptr %w
323 %conv = zext i8 %numlowbits to i64
324 %notmask = shl i64 -1, %conv
325 %mask = xor i64 %notmask, -1
326 %masked = and i64 %mask, %val
330 define i64 @bzhi64_b4_commutative(i64 %val, i64 %numlowbits) nounwind {
331 ; CHECK-LABEL: bzhi64_b4_commutative:
333 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
334 ; CHECK-NEXT: lsl x8, x8, x1
335 ; CHECK-NEXT: bic x0, x0, x8
337 %notmask = shl i64 -1, %numlowbits
338 %mask = xor i64 %notmask, -1
339 %masked = and i64 %val, %mask ; swapped order
343 ; ---------------------------------------------------------------------------- ;
345 ; ---------------------------------------------------------------------------- ;
347 define i32 @bzhi32_c0(i32 %val, i32 %numlowbits) nounwind {
348 ; CHECK-LABEL: bzhi32_c0:
350 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
351 ; CHECK-NEXT: neg w9, w1
352 ; CHECK-NEXT: lsr w8, w8, w9
353 ; CHECK-NEXT: and w0, w8, w0
355 %numhighbits = sub i32 32, %numlowbits
356 %mask = lshr i32 -1, %numhighbits
357 %masked = and i32 %mask, %val
361 define i32 @bzhi32_c1_indexzext(i32 %val, i8 %numlowbits) nounwind {
362 ; CHECK-LABEL: bzhi32_c1_indexzext:
364 ; CHECK-NEXT: mov w8, #32 // =0x20
365 ; CHECK-NEXT: mov w9, #-1 // =0xffffffff
366 ; CHECK-NEXT: sub w8, w8, w1
367 ; CHECK-NEXT: lsr w8, w9, w8
368 ; CHECK-NEXT: and w0, w8, w0
370 %numhighbits = sub i8 32, %numlowbits
371 %sh_prom = zext i8 %numhighbits to i32
372 %mask = lshr i32 -1, %sh_prom
373 %masked = and i32 %mask, %val
377 define i32 @bzhi32_c2_load(ptr %w, i32 %numlowbits) nounwind {
378 ; CHECK-LABEL: bzhi32_c2_load:
380 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
381 ; CHECK-NEXT: neg w9, w1
382 ; CHECK-NEXT: ldr w10, [x0]
383 ; CHECK-NEXT: lsr w8, w8, w9
384 ; CHECK-NEXT: and w0, w8, w10
386 %val = load i32, ptr %w
387 %numhighbits = sub i32 32, %numlowbits
388 %mask = lshr i32 -1, %numhighbits
389 %masked = and i32 %mask, %val
393 define i32 @bzhi32_c3_load_indexzext(ptr %w, i8 %numlowbits) nounwind {
394 ; CHECK-LABEL: bzhi32_c3_load_indexzext:
396 ; CHECK-NEXT: mov w8, #32 // =0x20
397 ; CHECK-NEXT: mov w9, #-1 // =0xffffffff
398 ; CHECK-NEXT: ldr w10, [x0]
399 ; CHECK-NEXT: sub w8, w8, w1
400 ; CHECK-NEXT: lsr w8, w9, w8
401 ; CHECK-NEXT: and w0, w8, w10
403 %val = load i32, ptr %w
404 %numhighbits = sub i8 32, %numlowbits
405 %sh_prom = zext i8 %numhighbits to i32
406 %mask = lshr i32 -1, %sh_prom
407 %masked = and i32 %mask, %val
411 define i32 @bzhi32_c4_commutative(i32 %val, i32 %numlowbits) nounwind {
412 ; CHECK-LABEL: bzhi32_c4_commutative:
414 ; CHECK-NEXT: mov w8, #-1 // =0xffffffff
415 ; CHECK-NEXT: neg w9, w1
416 ; CHECK-NEXT: lsr w8, w8, w9
417 ; CHECK-NEXT: and w0, w0, w8
419 %numhighbits = sub i32 32, %numlowbits
420 %mask = lshr i32 -1, %numhighbits
421 %masked = and i32 %val, %mask ; swapped order
427 define i64 @bzhi64_c0(i64 %val, i64 %numlowbits) nounwind {
428 ; CHECK-LABEL: bzhi64_c0:
430 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
431 ; CHECK-NEXT: neg x9, x1
432 ; CHECK-NEXT: lsr x8, x8, x9
433 ; CHECK-NEXT: and x0, x8, x0
435 %numhighbits = sub i64 64, %numlowbits
436 %mask = lshr i64 -1, %numhighbits
437 %masked = and i64 %mask, %val
441 define i64 @bzhi64_c1_indexzext(i64 %val, i8 %numlowbits) nounwind {
442 ; CHECK-LABEL: bzhi64_c1_indexzext:
444 ; CHECK-NEXT: mov w8, #64 // =0x40
445 ; CHECK-NEXT: mov x9, #-1 // =0xffffffffffffffff
446 ; CHECK-NEXT: sub w8, w8, w1
447 ; CHECK-NEXT: lsr x8, x9, x8
448 ; CHECK-NEXT: and x0, x8, x0
450 %numhighbits = sub i8 64, %numlowbits
451 %sh_prom = zext i8 %numhighbits to i64
452 %mask = lshr i64 -1, %sh_prom
453 %masked = and i64 %mask, %val
457 define i64 @bzhi64_c2_load(ptr %w, i64 %numlowbits) nounwind {
458 ; CHECK-LABEL: bzhi64_c2_load:
460 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
461 ; CHECK-NEXT: neg x9, x1
462 ; CHECK-NEXT: ldr x10, [x0]
463 ; CHECK-NEXT: lsr x8, x8, x9
464 ; CHECK-NEXT: and x0, x8, x10
466 %val = load i64, ptr %w
467 %numhighbits = sub i64 64, %numlowbits
468 %mask = lshr i64 -1, %numhighbits
469 %masked = and i64 %mask, %val
473 define i64 @bzhi64_c3_load_indexzext(ptr %w, i8 %numlowbits) nounwind {
474 ; CHECK-LABEL: bzhi64_c3_load_indexzext:
476 ; CHECK-NEXT: mov w8, #64 // =0x40
477 ; CHECK-NEXT: mov x9, #-1 // =0xffffffffffffffff
478 ; CHECK-NEXT: ldr x10, [x0]
479 ; CHECK-NEXT: sub w8, w8, w1
480 ; CHECK-NEXT: lsr x8, x9, x8
481 ; CHECK-NEXT: and x0, x8, x10
483 %val = load i64, ptr %w
484 %numhighbits = sub i8 64, %numlowbits
485 %sh_prom = zext i8 %numhighbits to i64
486 %mask = lshr i64 -1, %sh_prom
487 %masked = and i64 %mask, %val
491 define i64 @bzhi64_c4_commutative(i64 %val, i64 %numlowbits) nounwind {
492 ; CHECK-LABEL: bzhi64_c4_commutative:
494 ; CHECK-NEXT: mov x8, #-1 // =0xffffffffffffffff
495 ; CHECK-NEXT: neg x9, x1
496 ; CHECK-NEXT: lsr x8, x8, x9
497 ; CHECK-NEXT: and x0, x0, x8
499 %numhighbits = sub i64 64, %numlowbits
500 %mask = lshr i64 -1, %numhighbits
501 %masked = and i64 %val, %mask ; swapped order
505 ; ---------------------------------------------------------------------------- ;
507 ; ---------------------------------------------------------------------------- ;
509 define i32 @bzhi32_d0(i32 %val, i32 %numlowbits) nounwind {
510 ; CHECK-LABEL: bzhi32_d0:
512 ; CHECK-NEXT: neg w8, w1
513 ; CHECK-NEXT: lsl w9, w0, w8
514 ; CHECK-NEXT: lsr w0, w9, w8
516 %numhighbits = sub i32 32, %numlowbits
517 %highbitscleared = shl i32 %val, %numhighbits
518 %masked = lshr i32 %highbitscleared, %numhighbits
522 define i32 @bzhi32_d1_indexzext(i32 %val, i8 %numlowbits) nounwind {
523 ; CHECK-LABEL: bzhi32_d1_indexzext:
525 ; CHECK-NEXT: mov w8, #32 // =0x20
526 ; CHECK-NEXT: sub w8, w8, w1
527 ; CHECK-NEXT: lsl w9, w0, w8
528 ; CHECK-NEXT: lsr w0, w9, w8
530 %numhighbits = sub i8 32, %numlowbits
531 %sh_prom = zext i8 %numhighbits to i32
532 %highbitscleared = shl i32 %val, %sh_prom
533 %masked = lshr i32 %highbitscleared, %sh_prom
537 define i32 @bzhi32_d2_load(ptr %w, i32 %numlowbits) nounwind {
538 ; CHECK-LABEL: bzhi32_d2_load:
540 ; CHECK-NEXT: ldr w8, [x0]
541 ; CHECK-NEXT: neg w9, w1
542 ; CHECK-NEXT: lsl w8, w8, w9
543 ; CHECK-NEXT: lsr w0, w8, w9
545 %val = load i32, ptr %w
546 %numhighbits = sub i32 32, %numlowbits
547 %highbitscleared = shl i32 %val, %numhighbits
548 %masked = lshr i32 %highbitscleared, %numhighbits
552 define i32 @bzhi32_d3_load_indexzext(ptr %w, i8 %numlowbits) nounwind {
553 ; CHECK-LABEL: bzhi32_d3_load_indexzext:
555 ; CHECK-NEXT: mov w8, #32 // =0x20
556 ; CHECK-NEXT: ldr w9, [x0]
557 ; CHECK-NEXT: sub w8, w8, w1
558 ; CHECK-NEXT: lsl w9, w9, w8
559 ; CHECK-NEXT: lsr w0, w9, w8
561 %val = load i32, ptr %w
562 %numhighbits = sub i8 32, %numlowbits
563 %sh_prom = zext i8 %numhighbits to i32
564 %highbitscleared = shl i32 %val, %sh_prom
565 %masked = lshr i32 %highbitscleared, %sh_prom
571 define i64 @bzhi64_d0(i64 %val, i64 %numlowbits) nounwind {
572 ; CHECK-LABEL: bzhi64_d0:
574 ; CHECK-NEXT: neg x8, x1
575 ; CHECK-NEXT: lsl x9, x0, x8
576 ; CHECK-NEXT: lsr x0, x9, x8
578 %numhighbits = sub i64 64, %numlowbits
579 %highbitscleared = shl i64 %val, %numhighbits
580 %masked = lshr i64 %highbitscleared, %numhighbits
584 define i64 @bzhi64_d1_indexzext(i64 %val, i8 %numlowbits) nounwind {
585 ; CHECK-LABEL: bzhi64_d1_indexzext:
587 ; CHECK-NEXT: mov w8, #64 // =0x40
588 ; CHECK-NEXT: sub w8, w8, w1
589 ; CHECK-NEXT: lsl x9, x0, x8
590 ; CHECK-NEXT: lsr x0, x9, x8
592 %numhighbits = sub i8 64, %numlowbits
593 %sh_prom = zext i8 %numhighbits to i64
594 %highbitscleared = shl i64 %val, %sh_prom
595 %masked = lshr i64 %highbitscleared, %sh_prom
599 define i64 @bzhi64_d2_load(ptr %w, i64 %numlowbits) nounwind {
600 ; CHECK-LABEL: bzhi64_d2_load:
602 ; CHECK-NEXT: ldr x8, [x0]
603 ; CHECK-NEXT: neg x9, x1
604 ; CHECK-NEXT: lsl x8, x8, x9
605 ; CHECK-NEXT: lsr x0, x8, x9
607 %val = load i64, ptr %w
608 %numhighbits = sub i64 64, %numlowbits
609 %highbitscleared = shl i64 %val, %numhighbits
610 %masked = lshr i64 %highbitscleared, %numhighbits
614 define i64 @bzhi64_d3_load_indexzext(ptr %w, i8 %numlowbits) nounwind {
615 ; CHECK-LABEL: bzhi64_d3_load_indexzext:
617 ; CHECK-NEXT: mov w8, #64 // =0x40
618 ; CHECK-NEXT: ldr x9, [x0]
619 ; CHECK-NEXT: sub w8, w8, w1
620 ; CHECK-NEXT: lsl x9, x9, x8
621 ; CHECK-NEXT: lsr x0, x9, x8
623 %val = load i64, ptr %w
624 %numhighbits = sub i8 64, %numlowbits
625 %sh_prom = zext i8 %numhighbits to i64
626 %highbitscleared = shl i64 %val, %sh_prom
627 %masked = lshr i64 %highbitscleared, %sh_prom
631 ; ---------------------------------------------------------------------------- ;
633 ; ---------------------------------------------------------------------------- ;
637 define i32 @bzhi32_constant_mask32(i32 %val) nounwind {
638 ; CHECK-LABEL: bzhi32_constant_mask32:
640 ; CHECK-NEXT: and w0, w0, #0x7fffffff
642 %masked = and i32 %val, 2147483647
646 define i32 @bzhi32_constant_mask32_load(ptr %val) nounwind {
647 ; CHECK-LABEL: bzhi32_constant_mask32_load:
649 ; CHECK-NEXT: ldr w8, [x0]
650 ; CHECK-NEXT: and w0, w8, #0x7fffffff
652 %val1 = load i32, ptr %val
653 %masked = and i32 %val1, 2147483647
657 define i32 @bzhi32_constant_mask16(i32 %val) nounwind {
658 ; CHECK-LABEL: bzhi32_constant_mask16:
660 ; CHECK-NEXT: and w0, w0, #0x7fff
662 %masked = and i32 %val, 32767
666 define i32 @bzhi32_constant_mask16_load(ptr %val) nounwind {
667 ; CHECK-LABEL: bzhi32_constant_mask16_load:
669 ; CHECK-NEXT: ldr w8, [x0]
670 ; CHECK-NEXT: and w0, w8, #0x7fff
672 %val1 = load i32, ptr %val
673 %masked = and i32 %val1, 32767
677 define i32 @bzhi32_constant_mask8(i32 %val) nounwind {
678 ; CHECK-LABEL: bzhi32_constant_mask8:
680 ; CHECK-NEXT: and w0, w0, #0x7f
682 %masked = and i32 %val, 127
686 define i32 @bzhi32_constant_mask8_load(ptr %val) nounwind {
687 ; CHECK-LABEL: bzhi32_constant_mask8_load:
689 ; CHECK-NEXT: ldr w8, [x0]
690 ; CHECK-NEXT: and w0, w8, #0x7f
692 %val1 = load i32, ptr %val
693 %masked = and i32 %val1, 127
699 define i64 @bzhi64_constant_mask64(i64 %val) nounwind {
700 ; CHECK-LABEL: bzhi64_constant_mask64:
702 ; CHECK-NEXT: and x0, x0, #0x3fffffffffffffff
704 %masked = and i64 %val, 4611686018427387903
708 define i64 @bzhi64_constant_mask64_load(ptr %val) nounwind {
709 ; CHECK-LABEL: bzhi64_constant_mask64_load:
711 ; CHECK-NEXT: ldr x8, [x0]
712 ; CHECK-NEXT: and x0, x8, #0x3fffffffffffffff
714 %val1 = load i64, ptr %val
715 %masked = and i64 %val1, 4611686018427387903
719 define i64 @bzhi64_constant_mask32(i64 %val) nounwind {
720 ; CHECK-LABEL: bzhi64_constant_mask32:
722 ; CHECK-NEXT: and x0, x0, #0x7fffffff
724 %masked = and i64 %val, 2147483647
728 define i64 @bzhi64_constant_mask32_load(ptr %val) nounwind {
729 ; CHECK-LABEL: bzhi64_constant_mask32_load:
731 ; CHECK-NEXT: ldr x8, [x0]
732 ; CHECK-NEXT: and x0, x8, #0x7fffffff
734 %val1 = load i64, ptr %val
735 %masked = and i64 %val1, 2147483647
739 define i64 @bzhi64_constant_mask16(i64 %val) nounwind {
740 ; CHECK-LABEL: bzhi64_constant_mask16:
742 ; CHECK-NEXT: and x0, x0, #0x7fff
744 %masked = and i64 %val, 32767
748 define i64 @bzhi64_constant_mask16_load(ptr %val) nounwind {
749 ; CHECK-LABEL: bzhi64_constant_mask16_load:
751 ; CHECK-NEXT: ldr x8, [x0]
752 ; CHECK-NEXT: and x0, x8, #0x7fff
754 %val1 = load i64, ptr %val
755 %masked = and i64 %val1, 32767
759 define i64 @bzhi64_constant_mask8(i64 %val) nounwind {
760 ; CHECK-LABEL: bzhi64_constant_mask8:
762 ; CHECK-NEXT: and x0, x0, #0x7f
764 %masked = and i64 %val, 127
768 define i64 @bzhi64_constant_mask8_load(ptr %val) nounwind {
769 ; CHECK-LABEL: bzhi64_constant_mask8_load:
771 ; CHECK-NEXT: ldr x8, [x0]
772 ; CHECK-NEXT: and x0, x8, #0x7f
774 %val1 = load i64, ptr %val
775 %masked = and i64 %val1, 127