blob: d5ac9910906a87c177cf007343f197491c95d045 [file] [edit]
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+sse2 | FileCheck %s --check-prefixes=SSE,SSE2
; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+sse4.2 | FileCheck %s --check-prefixes=SSE,SSE42
; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+avx | FileCheck %s --check-prefixes=AVX,AVX1OR2,AVX1
; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+avx2 | FileCheck %s --check-prefixes=AVX,AVX1OR2,AVX2
; RUN: llc < %s -mtriple=x86_64-unknown -mattr=+avx512f,+avx512bw,+avx512vl | FileCheck %s --check-prefixes=AVX,AVX512
define i64 @test_v2f64_sext(<2 x double> %a0, <2 x double> %a1) {
; SSE-LABEL: test_v2f64_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltpd %xmm0, %xmm1
; SSE-NEXT: movmskpd %xmm1, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbq %rax, %rax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v2f64_sext:
; AVX: # %bb.0:
; AVX-NEXT: vcmpltpd %xmm0, %xmm1, %xmm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestpd %xmm0, %xmm0
; AVX-NEXT: setne %al
; AVX-NEXT: negq %rax
; AVX-NEXT: retq
%c = fcmp ogt <2 x double> %a0, %a1
%s = sext <2 x i1> %c to <2 x i64>
%r = call i64 @llvm.vector.reduce.or.v2i64(<2 x i64> %s)
ret i64 %r
}
define i64 @test_v4f64_sext(<4 x double> %a0, <4 x double> %a1) {
; SSE-LABEL: test_v4f64_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltpd %xmm1, %xmm3
; SSE-NEXT: cmpltpd %xmm0, %xmm2
; SSE-NEXT: orpd %xmm3, %xmm2
; SSE-NEXT: movmskpd %xmm2, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbq %rax, %rax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v4f64_sext:
; AVX: # %bb.0:
; AVX-NEXT: vcmpltpd %ymm0, %ymm1, %ymm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestpd %ymm0, %ymm0
; AVX-NEXT: setne %al
; AVX-NEXT: negq %rax
; AVX-NEXT: vzeroupper
; AVX-NEXT: retq
%c = fcmp ogt <4 x double> %a0, %a1
%s = sext <4 x i1> %c to <4 x i64>
%r = call i64 @llvm.vector.reduce.or.v4i64(<4 x i64> %s)
ret i64 %r
}
define i64 @test_v4f64_legal_sext(<4 x double> %a0, <4 x double> %a1) {
; SSE-LABEL: test_v4f64_legal_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltpd %xmm1, %xmm3
; SSE-NEXT: cmpltpd %xmm0, %xmm2
; SSE-NEXT: shufps {{.*#+}} xmm2 = xmm2[0,2],xmm3[0,2]
; SSE-NEXT: movmskps %xmm2, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbq %rax, %rax
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: test_v4f64_legal_sext:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmpltpd %ymm0, %ymm1, %ymm0
; AVX1OR2-NEXT: vextractf128 $1, %ymm0, %xmm1
; AVX1OR2-NEXT: vpackssdw %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: xorl %eax, %eax
; AVX1OR2-NEXT: vtestps %xmm0, %xmm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: negq %rax
; AVX1OR2-NEXT: vzeroupper
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: test_v4f64_legal_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmpltpd %ymm0, %ymm1, %k1
; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0
; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z}
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: vtestps %xmm0, %xmm0
; AVX512-NEXT: setne %al
; AVX512-NEXT: negq %rax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = fcmp ogt <4 x double> %a0, %a1
%s = sext <4 x i1> %c to <4 x i32>
%r = call i32 @llvm.vector.reduce.or.v4i32(<4 x i32> %s)
%x = sext i32 %r to i64
ret i64 %x
}
define i32 @test_v4f32_sext(<4 x float> %a0, <4 x float> %a1) {
; SSE-LABEL: test_v4f32_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltps %xmm0, %xmm1
; SSE-NEXT: movmskps %xmm1, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v4f32_sext:
; AVX: # %bb.0:
; AVX-NEXT: vcmpltps %xmm0, %xmm1, %xmm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestps %xmm0, %xmm0
; AVX-NEXT: setne %al
; AVX-NEXT: negl %eax
; AVX-NEXT: retq
%c = fcmp ogt <4 x float> %a0, %a1
%s = sext <4 x i1> %c to <4 x i32>
%r = call i32 @llvm.vector.reduce.or.v4i32(<4 x i32> %s)
ret i32 %r
}
define i32 @test_v8f32_sext(<8 x float> %a0, <8 x float> %a1) {
; SSE-LABEL: test_v8f32_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltps %xmm1, %xmm3
; SSE-NEXT: cmpltps %xmm0, %xmm2
; SSE-NEXT: orps %xmm3, %xmm2
; SSE-NEXT: movmskps %xmm2, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v8f32_sext:
; AVX: # %bb.0:
; AVX-NEXT: vcmpltps %ymm0, %ymm1, %ymm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestps %ymm0, %ymm0
; AVX-NEXT: setne %al
; AVX-NEXT: negl %eax
; AVX-NEXT: vzeroupper
; AVX-NEXT: retq
%c = fcmp ogt <8 x float> %a0, %a1
%s = sext <8 x i1> %c to <8 x i32>
%r = call i32 @llvm.vector.reduce.or.v8i32(<8 x i32> %s)
ret i32 %r
}
define i32 @test_v8f32_legal_sext(<8 x float> %a0, <8 x float> %a1) {
; SSE-LABEL: test_v8f32_legal_sext:
; SSE: # %bb.0:
; SSE-NEXT: cmpltps %xmm1, %xmm3
; SSE-NEXT: cmpltps %xmm0, %xmm2
; SSE-NEXT: packssdw %xmm3, %xmm2
; SSE-NEXT: pmovmskb %xmm2, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: test_v8f32_legal_sext:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmpltps %ymm0, %ymm1, %ymm0
; AVX1OR2-NEXT: vextractf128 $1, %ymm0, %xmm1
; AVX1OR2-NEXT: vpackssdw %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: vpmovmskb %xmm0, %ecx
; AVX1OR2-NEXT: xorl %eax, %eax
; AVX1OR2-NEXT: negl %ecx
; AVX1OR2-NEXT: sbbl %eax, %eax
; AVX1OR2-NEXT: vzeroupper
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: test_v8f32_legal_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmpltps %ymm0, %ymm1, %k0
; AVX512-NEXT: vpmovm2w %k0, %xmm0
; AVX512-NEXT: vpmovmskb %xmm0, %ecx
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: negl %ecx
; AVX512-NEXT: sbbl %eax, %eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = fcmp ogt <8 x float> %a0, %a1
%s = sext <8 x i1> %c to <8 x i16>
%r = call i16 @llvm.vector.reduce.or.v8i16(<8 x i16> %s)
%x = sext i16 %r to i32
ret i32 %x
}
define i64 @test_v2i64_sext(<2 x i64> %a0, <2 x i64> %a1) {
; SSE2-LABEL: test_v2i64_sext:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm2 = [2147483648,2147483648]
; SSE2-NEXT: pxor %xmm2, %xmm1
; SSE2-NEXT: pxor %xmm2, %xmm0
; SSE2-NEXT: movdqa %xmm0, %xmm2
; SSE2-NEXT: pcmpgtd %xmm1, %xmm2
; SSE2-NEXT: pshufd {{.*#+}} xmm3 = xmm2[0,0,2,2]
; SSE2-NEXT: pcmpeqd %xmm1, %xmm0
; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,1,3,3]
; SSE2-NEXT: pand %xmm3, %xmm0
; SSE2-NEXT: pshufd {{.*#+}} xmm1 = xmm2[1,1,3,3]
; SSE2-NEXT: por %xmm0, %xmm1
; SSE2-NEXT: movmskpd %xmm1, %ecx
; SSE2-NEXT: xorl %eax, %eax
; SSE2-NEXT: negl %ecx
; SSE2-NEXT: sbbq %rax, %rax
; SSE2-NEXT: retq
;
; SSE42-LABEL: test_v2i64_sext:
; SSE42: # %bb.0:
; SSE42-NEXT: pcmpgtq %xmm1, %xmm0
; SSE42-NEXT: movmskpd %xmm0, %ecx
; SSE42-NEXT: xorl %eax, %eax
; SSE42-NEXT: negl %ecx
; SSE42-NEXT: sbbq %rax, %rax
; SSE42-NEXT: retq
;
; AVX-LABEL: test_v2i64_sext:
; AVX: # %bb.0:
; AVX-NEXT: vpcmpgtq %xmm1, %xmm0, %xmm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestpd %xmm0, %xmm0
; AVX-NEXT: setne %al
; AVX-NEXT: negq %rax
; AVX-NEXT: retq
%c = icmp sgt <2 x i64> %a0, %a1
%s = sext <2 x i1> %c to <2 x i64>
%r = call i64 @llvm.vector.reduce.or.v2i64(<2 x i64> %s)
ret i64 %r
}
define i64 @test_v4i64_sext(<4 x i64> %a0, <4 x i64> %a1) {
; SSE2-LABEL: test_v4i64_sext:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm4 = [2147483648,2147483648]
; SSE2-NEXT: pxor %xmm4, %xmm3
; SSE2-NEXT: pxor %xmm4, %xmm1
; SSE2-NEXT: movdqa %xmm1, %xmm5
; SSE2-NEXT: pcmpgtd %xmm3, %xmm5
; SSE2-NEXT: pshufd {{.*#+}} xmm6 = xmm5[0,0,2,2]
; SSE2-NEXT: pcmpeqd %xmm3, %xmm1
; SSE2-NEXT: pshufd {{.*#+}} xmm1 = xmm1[1,1,3,3]
; SSE2-NEXT: pand %xmm6, %xmm1
; SSE2-NEXT: pshufd {{.*#+}} xmm3 = xmm5[1,1,3,3]
; SSE2-NEXT: por %xmm1, %xmm3
; SSE2-NEXT: pxor %xmm4, %xmm2
; SSE2-NEXT: pxor %xmm4, %xmm0
; SSE2-NEXT: movdqa %xmm0, %xmm1
; SSE2-NEXT: pcmpgtd %xmm2, %xmm1
; SSE2-NEXT: pshufd {{.*#+}} xmm4 = xmm1[0,0,2,2]
; SSE2-NEXT: pcmpeqd %xmm2, %xmm0
; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,1,3,3]
; SSE2-NEXT: pand %xmm4, %xmm0
; SSE2-NEXT: pshufd {{.*#+}} xmm1 = xmm1[1,1,3,3]
; SSE2-NEXT: por %xmm0, %xmm1
; SSE2-NEXT: por %xmm3, %xmm1
; SSE2-NEXT: movmskpd %xmm1, %ecx
; SSE2-NEXT: xorl %eax, %eax
; SSE2-NEXT: negl %ecx
; SSE2-NEXT: sbbq %rax, %rax
; SSE2-NEXT: retq
;
; SSE42-LABEL: test_v4i64_sext:
; SSE42: # %bb.0:
; SSE42-NEXT: pcmpgtq %xmm3, %xmm1
; SSE42-NEXT: pcmpgtq %xmm2, %xmm0
; SSE42-NEXT: por %xmm1, %xmm0
; SSE42-NEXT: movmskpd %xmm0, %ecx
; SSE42-NEXT: xorl %eax, %eax
; SSE42-NEXT: negl %ecx
; SSE42-NEXT: sbbq %rax, %rax
; SSE42-NEXT: retq
;
; AVX1-LABEL: test_v4i64_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtq %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtq %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: vtestpd %xmm0, %xmm0
; AVX1-NEXT: setne %al
; AVX1-NEXT: negq %rax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v4i64_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtq %ymm1, %ymm0, %ymm0
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: vtestpd %ymm0, %ymm0
; AVX2-NEXT: setne %al
; AVX2-NEXT: negq %rax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v4i64_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtq %ymm1, %ymm0, %ymm0
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: vtestpd %ymm0, %ymm0
; AVX512-NEXT: setne %al
; AVX512-NEXT: negq %rax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <4 x i64> %a0, %a1
%s = sext <4 x i1> %c to <4 x i64>
%r = call i64 @llvm.vector.reduce.or.v4i64(<4 x i64> %s)
ret i64 %r
}
define i64 @test_v4i64_legal_sext(<4 x i64> %a0, <4 x i64> %a1) {
; SSE2-LABEL: test_v4i64_legal_sext:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm4 = [2147483648,2147483648]
; SSE2-NEXT: pxor %xmm4, %xmm3
; SSE2-NEXT: pxor %xmm4, %xmm1
; SSE2-NEXT: movdqa %xmm1, %xmm5
; SSE2-NEXT: pcmpgtd %xmm3, %xmm5
; SSE2-NEXT: pxor %xmm4, %xmm2
; SSE2-NEXT: pxor %xmm4, %xmm0
; SSE2-NEXT: movdqa %xmm0, %xmm4
; SSE2-NEXT: pcmpgtd %xmm2, %xmm4
; SSE2-NEXT: movdqa %xmm4, %xmm6
; SSE2-NEXT: shufps {{.*#+}} xmm6 = xmm6[0,2],xmm5[0,2]
; SSE2-NEXT: pcmpeqd %xmm3, %xmm1
; SSE2-NEXT: pcmpeqd %xmm2, %xmm0
; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,3],xmm1[1,3]
; SSE2-NEXT: andps %xmm6, %xmm0
; SSE2-NEXT: shufps {{.*#+}} xmm4 = xmm4[1,3],xmm5[1,3]
; SSE2-NEXT: orps %xmm0, %xmm4
; SSE2-NEXT: movmskps %xmm4, %ecx
; SSE2-NEXT: xorl %eax, %eax
; SSE2-NEXT: negl %ecx
; SSE2-NEXT: sbbq %rax, %rax
; SSE2-NEXT: retq
;
; SSE42-LABEL: test_v4i64_legal_sext:
; SSE42: # %bb.0:
; SSE42-NEXT: pcmpgtq %xmm3, %xmm1
; SSE42-NEXT: pcmpgtq %xmm2, %xmm0
; SSE42-NEXT: packssdw %xmm1, %xmm0
; SSE42-NEXT: movmskps %xmm0, %ecx
; SSE42-NEXT: xorl %eax, %eax
; SSE42-NEXT: negl %ecx
; SSE42-NEXT: sbbq %rax, %rax
; SSE42-NEXT: retq
;
; AVX1-LABEL: test_v4i64_legal_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtq %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtq %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpackssdw %xmm2, %xmm0, %xmm0
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: vtestps %xmm0, %xmm0
; AVX1-NEXT: setne %al
; AVX1-NEXT: negq %rax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v4i64_legal_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtq %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm1
; AVX2-NEXT: vpackssdw %xmm1, %xmm0, %xmm0
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: vtestps %xmm0, %xmm0
; AVX2-NEXT: setne %al
; AVX2-NEXT: negq %rax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v4i64_legal_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtq %ymm1, %ymm0, %k1
; AVX512-NEXT: vpcmpeqd %xmm0, %xmm0, %xmm0
; AVX512-NEXT: vmovdqa32 %xmm0, %xmm0 {%k1} {z}
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: vtestps %xmm0, %xmm0
; AVX512-NEXT: setne %al
; AVX512-NEXT: negq %rax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <4 x i64> %a0, %a1
%s = sext <4 x i1> %c to <4 x i32>
%r = call i32 @llvm.vector.reduce.or.v4i32(<4 x i32> %s)
%x = sext i32 %r to i64
ret i64 %x
}
define i32 @test_v4i32_sext(<4 x i32> %a0, <4 x i32> %a1) {
; SSE-LABEL: test_v4i32_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtd %xmm1, %xmm0
; SSE-NEXT: movmskps %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v4i32_sext:
; AVX: # %bb.0:
; AVX-NEXT: vpcmpgtd %xmm1, %xmm0, %xmm0
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: vtestps %xmm0, %xmm0
; AVX-NEXT: setne %al
; AVX-NEXT: negl %eax
; AVX-NEXT: retq
%c = icmp sgt <4 x i32> %a0, %a1
%s = sext <4 x i1> %c to <4 x i32>
%r = call i32 @llvm.vector.reduce.or.v4i32(<4 x i32> %s)
ret i32 %r
}
define i32 @test_v8i32_sext(<8 x i32> %a0, <8 x i32> %a1) {
; SSE-LABEL: test_v8i32_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtd %xmm3, %xmm1
; SSE-NEXT: pcmpgtd %xmm2, %xmm0
; SSE-NEXT: por %xmm1, %xmm0
; SSE-NEXT: movmskps %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v8i32_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtd %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtd %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: vtestps %xmm0, %xmm0
; AVX1-NEXT: setne %al
; AVX1-NEXT: negl %eax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v8i32_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtd %ymm1, %ymm0, %ymm0
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: vtestps %ymm0, %ymm0
; AVX2-NEXT: setne %al
; AVX2-NEXT: negl %eax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v8i32_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtd %ymm1, %ymm0, %ymm0
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: vtestps %ymm0, %ymm0
; AVX512-NEXT: setne %al
; AVX512-NEXT: negl %eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <8 x i32> %a0, %a1
%s = sext <8 x i1> %c to <8 x i32>
%r = call i32 @llvm.vector.reduce.or.v8i32(<8 x i32> %s)
ret i32 %r
}
define i32 @test_v8i32_legal_sext(<8 x i32> %a0, <8 x i32> %a1) {
; SSE-LABEL: test_v8i32_legal_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtd %xmm3, %xmm1
; SSE-NEXT: pcmpgtd %xmm2, %xmm0
; SSE-NEXT: packssdw %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v8i32_legal_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtd %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtd %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpackssdw %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %ecx
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: negl %ecx
; AVX1-NEXT: sbbl %eax, %eax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v8i32_legal_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtd %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vextracti128 $1, %ymm0, %xmm1
; AVX2-NEXT: vpackssdw %xmm1, %xmm0, %xmm0
; AVX2-NEXT: vpmovmskb %xmm0, %ecx
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: negl %ecx
; AVX2-NEXT: sbbl %eax, %eax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v8i32_legal_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtd %ymm1, %ymm0, %k0
; AVX512-NEXT: vpmovm2w %k0, %xmm0
; AVX512-NEXT: vpmovmskb %xmm0, %ecx
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: negl %ecx
; AVX512-NEXT: sbbl %eax, %eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <8 x i32> %a0, %a1
%s = sext <8 x i1> %c to <8 x i16>
%r = call i16 @llvm.vector.reduce.or.v8i16(<8 x i16> %s)
%x = sext i16 %r to i32
ret i32 %x
}
define i16 @test_v8i16_sext(<8 x i16> %a0, <8 x i16> %a1) {
; SSE-LABEL: test_v8i16_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtw %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: # kill: def $ax killed $ax killed $eax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v8i16_sext:
; AVX: # %bb.0:
; AVX-NEXT: vpcmpgtw %xmm1, %xmm0, %xmm0
; AVX-NEXT: vpmovmskb %xmm0, %ecx
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: negl %ecx
; AVX-NEXT: sbbl %eax, %eax
; AVX-NEXT: # kill: def $ax killed $ax killed $eax
; AVX-NEXT: retq
%c = icmp sgt <8 x i16> %a0, %a1
%s = sext <8 x i1> %c to <8 x i16>
%r = call i16 @llvm.vector.reduce.or.v8i16(<8 x i16> %s)
ret i16 %r
}
define i16 @test_v16i16_sext(<16 x i16> %a0, <16 x i16> %a1) {
; SSE-LABEL: test_v16i16_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtw %xmm3, %xmm1
; SSE-NEXT: pcmpgtw %xmm2, %xmm0
; SSE-NEXT: por %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: # kill: def $ax killed $ax killed $eax
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v16i16_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtw %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtw %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %ecx
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: negl %ecx
; AVX1-NEXT: sbbl %eax, %eax
; AVX1-NEXT: # kill: def $ax killed $ax killed $eax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v16i16_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtw %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %ecx
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: negl %ecx
; AVX2-NEXT: sbbl %eax, %eax
; AVX2-NEXT: # kill: def $ax killed $ax killed $eax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v16i16_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtw %ymm1, %ymm0, %ymm0
; AVX512-NEXT: vpmovmskb %ymm0, %ecx
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: negl %ecx
; AVX512-NEXT: sbbl %eax, %eax
; AVX512-NEXT: # kill: def $ax killed $ax killed $eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <16 x i16> %a0, %a1
%s = sext <16 x i1> %c to <16 x i16>
%r = call i16 @llvm.vector.reduce.or.v16i16(<16 x i16> %s)
ret i16 %r
}
define i16 @test_v16i16_legal_sext(<16 x i16> %a0, <16 x i16> %a1) {
; SSE-LABEL: test_v16i16_legal_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtw %xmm3, %xmm1
; SSE-NEXT: pcmpgtw %xmm2, %xmm0
; SSE-NEXT: packsswb %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: # kill: def $ax killed $ax killed $eax
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v16i16_legal_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtw %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtw %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpacksswb %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %ecx
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: negl %ecx
; AVX1-NEXT: sbbl %eax, %eax
; AVX1-NEXT: # kill: def $ax killed $ax killed $eax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v16i16_legal_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtw %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %ecx
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: negl %ecx
; AVX2-NEXT: sbbl %eax, %eax
; AVX2-NEXT: # kill: def $ax killed $ax killed $eax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v16i16_legal_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtw %ymm1, %ymm0, %k0
; AVX512-NEXT: vpmovm2b %k0, %xmm0
; AVX512-NEXT: vpmovmskb %xmm0, %ecx
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: negl %ecx
; AVX512-NEXT: sbbl %eax, %eax
; AVX512-NEXT: # kill: def $ax killed $ax killed $eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <16 x i16> %a0, %a1
%s = sext <16 x i1> %c to <16 x i8>
%r = call i8 @llvm.vector.reduce.or.v16i8(<16 x i8> %s)
%x = sext i8 %r to i16
ret i16 %x
}
define i8 @test_v16i8_sext(<16 x i8> %a0, <16 x i8> %a1) {
; SSE-LABEL: test_v16i8_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtb %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: # kill: def $al killed $al killed $eax
; SSE-NEXT: retq
;
; AVX-LABEL: test_v16i8_sext:
; AVX: # %bb.0:
; AVX-NEXT: vpcmpgtb %xmm1, %xmm0, %xmm0
; AVX-NEXT: vpmovmskb %xmm0, %ecx
; AVX-NEXT: xorl %eax, %eax
; AVX-NEXT: negl %ecx
; AVX-NEXT: sbbl %eax, %eax
; AVX-NEXT: # kill: def $al killed $al killed $eax
; AVX-NEXT: retq
%c = icmp sgt <16 x i8> %a0, %a1
%s = sext <16 x i1> %c to <16 x i8>
%r = call i8 @llvm.vector.reduce.or.v16i8(<16 x i8> %s)
ret i8 %r
}
define i8 @test_v32i8_sext(<32 x i8> %a0, <32 x i8> %a1) {
; SSE-LABEL: test_v32i8_sext:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtb %xmm3, %xmm1
; SSE-NEXT: pcmpgtb %xmm2, %xmm0
; SSE-NEXT: por %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: xorl %eax, %eax
; SSE-NEXT: negl %ecx
; SSE-NEXT: sbbl %eax, %eax
; SSE-NEXT: # kill: def $al killed $al killed $eax
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v32i8_sext:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpgtb %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtb %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %ecx
; AVX1-NEXT: xorl %eax, %eax
; AVX1-NEXT: negl %ecx
; AVX1-NEXT: sbbl %eax, %eax
; AVX1-NEXT: # kill: def $al killed $al killed $eax
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v32i8_sext:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtb %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %ecx
; AVX2-NEXT: xorl %eax, %eax
; AVX2-NEXT: negl %ecx
; AVX2-NEXT: sbbl %eax, %eax
; AVX2-NEXT: # kill: def $al killed $al killed $eax
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v32i8_sext:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtb %ymm1, %ymm0, %ymm0
; AVX512-NEXT: vpmovmskb %ymm0, %ecx
; AVX512-NEXT: xorl %eax, %eax
; AVX512-NEXT: negl %ecx
; AVX512-NEXT: sbbl %eax, %eax
; AVX512-NEXT: # kill: def $al killed $al killed $eax
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%c = icmp sgt <32 x i8> %a0, %a1
%s = sext <32 x i1> %c to <32 x i8>
%r = call i8 @llvm.vector.reduce.or.v32i8(<32 x i8> %s)
ret i8 %r
}
define i1 @bool_reduction_v2f64(<2 x double> %x, <2 x double> %y) {
; SSE-LABEL: bool_reduction_v2f64:
; SSE: # %bb.0:
; SSE-NEXT: cmpltpd %xmm0, %xmm1
; SSE-NEXT: movmskpd %xmm1, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v2f64:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmpltpd %xmm0, %xmm1, %xmm0
; AVX1OR2-NEXT: vtestpd %xmm0, %xmm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v2f64:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmpltpd %xmm0, %xmm1, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%a = fcmp ogt <2 x double> %x, %y
%b = bitcast <2 x i1> %a to i2
%c = icmp ne i2 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v4f32(<4 x float> %x, <4 x float> %y) {
; SSE-LABEL: bool_reduction_v4f32:
; SSE: # %bb.0:
; SSE-NEXT: cmpeqps %xmm1, %xmm0
; SSE-NEXT: movmskps %xmm0, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v4f32:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmpeqps %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: vtestps %xmm0, %xmm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v4f32:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmpeqps %xmm1, %xmm0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%a = fcmp oeq <4 x float> %x, %y
%b = bitcast <4 x i1> %a to i4
%c = icmp ne i4 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v4f64(<4 x double> %x, <4 x double> %y) {
; SSE-LABEL: bool_reduction_v4f64:
; SSE: # %bb.0:
; SSE-NEXT: cmplepd %xmm1, %xmm3
; SSE-NEXT: cmplepd %xmm0, %xmm2
; SSE-NEXT: shufps {{.*#+}} xmm2 = xmm2[0,2],xmm3[0,2]
; SSE-NEXT: movmskps %xmm2, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v4f64:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmplepd %ymm0, %ymm1, %ymm0
; AVX1OR2-NEXT: vtestpd %ymm0, %ymm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: vzeroupper
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v4f64:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmplepd %ymm0, %ymm1, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = fcmp oge <4 x double> %x, %y
%b = bitcast <4 x i1> %a to i4
%c = icmp ne i4 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v8f32(<8 x float> %x, <8 x float> %y) {
; SSE-LABEL: bool_reduction_v8f32:
; SSE: # %bb.0:
; SSE-NEXT: cmpneqps %xmm3, %xmm1
; SSE-NEXT: cmpneqps %xmm2, %xmm0
; SSE-NEXT: packssdw %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v8f32:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vcmpneqps %ymm1, %ymm0, %ymm0
; AVX1OR2-NEXT: vtestps %ymm0, %ymm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: vzeroupper
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v8f32:
; AVX512: # %bb.0:
; AVX512-NEXT: vcmpneqps %ymm1, %ymm0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = fcmp une <8 x float> %x, %y
%b = bitcast <8 x i1> %a to i8
%c = icmp ne i8 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v2i64(<2 x i64> %x, <2 x i64> %y) {
; SSE2-LABEL: bool_reduction_v2i64:
; SSE2: # %bb.0:
; SSE2-NEXT: pcmpeqd %xmm1, %xmm0
; SSE2-NEXT: movmskps %xmm0, %eax
; SSE2-NEXT: xorl $15, %eax
; SSE2-NEXT: setne %al
; SSE2-NEXT: retq
;
; SSE42-LABEL: bool_reduction_v2i64:
; SSE42: # %bb.0:
; SSE42-NEXT: pxor %xmm1, %xmm0
; SSE42-NEXT: ptest %xmm0, %xmm0
; SSE42-NEXT: setne %al
; SSE42-NEXT: retq
;
; AVX-LABEL: bool_reduction_v2i64:
; AVX: # %bb.0:
; AVX-NEXT: vpxor %xmm1, %xmm0, %xmm0
; AVX-NEXT: vptest %xmm0, %xmm0
; AVX-NEXT: setne %al
; AVX-NEXT: retq
%a = icmp ne <2 x i64> %x, %y
%b = bitcast <2 x i1> %a to i2
%c = icmp ne i2 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v4i32(<4 x i32> %x, <4 x i32> %y) {
; SSE2-LABEL: bool_reduction_v4i32:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm2 = [2147483648,2147483648,2147483648,2147483648]
; SSE2-NEXT: pxor %xmm2, %xmm1
; SSE2-NEXT: pxor %xmm2, %xmm0
; SSE2-NEXT: pcmpgtd %xmm1, %xmm0
; SSE2-NEXT: movmskps %xmm0, %eax
; SSE2-NEXT: testl %eax, %eax
; SSE2-NEXT: setne %al
; SSE2-NEXT: retq
;
; SSE42-LABEL: bool_reduction_v4i32:
; SSE42: # %bb.0:
; SSE42-NEXT: pminud %xmm0, %xmm1
; SSE42-NEXT: pxor %xmm0, %xmm1
; SSE42-NEXT: ptest %xmm1, %xmm1
; SSE42-NEXT: setne %al
; SSE42-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v4i32:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vpminud %xmm1, %xmm0, %xmm1
; AVX1OR2-NEXT: vpxor %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: vptest %xmm0, %xmm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v4i32:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpnleud %xmm1, %xmm0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%a = icmp ugt <4 x i32> %x, %y
%b = bitcast <4 x i1> %a to i4
%c = icmp ne i4 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v8i16(<8 x i16> %x, <8 x i16> %y) {
; SSE-LABEL: bool_reduction_v8i16:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtw %xmm0, %xmm1
; SSE-NEXT: pmovmskb %xmm1, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v8i16:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vpcmpgtw %xmm0, %xmm1, %xmm0
; AVX1OR2-NEXT: vpmovmskb %xmm0, %eax
; AVX1OR2-NEXT: testl %eax, %eax
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v8i16:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtw %xmm0, %xmm1, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%a = icmp slt <8 x i16> %x, %y
%b = bitcast <8 x i1> %a to i8
%c = icmp ne i8 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v16i8(<16 x i8> %x, <16 x i8> %y) {
; SSE-LABEL: bool_reduction_v16i8:
; SSE: # %bb.0:
; SSE-NEXT: pcmpgtb %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1OR2-LABEL: bool_reduction_v16i8:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: vpcmpgtb %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: vpmovmskb %xmm0, %eax
; AVX1OR2-NEXT: testl %eax, %eax
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v16i8:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtb %xmm1, %xmm0, %k0
; AVX512-NEXT: kortestw %k0, %k0
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%a = icmp sgt <16 x i8> %x, %y
%b = bitcast <16 x i1> %a to i16
%c = icmp ne i16 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v4i64(<4 x i64> %x, <4 x i64> %y) {
; SSE2-LABEL: bool_reduction_v4i64:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm4 = [2147483648,2147483648]
; SSE2-NEXT: pxor %xmm4, %xmm1
; SSE2-NEXT: pxor %xmm4, %xmm3
; SSE2-NEXT: movdqa %xmm3, %xmm5
; SSE2-NEXT: pcmpgtd %xmm1, %xmm5
; SSE2-NEXT: pxor %xmm4, %xmm0
; SSE2-NEXT: pxor %xmm4, %xmm2
; SSE2-NEXT: movdqa %xmm2, %xmm4
; SSE2-NEXT: pcmpgtd %xmm0, %xmm4
; SSE2-NEXT: movdqa %xmm4, %xmm6
; SSE2-NEXT: shufps {{.*#+}} xmm6 = xmm6[0,2],xmm5[0,2]
; SSE2-NEXT: pcmpeqd %xmm1, %xmm3
; SSE2-NEXT: pcmpeqd %xmm0, %xmm2
; SSE2-NEXT: shufps {{.*#+}} xmm2 = xmm2[1,3],xmm3[1,3]
; SSE2-NEXT: andps %xmm6, %xmm2
; SSE2-NEXT: shufps {{.*#+}} xmm4 = xmm4[1,3],xmm5[1,3]
; SSE2-NEXT: orps %xmm2, %xmm4
; SSE2-NEXT: movmskps %xmm4, %eax
; SSE2-NEXT: testl %eax, %eax
; SSE2-NEXT: setne %al
; SSE2-NEXT: retq
;
; SSE42-LABEL: bool_reduction_v4i64:
; SSE42: # %bb.0:
; SSE42-NEXT: pcmpgtq %xmm1, %xmm3
; SSE42-NEXT: pcmpgtq %xmm0, %xmm2
; SSE42-NEXT: packssdw %xmm3, %xmm2
; SSE42-NEXT: movmskps %xmm2, %eax
; SSE42-NEXT: testl %eax, %eax
; SSE42-NEXT: setne %al
; SSE42-NEXT: retq
;
; AVX1-LABEL: bool_reduction_v4i64:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm3
; AVX1-NEXT: vpcmpgtq %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpgtq %xmm0, %xmm1, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vtestpd %xmm0, %xmm0
; AVX1-NEXT: setne %al
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: bool_reduction_v4i64:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpgtq %ymm0, %ymm1, %ymm0
; AVX2-NEXT: vtestpd %ymm0, %ymm0
; AVX2-NEXT: setne %al
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v4i64:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpgtq %ymm0, %ymm1, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = icmp slt <4 x i64> %x, %y
%b = bitcast <4 x i1> %a to i4
%c = icmp ne i4 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v8i32(<8 x i32> %x, <8 x i32> %y) {
; SSE2-LABEL: bool_reduction_v8i32:
; SSE2: # %bb.0:
; SSE2-NEXT: movdqa {{.*#+}} xmm4 = [2147483648,2147483648,2147483648,2147483648]
; SSE2-NEXT: pxor %xmm4, %xmm3
; SSE2-NEXT: pxor %xmm4, %xmm1
; SSE2-NEXT: pcmpgtd %xmm3, %xmm1
; SSE2-NEXT: pxor %xmm4, %xmm2
; SSE2-NEXT: pxor %xmm4, %xmm0
; SSE2-NEXT: pcmpgtd %xmm2, %xmm0
; SSE2-NEXT: packssdw %xmm1, %xmm0
; SSE2-NEXT: packsswb %xmm0, %xmm0
; SSE2-NEXT: pmovmskb %xmm0, %eax
; SSE2-NEXT: xorb $-1, %al
; SSE2-NEXT: setne %al
; SSE2-NEXT: retq
;
; SSE42-LABEL: bool_reduction_v8i32:
; SSE42: # %bb.0:
; SSE42-NEXT: pminud %xmm1, %xmm3
; SSE42-NEXT: pcmpeqd %xmm1, %xmm3
; SSE42-NEXT: pminud %xmm0, %xmm2
; SSE42-NEXT: pcmpeqd %xmm0, %xmm2
; SSE42-NEXT: packssdw %xmm3, %xmm2
; SSE42-NEXT: pmovmskb %xmm2, %eax
; SSE42-NEXT: testl %eax, %eax
; SSE42-NEXT: setne %al
; SSE42-NEXT: retq
;
; AVX1-LABEL: bool_reduction_v8i32:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpminud %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpeqd %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpminud %xmm1, %xmm0, %xmm1
; AVX1-NEXT: vpcmpeqd %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vtestps %xmm0, %xmm0
; AVX1-NEXT: setne %al
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: bool_reduction_v8i32:
; AVX2: # %bb.0:
; AVX2-NEXT: vpminud %ymm1, %ymm0, %ymm1
; AVX2-NEXT: vpcmpeqd %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vtestps %ymm0, %ymm0
; AVX2-NEXT: setne %al
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v8i32:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpleud %ymm1, %ymm0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb %al, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = icmp ule <8 x i32> %x, %y
%b = bitcast <8 x i1> %a to i8
%c = icmp ne i8 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v16i16(<16 x i16> %x, <16 x i16> %y) {
; SSE-LABEL: bool_reduction_v16i16:
; SSE: # %bb.0:
; SSE-NEXT: pcmpeqw %xmm3, %xmm1
; SSE-NEXT: pcmpeqw %xmm2, %xmm0
; SSE-NEXT: packsswb %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1-LABEL: bool_reduction_v16i16:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpeqw %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpeqw %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpacksswb %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %eax
; AVX1-NEXT: testl %eax, %eax
; AVX1-NEXT: setne %al
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: bool_reduction_v16i16:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpeqw %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %eax
; AVX2-NEXT: testl %eax, %eax
; AVX2-NEXT: setne %al
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v16i16:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpeqw %ymm1, %ymm0, %k0
; AVX512-NEXT: kortestw %k0, %k0
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = icmp eq <16 x i16> %x, %y
%b = bitcast <16 x i1> %a to i16
%c = icmp ne i16 %b, 0
ret i1 %c
}
define i1 @bool_reduction_v32i8(<32 x i8> %x, <32 x i8> %y) {
; SSE-LABEL: bool_reduction_v32i8:
; SSE: # %bb.0:
; SSE-NEXT: pcmpeqb %xmm3, %xmm1
; SSE-NEXT: pcmpeqb %xmm2, %xmm0
; SSE-NEXT: por %xmm1, %xmm0
; SSE-NEXT: pmovmskb %xmm0, %eax
; SSE-NEXT: testl %eax, %eax
; SSE-NEXT: setne %al
; SSE-NEXT: retq
;
; AVX1-LABEL: bool_reduction_v32i8:
; AVX1: # %bb.0:
; AVX1-NEXT: vextractf128 $1, %ymm1, %xmm2
; AVX1-NEXT: vextractf128 $1, %ymm0, %xmm3
; AVX1-NEXT: vpcmpeqb %xmm2, %xmm3, %xmm2
; AVX1-NEXT: vpcmpeqb %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpor %xmm2, %xmm0, %xmm0
; AVX1-NEXT: vpmovmskb %xmm0, %eax
; AVX1-NEXT: testl %eax, %eax
; AVX1-NEXT: setne %al
; AVX1-NEXT: vzeroupper
; AVX1-NEXT: retq
;
; AVX2-LABEL: bool_reduction_v32i8:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpeqb %ymm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %eax
; AVX2-NEXT: testl %eax, %eax
; AVX2-NEXT: setne %al
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: bool_reduction_v32i8:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpeqb %ymm1, %ymm0, %k0
; AVX512-NEXT: kortestd %k0, %k0
; AVX512-NEXT: setne %al
; AVX512-NEXT: vzeroupper
; AVX512-NEXT: retq
%a = icmp eq <32 x i8> %x, %y
%b = bitcast <32 x i1> %a to i32
%c = icmp ne i32 %b, 0
ret i1 %c
}
define {i32, i1} @test_v16i8_muti_uses(<16 x i8> %x, <16 x i8>%y, <16 x i8> %z) {
; SSE-LABEL: test_v16i8_muti_uses:
; SSE: # %bb.0:
; SSE-NEXT: pcmpeqb %xmm1, %xmm0
; SSE-NEXT: pcmpeqb %xmm1, %xmm2
; SSE-NEXT: pmovmskb %xmm0, %ecx
; SSE-NEXT: pmovmskb %xmm2, %eax
; SSE-NEXT: shll $16, %eax
; SSE-NEXT: orl %ecx, %eax
; SSE-NEXT: sete %dl
; SSE-NEXT: retq
;
; AVX1-LABEL: test_v16i8_muti_uses:
; AVX1: # %bb.0:
; AVX1-NEXT: vpcmpeqb %xmm1, %xmm0, %xmm0
; AVX1-NEXT: vpcmpeqb %xmm1, %xmm2, %xmm1
; AVX1-NEXT: vpmovmskb %xmm0, %ecx
; AVX1-NEXT: vpmovmskb %xmm1, %eax
; AVX1-NEXT: shll $16, %eax
; AVX1-NEXT: orl %ecx, %eax
; AVX1-NEXT: sete %dl
; AVX1-NEXT: retq
;
; AVX2-LABEL: test_v16i8_muti_uses:
; AVX2: # %bb.0:
; AVX2-NEXT: vpcmpeqb %xmm1, %xmm0, %xmm0
; AVX2-NEXT: vpcmpeqb %xmm1, %xmm2, %xmm1
; AVX2-NEXT: vinserti128 $1, %xmm1, %ymm0, %ymm0
; AVX2-NEXT: vpmovmskb %ymm0, %eax
; AVX2-NEXT: testl %eax, %eax
; AVX2-NEXT: sete %dl
; AVX2-NEXT: vzeroupper
; AVX2-NEXT: retq
;
; AVX512-LABEL: test_v16i8_muti_uses:
; AVX512: # %bb.0:
; AVX512-NEXT: vpcmpeqb %xmm1, %xmm0, %k0
; AVX512-NEXT: vpcmpeqb %xmm1, %xmm2, %k1
; AVX512-NEXT: kunpckwd %k0, %k1, %k0
; AVX512-NEXT: kortestd %k0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: sete %dl
; AVX512-NEXT: retq
%t1 = icmp eq <16 x i8> %x, %y
%t2 = icmp eq <16 x i8> %z, %y
%a = shufflevector <16 x i1> %t1, <16 x i1> %t2, <32 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7, i32 8, i32 9, i32 10, i32 11, i32 12, i32 13, i32 14, i32 15, i32 16, i32 17, i32 18, i32 19, i32 20, i32 21, i32 22, i32 23, i32 24, i32 25, i32 26, i32 27, i32 28, i32 29, i32 30, i32 31>
%b = bitcast <32 x i1> %a to i32
%c = icmp eq i32 %b, 0
%r1 = insertvalue {i32, i1} poison, i32 %b, 0
%r2 = insertvalue {i32, i1} %r1, i1 %c, 1
ret {i32, i1} %r2
}
; PR59867
define i1 @select_v2i8(ptr %s0, ptr %s1) {
; SSE2-LABEL: select_v2i8:
; SSE2: # %bb.0:
; SSE2-NEXT: movzwl (%rdi), %eax
; SSE2-NEXT: movd %eax, %xmm0
; SSE2-NEXT: movzwl (%rsi), %eax
; SSE2-NEXT: movd %eax, %xmm1
; SSE2-NEXT: pcmpeqb %xmm0, %xmm1
; SSE2-NEXT: punpcklbw {{.*#+}} xmm1 = xmm1[0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7]
; SSE2-NEXT: pshuflw {{.*#+}} xmm0 = xmm1[0,0,1,1,4,5,6,7]
; SSE2-NEXT: pshufd {{.*#+}} xmm0 = xmm0[0,0,1,1]
; SSE2-NEXT: movmskpd %xmm0, %eax
; SSE2-NEXT: testl %eax, %eax
; SSE2-NEXT: setne %al
; SSE2-NEXT: retq
;
; SSE42-LABEL: select_v2i8:
; SSE42: # %bb.0:
; SSE42-NEXT: movzwl (%rdi), %eax
; SSE42-NEXT: movd %eax, %xmm0
; SSE42-NEXT: movzwl (%rsi), %eax
; SSE42-NEXT: movd %eax, %xmm1
; SSE42-NEXT: pcmpeqb %xmm0, %xmm1
; SSE42-NEXT: pmovsxbq %xmm1, %xmm0
; SSE42-NEXT: movmskpd %xmm0, %eax
; SSE42-NEXT: testl %eax, %eax
; SSE42-NEXT: setne %al
; SSE42-NEXT: retq
;
; AVX1OR2-LABEL: select_v2i8:
; AVX1OR2: # %bb.0:
; AVX1OR2-NEXT: movzwl (%rdi), %eax
; AVX1OR2-NEXT: vmovd %eax, %xmm0
; AVX1OR2-NEXT: movzwl (%rsi), %eax
; AVX1OR2-NEXT: vmovd %eax, %xmm1
; AVX1OR2-NEXT: vpcmpeqb %xmm1, %xmm0, %xmm0
; AVX1OR2-NEXT: vpmovsxbq %xmm0, %xmm0
; AVX1OR2-NEXT: vtestpd %xmm0, %xmm0
; AVX1OR2-NEXT: setne %al
; AVX1OR2-NEXT: retq
;
; AVX512-LABEL: select_v2i8:
; AVX512: # %bb.0:
; AVX512-NEXT: movzwl (%rdi), %eax
; AVX512-NEXT: vmovd %eax, %xmm0
; AVX512-NEXT: movzwl (%rsi), %eax
; AVX512-NEXT: vmovd %eax, %xmm1
; AVX512-NEXT: vpcmpeqb %xmm1, %xmm0, %k0
; AVX512-NEXT: kmovd %k0, %eax
; AVX512-NEXT: testb $3, %al
; AVX512-NEXT: setne %al
; AVX512-NEXT: retq
%v0 = load <2 x i8>, ptr %s0, align 1
%v1 = load <2 x i8>, ptr %s1, align 1
%cmp = icmp eq <2 x i8> %v0, %v1
%cmp0 = extractelement <2 x i1> %cmp, i32 0
%cmp1 = extractelement <2 x i1> %cmp, i32 1
%res = select i1 %cmp0, i1 true, i1 %cmp1
ret i1 %res
}