forked from OSchip/llvm-project
[x86] fix predicate for avoiding vblendv
It only makes sense to produce the logic ops when 1 of the constants is +0.0. Otherwise, go with vblendv to reduce code. llvm-svn: 347403
This commit is contained in:
parent
59974412a4
commit
cadf62f360
|
@ -19632,7 +19632,7 @@ SDValue X86TargetLowering::LowerSELECT(SDValue Op, SelectionDAG &DAG) const {
|
|||
// of 3 logic instructions for size savings and potentially speed.
|
||||
// Unfortunately, there is no scalar form of VBLENDV.
|
||||
|
||||
// If either operand is a constant, don't try this. We can expect to
|
||||
// If either operand is a +0.0 constant, don't try this. We can expect to
|
||||
// optimize away at least one of the logic instructions later in that
|
||||
// case, so that sequence would be faster than a variable blend.
|
||||
|
||||
|
@ -19640,13 +19640,10 @@ SDValue X86TargetLowering::LowerSELECT(SDValue Op, SelectionDAG &DAG) const {
|
|||
// uses XMM0 as the selection register. That may need just as many
|
||||
// instructions as the AND/ANDN/OR sequence due to register moves, so
|
||||
// don't bother.
|
||||
|
||||
if (Subtarget.hasAVX() &&
|
||||
!isa<ConstantFPSDNode>(Op1) && !isa<ConstantFPSDNode>(Op2)) {
|
||||
|
||||
if (Subtarget.hasAVX() && !isNullFPConstant(Op1) &&
|
||||
!isNullFPConstant(Op2)) {
|
||||
// Convert to vectors, do a VSELECT, and convert back to scalar.
|
||||
// All of the conversions should be optimized away.
|
||||
|
||||
MVT VecVT = VT == MVT::f32 ? MVT::v4f32 : MVT::v2f64;
|
||||
SDValue VOp1 = DAG.getNode(ISD::SCALAR_TO_VECTOR, DL, VecVT, Op1);
|
||||
SDValue VOp2 = DAG.getNode(ISD::SCALAR_TO_VECTOR, DL, VecVT, Op2);
|
||||
|
|
|
@ -88,10 +88,8 @@ define double @fsel_nonzero_false_val(double %x, double %y, double %z) {
|
|||
; AVX-LABEL: fsel_nonzero_false_val:
|
||||
; AVX: # %bb.0:
|
||||
; AVX-NEXT: vcmpeqsd %xmm1, %xmm0, %xmm0
|
||||
; AVX-NEXT: vandpd %xmm2, %xmm0, %xmm1
|
||||
; AVX-NEXT: vmovsd {{.*#+}} xmm2 = mem[0],zero
|
||||
; AVX-NEXT: vandnpd %xmm2, %xmm0, %xmm0
|
||||
; AVX-NEXT: vorpd %xmm1, %xmm0, %xmm0
|
||||
; AVX-NEXT: vmovsd {{.*#+}} xmm1 = mem[0],zero
|
||||
; AVX-NEXT: vblendvpd %xmm0, %xmm2, %xmm1, %xmm0
|
||||
; AVX-NEXT: retq
|
||||
%cond = fcmp oeq double %x, %y
|
||||
%r = select i1 %cond, double %z, double 42.0
|
||||
|
@ -112,9 +110,7 @@ define double @fsel_nonzero_true_val(double %x, double %y, double %z) {
|
|||
; AVX: # %bb.0:
|
||||
; AVX-NEXT: vcmpeqsd %xmm1, %xmm0, %xmm0
|
||||
; AVX-NEXT: vmovsd {{.*#+}} xmm1 = mem[0],zero
|
||||
; AVX-NEXT: vandpd %xmm1, %xmm0, %xmm1
|
||||
; AVX-NEXT: vandnpd %xmm2, %xmm0, %xmm0
|
||||
; AVX-NEXT: vorpd %xmm1, %xmm0, %xmm0
|
||||
; AVX-NEXT: vblendvpd %xmm0, %xmm1, %xmm2, %xmm0
|
||||
; AVX-NEXT: retq
|
||||
%cond = fcmp oeq double %x, %y
|
||||
%r = select i1 %cond, double 42.0, double %z
|
||||
|
|
Loading…
Reference in New Issue