forked from OSchip/llvm-project
LegalizeDAG: Implement promote for extract_vector_elt
This is for AMDGPU to implement v2i64 extract as extract of half of a v4i32. This is covered by existing tests and used by a future commit which makes 64-bit vectors legal types on AMDGPU. llvm-svn: 252630
This commit is contained in:
parent
2d858747df
commit
0b7958a59b
|
@ -4058,12 +4058,23 @@ void SelectionDAGLegalize::ConvertNodeToLibcall(SDNode *Node) {
|
|||
ReplaceNode(Node, Results.data());
|
||||
}
|
||||
|
||||
// Determine the vector type to use in place of an original scalar element when
|
||||
// promoting equally sized vectors.
|
||||
static MVT getPromotedVectorElementType(const TargetLowering &TLI,
|
||||
MVT EltVT, MVT NewEltVT) {
|
||||
unsigned OldEltsPerNewElt = EltVT.getSizeInBits() / NewEltVT.getSizeInBits();
|
||||
MVT MidVT = MVT::getVectorVT(NewEltVT, OldEltsPerNewElt);
|
||||
assert(TLI.isTypeLegal(MidVT) && "unexpected");
|
||||
return MidVT;
|
||||
}
|
||||
|
||||
void SelectionDAGLegalize::PromoteNode(SDNode *Node) {
|
||||
SmallVector<SDValue, 8> Results;
|
||||
MVT OVT = Node->getSimpleValueType(0);
|
||||
if (Node->getOpcode() == ISD::UINT_TO_FP ||
|
||||
Node->getOpcode() == ISD::SINT_TO_FP ||
|
||||
Node->getOpcode() == ISD::SETCC) {
|
||||
Node->getOpcode() == ISD::SETCC ||
|
||||
Node->getOpcode() == ISD::EXTRACT_VECTOR_ELT) {
|
||||
OVT = Node->getOperand(0).getSimpleValueType();
|
||||
}
|
||||
if (Node->getOpcode() == ISD::BR_CC)
|
||||
|
@ -4317,9 +4328,7 @@ void SelectionDAGLegalize::PromoteNode(SDNode *Node) {
|
|||
"Invalid promote type for build_vector");
|
||||
assert(NewEltVT.bitsLT(EltVT) && "not handled");
|
||||
|
||||
unsigned OldEltsPerNewElt = EltVT.getSizeInBits() / NewEltVT.getSizeInBits();
|
||||
MVT MidVT = MVT::getVectorVT(NewEltVT, OldEltsPerNewElt);
|
||||
assert(TLI.isTypeLegal(MidVT) && "unexpected");
|
||||
MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
|
||||
|
||||
SmallVector<SDValue, 8> NewOps;
|
||||
for (unsigned I = 0, E = Node->getNumOperands(); I != E; ++I) {
|
||||
|
@ -4333,6 +4342,51 @@ void SelectionDAGLegalize::PromoteNode(SDNode *Node) {
|
|||
Results.push_back(CvtVec);
|
||||
break;
|
||||
}
|
||||
case ISD::EXTRACT_VECTOR_ELT: {
|
||||
MVT EltVT = OVT.getVectorElementType();
|
||||
MVT NewEltVT = NVT.getVectorElementType();
|
||||
|
||||
// Handle bitcasts to a different vector type with the same total bit size.
|
||||
//
|
||||
// e.g. v2i64 = extract_vector_elt x:v2i64, y:i32
|
||||
// =>
|
||||
// v4i32:castx = bitcast x:v2i64
|
||||
//
|
||||
// i64 = bitcast
|
||||
// (v2i32 build_vector (i32 (extract_vector_elt castx, (2 * y))),
|
||||
// (i32 (extract_vector_elt castx, (2 * y + 1)))
|
||||
//
|
||||
|
||||
assert(NVT.isVector() && OVT.getSizeInBits() == NVT.getSizeInBits() &&
|
||||
"Invalid promote type for extract_vector_elt");
|
||||
assert(NewEltVT.bitsLT(EltVT) && "not handled");
|
||||
|
||||
MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
|
||||
unsigned NewEltsPerOldElt = MidVT.getVectorNumElements();
|
||||
|
||||
SDValue Idx = Node->getOperand(1);
|
||||
EVT IdxVT = Idx.getValueType();
|
||||
SDLoc SL(Node);
|
||||
SDValue Factor = DAG.getConstant(NewEltsPerOldElt, SL, IdxVT);
|
||||
SDValue NewBaseIdx = DAG.getNode(ISD::MUL, SL, IdxVT, Idx, Factor);
|
||||
|
||||
SDValue CastVec = DAG.getNode(ISD::BITCAST, SL, NVT, Node->getOperand(0));
|
||||
|
||||
SmallVector<SDValue, 8> NewOps;
|
||||
for (unsigned I = 0; I < NewEltsPerOldElt; ++I) {
|
||||
SDValue IdxOffset = DAG.getConstant(I, SL, IdxVT);
|
||||
SDValue TmpIdx = DAG.getNode(ISD::ADD, SL, IdxVT, NewBaseIdx, IdxOffset);
|
||||
|
||||
SDValue Elt = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, SL, NewEltVT,
|
||||
CastVec, TmpIdx);
|
||||
NewOps.push_back(Elt);
|
||||
}
|
||||
|
||||
SDValue NewVec = DAG.getNode(ISD::BUILD_VECTOR, SL, MidVT, NewOps);
|
||||
|
||||
Results.push_back(DAG.getNode(ISD::BITCAST, SL, EltVT, NewVec));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Replace the original node with the legalized result.
|
||||
|
|
Loading…
Reference in New Issue