diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp index 378eb97a7469c..12d36071ca9f6 100644 --- a/llvm/lib/Target/X86/X86ISelLowering.cpp +++ b/llvm/lib/Target/X86/X86ISelLowering.cpp @@ -40906,6 +40906,28 @@ bool X86TargetLowering::SimplifyDemandedBitsForTargetNode( Known.One.setHighBits(ShAmt); return false; } + case X86ISD::BLENDV: { + SDValue Sel = Op.getOperand(0); + SDValue LHS = Op.getOperand(1); + SDValue RHS = Op.getOperand(2); + + APInt SignMask = APInt::getSignMask(BitWidth); + SDValue NewSel = SimplifyMultipleUseDemandedBits( + Sel, SignMask, OriginalDemandedElts, TLO.DAG, Depth + 1); + SDValue NewLHS = SimplifyMultipleUseDemandedBits( + LHS, OriginalDemandedBits, OriginalDemandedElts, TLO.DAG, Depth + 1); + SDValue NewRHS = SimplifyMultipleUseDemandedBits( + RHS, OriginalDemandedBits, OriginalDemandedElts, TLO.DAG, Depth + 1); + + if (NewSel || NewLHS || NewRHS) { + NewSel = NewSel ? NewSel : Sel; + NewLHS = NewLHS ? NewLHS : LHS; + NewRHS = NewRHS ? NewRHS : RHS; + return TLO.CombineTo(Op, TLO.DAG.getNode(X86ISD::BLENDV, SDLoc(Op), VT, + NewSel, NewLHS, NewRHS)); + } + break; + } case X86ISD::PEXTRB: case X86ISD::PEXTRW: { SDValue Vec = Op.getOperand(0); diff --git a/llvm/test/CodeGen/X86/vselect.ll b/llvm/test/CodeGen/X86/vselect.ll index adeeb874c7bb9..c7439e12098d4 100644 --- a/llvm/test/CodeGen/X86/vselect.ll +++ b/llvm/test/CodeGen/X86/vselect.ll @@ -535,8 +535,8 @@ define <2 x i64> @shrunkblend_nonvselectuse(<2 x i1> %cond, <2 x i64> %a, <2 x i ; SSE41-LABEL: shrunkblend_nonvselectuse: ; SSE41: # %bb.0: ; SSE41-NEXT: psllq $63, %xmm0 -; SSE41-NEXT: psrad $31, %xmm0 ; SSE41-NEXT: blendvpd %xmm0, %xmm1, %xmm2 +; SSE41-NEXT: psrad $31, %xmm0 ; SSE41-NEXT: pshufd {{.*#+}} xmm0 = xmm0[1,1,3,3] ; SSE41-NEXT: paddq %xmm2, %xmm0 ; SSE41-NEXT: retq