forked from OSchip/llvm-project
[X86][SSE] Pull out duplicate VSELECT to shuffle mask code. NFCI.
llvm-svn: 338693
This commit is contained in:
parent
48eba54f18
commit
8b16e15d47
|
@ -9097,6 +9097,28 @@ static SmallVector<int, 64> createTargetShuffleMask(ArrayRef<int> Mask,
|
||||||
return TargetMask;
|
return TargetMask;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Attempt to create a shuffle mask from a VSELECT condition mask.
|
||||||
|
static bool createShuffleMaskFromVSELECT(SmallVectorImpl<int> &Mask,
|
||||||
|
SDValue Cond) {
|
||||||
|
if (!ISD::isBuildVectorOfConstantSDNodes(Cond.getNode()))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
unsigned Size = Cond.getValueType().getVectorNumElements();
|
||||||
|
Mask.resize(Size, SM_SentinelUndef);
|
||||||
|
|
||||||
|
for (int i = 0; i != (int)Size; ++i) {
|
||||||
|
SDValue CondElt = Cond.getOperand(i);
|
||||||
|
Mask[i] = i;
|
||||||
|
// Arbitrarily choose from the 2nd operand if the select condition element
|
||||||
|
// is undef.
|
||||||
|
// TODO: Can we do better by matching patterns such as even/odd?
|
||||||
|
if (CondElt.isUndef() || isNullConstant(CondElt))
|
||||||
|
Mask[i] += Size;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// Check if the shuffle mask is suitable for the AVX vpunpcklwd or vpunpckhwd
|
// Check if the shuffle mask is suitable for the AVX vpunpcklwd or vpunpckhwd
|
||||||
// instructions.
|
// instructions.
|
||||||
static bool isUnpackWdShuffleMask(ArrayRef<int> Mask, MVT VT) {
|
static bool isUnpackWdShuffleMask(ArrayRef<int> Mask, MVT VT) {
|
||||||
|
@ -15135,26 +15157,15 @@ static SDValue lowerVSELECTtoVectorShuffle(SDValue Op,
|
||||||
SDValue Cond = Op.getOperand(0);
|
SDValue Cond = Op.getOperand(0);
|
||||||
SDValue LHS = Op.getOperand(1);
|
SDValue LHS = Op.getOperand(1);
|
||||||
SDValue RHS = Op.getOperand(2);
|
SDValue RHS = Op.getOperand(2);
|
||||||
SDLoc dl(Op);
|
|
||||||
MVT VT = Op.getSimpleValueType();
|
MVT VT = Op.getSimpleValueType();
|
||||||
|
|
||||||
if (!ISD::isBuildVectorOfConstantSDNodes(Cond.getNode()))
|
|
||||||
return SDValue();
|
|
||||||
auto *CondBV = cast<BuildVectorSDNode>(Cond);
|
|
||||||
|
|
||||||
// Only non-legal VSELECTs reach this lowering, convert those into generic
|
// Only non-legal VSELECTs reach this lowering, convert those into generic
|
||||||
// shuffles and re-use the shuffle lowering path for blends.
|
// shuffles and re-use the shuffle lowering path for blends.
|
||||||
SmallVector<int, 32> Mask;
|
SmallVector<int, 32> Mask;
|
||||||
for (int i = 0, Size = VT.getVectorNumElements(); i < Size; ++i) {
|
if (createShuffleMaskFromVSELECT(Mask, Cond))
|
||||||
SDValue CondElt = CondBV->getOperand(i);
|
return DAG.getVectorShuffle(VT, SDLoc(Op), LHS, RHS, Mask);
|
||||||
int M = i;
|
|
||||||
// We can't map undef to undef here. They have different meanings. Treat
|
return SDValue();
|
||||||
// as the same as zero.
|
|
||||||
if (CondElt.isUndef() || isNullConstant(CondElt))
|
|
||||||
M += Size;
|
|
||||||
Mask.push_back(M);
|
|
||||||
}
|
|
||||||
return DAG.getVectorShuffle(VT, dl, LHS, RHS, Mask);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
SDValue X86TargetLowering::LowerVSELECT(SDValue Op, SelectionDAG &DAG) const {
|
SDValue X86TargetLowering::LowerVSELECT(SDValue Op, SelectionDAG &DAG) const {
|
||||||
|
@ -32560,18 +32571,9 @@ static SDValue combineSelect(SDNode *N, SelectionDAG &DAG,
|
||||||
// Convert vselects with constant condition into shuffles.
|
// Convert vselects with constant condition into shuffles.
|
||||||
if (ISD::isBuildVectorOfConstantSDNodes(Cond.getNode()) &&
|
if (ISD::isBuildVectorOfConstantSDNodes(Cond.getNode()) &&
|
||||||
DCI.isBeforeLegalizeOps()) {
|
DCI.isBeforeLegalizeOps()) {
|
||||||
SmallVector<int, 64> Mask(VT.getVectorNumElements(), -1);
|
SmallVector<int, 64> Mask;
|
||||||
for (int i = 0, Size = Mask.size(); i != Size; ++i) {
|
if (createShuffleMaskFromVSELECT(Mask, Cond))
|
||||||
SDValue CondElt = Cond->getOperand(i);
|
return DAG.getVectorShuffle(VT, DL, LHS, RHS, Mask);
|
||||||
Mask[i] = i;
|
|
||||||
// Arbitrarily choose from the 2nd operand if the select condition element
|
|
||||||
// is undef.
|
|
||||||
// TODO: Can we do better by matching patterns such as even/odd?
|
|
||||||
if (CondElt.isUndef() || isNullConstant(CondElt))
|
|
||||||
Mask[i] += Size;
|
|
||||||
}
|
|
||||||
|
|
||||||
return DAG.getVectorShuffle(VT, DL, LHS, RHS, Mask);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// If we have SSE[12] support, try to form min/max nodes. SSE min/max
|
// If we have SSE[12] support, try to form min/max nodes. SSE min/max
|
||||||
|
|
Loading…
Reference in New Issue