@@ -554,6 +554,40 @@ define <16 x i8> @umaxmin_v16i8_com1(<16 x i8> %0, <16 x i8> %1) {
554
554
ret <16 x i8 > %sub
555
555
}
556
556
557
+ ; (abds x, y) upper bits are known zero if x and y have extra sign bits
558
+ define <4 x i16 > @combine_sabd_4h_zerosign (<4 x i16 > %a , <4 x i16 > %b ) #0 {
559
+ ; CHECK-LABEL: combine_sabd_4h_zerosign:
560
+ ; CHECK: // %bb.0:
561
+ ; CHECK-NEXT: movi v0.2d, #0000000000000000
562
+ ; CHECK-NEXT: ret
563
+ %a.ext = ashr <4 x i16 > %a , <i16 7 , i16 8 , i16 9 , i16 10 >
564
+ %b.ext = ashr <4 x i16 > %b , <i16 11 , i16 12 , i16 13 , i16 14 >
565
+ %max = tail call <4 x i16 > @llvm.smax.v4i16 (<4 x i16 > %a.ext , <4 x i16 > %b.ext )
566
+ %min = tail call <4 x i16 > @llvm.smin.v4i16 (<4 x i16 > %a.ext , <4 x i16 > %b.ext )
567
+ %sub = sub <4 x i16 > %max , %min
568
+ %mask = and <4 x i16 > %sub , <i16 32768 , i16 32768 , i16 32768 , i16 32768 >
569
+ ret <4 x i16 > %mask
570
+ }
571
+
572
+ ; negative test - mask extends beyond known zero bits
573
+ define <2 x i32 > @combine_sabd_2s_zerosign_negative (<2 x i32 > %a , <2 x i32 > %b ) {
574
+ ; CHECK-LABEL: combine_sabd_2s_zerosign_negative:
575
+ ; CHECK: // %bb.0:
576
+ ; CHECK-NEXT: sshr v0.2s, v0.2s, #3
577
+ ; CHECK-NEXT: sshr v1.2s, v1.2s, #15
578
+ ; CHECK-NEXT: mvni v2.2s, #7, msl #16
579
+ ; CHECK-NEXT: sabd v0.2s, v0.2s, v1.2s
580
+ ; CHECK-NEXT: and v0.8b, v0.8b, v2.8b
581
+ ; CHECK-NEXT: ret
582
+ %a.ext = ashr <2 x i32 > %a , <i32 3 , i32 3 >
583
+ %b.ext = ashr <2 x i32 > %b , <i32 15 , i32 15 >
584
+ %max = tail call <2 x i32 > @llvm.smax.v2i32 (<2 x i32 > %a.ext , <2 x i32 > %b.ext )
585
+ %min = tail call <2 x i32 > @llvm.smin.v2i32 (<2 x i32 > %a.ext , <2 x i32 > %b.ext )
586
+ %sub = sub <2 x i32 > %max , %min
587
+ %mask = and <2 x i32 > %sub , <i32 -524288 , i32 -524288 > ; 0xFFF80000
588
+ ret <2 x i32 > %mask
589
+ }
590
+
557
591
declare <8 x i8 > @llvm.abs.v8i8 (<8 x i8 >, i1 )
558
592
declare <16 x i8 > @llvm.abs.v16i8 (<16 x i8 >, i1 )
559
593
0 commit comments