aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/CodeGen/SelectionDAG/SelectionDAG.cpp')
-rw-r--r--lib/CodeGen/SelectionDAG/SelectionDAG.cpp95
1 files changed, 52 insertions, 43 deletions
diff --git a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
index d70823379a..5780eff67a 100644
--- a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
+++ b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp
@@ -673,7 +673,9 @@ SDOperand SelectionDAG::getConstant(uint64_t Val, MVT::ValueType VT, bool isT) {
SDOperand SelectionDAG::getConstantFP(double Val, MVT::ValueType VT,
bool isTarget) {
assert(MVT::isFloatingPoint(VT) && "Cannot create integer FP constant!");
- if (VT == MVT::f32)
+ MVT::ValueType EltVT =
+ MVT::isVector(VT) ? MVT::getVectorElementType(VT) : VT;
+ if (EltVT == MVT::f32)
Val = (float)Val; // Mask out extra precision.
// Do the map lookup using the actual bit pattern for the floating point
@@ -681,15 +683,21 @@ SDOperand SelectionDAG::getConstantFP(double Val, MVT::ValueType VT,
// we don't have issues with SNANs.
unsigned Opc = isTarget ? ISD::TargetConstantFP : ISD::ConstantFP;
FoldingSetNodeID ID;
- AddNodeIDNode(ID, Opc, getVTList(VT), 0, 0);
+ AddNodeIDNode(ID, Opc, getVTList(EltVT), 0, 0);
ID.AddDouble(Val);
void *IP = 0;
if (SDNode *E = CSEMap.FindNodeOrInsertPos(ID, IP))
return SDOperand(E, 0);
- SDNode *N = new ConstantFPSDNode(isTarget, Val, VT);
+ SDNode *N = new ConstantFPSDNode(isTarget, Val, EltVT);
CSEMap.InsertNode(N, IP);
AllNodes.push_back(N);
- return SDOperand(N, 0);
+ SDOperand Result(N, 0);
+ if (MVT::isVector(VT)) {
+ SmallVector<SDOperand, 8> Ops;
+ Ops.assign(MVT::getVectorNumElements(VT), Result);
+ Result = getNode(ISD::BUILD_VECTOR, VT, &Ops[0], Ops.size());
+ }
+ return Result;
}
SDOperand SelectionDAG::getGlobalAddress(const GlobalValue *GV,
@@ -1952,6 +1960,23 @@ SDOperand SelectionDAG::getNode(unsigned Opcode, MVT::ValueType VT,
if (EVT == VT) return N1; // Not actually extending
break;
}
+ case ISD::EXTRACT_VECTOR_ELT:
+ assert(N2C && "Bad EXTRACT_VECTOR_ELT!");
+
+ // EXTRACT_VECTOR_ELT of BUILD_PAIR is often formed while lowering is
+ // expanding copies of large vectors from registers.
+ if (N1.getOpcode() == ISD::BUILD_PAIR) {
+ unsigned NewNumElts = MVT::getVectorNumElements(N1.getValueType()) / 2;
+ bool Low = N2C->getValue() < NewNumElts;
+ return getNode(ISD::EXTRACT_VECTOR_ELT, VT, N1.getOperand(!Low),
+ Low ? N2 : getConstant(N2C->getValue() - NewNumElts,
+ N2.getValueType()));
+ }
+ // EXTRACT_VECTOR_ELT of BUILD_VECTOR is often formed while lowering is
+ // expanding large vector constants.
+ if (N1.getOpcode() == ISD::BUILD_VECTOR)
+ return N1.getOperand(N2C->getValue());
+ break;
case ISD::EXTRACT_ELEMENT:
assert(N2C && (unsigned)N2C->getValue() < 2 && "Bad EXTRACT_ELEMENT!");
@@ -2045,14 +2070,10 @@ SDOperand SelectionDAG::getNode(unsigned Opcode, MVT::ValueType VT,
MVT::getVectorNumElements(VT) == N3.getNumOperands() &&
"Illegal VECTOR_SHUFFLE node!");
break;
- case ISD::VBIT_CONVERT:
- // Fold vbit_convert nodes from a type to themselves.
- if (N1.getValueType() == MVT::Vector) {
- assert(isa<ConstantSDNode>(*(N1.Val->op_end()-2)) &&
- isa<VTSDNode>(*(N1.Val->op_end()-1)) && "Malformed vector input!");
- if (*(N1.Val->op_end()-2) == N2 && *(N1.Val->op_end()-1) == N3)
- return N1;
- }
+ case ISD::BIT_CONVERT:
+ // Fold bit_convert nodes from a type to themselves.
+ if (N1.getValueType() == VT)
+ return N1;
break;
}
@@ -2095,7 +2116,7 @@ SDOperand SelectionDAG::getLoad(MVT::ValueType VT,
bool isVolatile, unsigned Alignment) {
if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0;
- if (VT != MVT::Vector && VT != MVT::iPTR) {
+ if (VT != MVT::iPTR) {
Ty = MVT::getTypeForValueType(VT);
} else if (SV) {
const PointerType *PT = dyn_cast<PointerType>(SV->getType());
@@ -2149,7 +2170,7 @@ SDOperand SelectionDAG::getExtLoad(ISD::LoadExtType ExtType, MVT::ValueType VT,
if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0;
- if (VT != MVT::Vector && VT != MVT::iPTR) {
+ if (VT != MVT::iPTR) {
Ty = MVT::getTypeForValueType(VT);
} else if (SV) {
const PointerType *PT = dyn_cast<PointerType>(SV->getType());
@@ -2211,14 +2232,6 @@ SelectionDAG::getIndexedLoad(SDOperand OrigLoad, SDOperand Base,
return SDOperand(N, 0);
}
-SDOperand SelectionDAG::getVecLoad(unsigned Count, MVT::ValueType EVT,
- SDOperand Chain, SDOperand Ptr,
- SDOperand SV) {
- SDOperand Ops[] = { Chain, Ptr, SV, getConstant(Count, MVT::i32),
- getValueType(EVT) };
- return getNode(ISD::VLOAD, getVTList(MVT::Vector, MVT::Other), Ops, 5);
-}
-
SDOperand SelectionDAG::getStore(SDOperand Chain, SDOperand Val,
SDOperand Ptr, const Value *SV, int SVOffset,
bool isVolatile, unsigned Alignment) {
@@ -2226,7 +2239,7 @@ SDOperand SelectionDAG::getStore(SDOperand Chain, SDOperand Val,
if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0;
- if (VT != MVT::Vector && VT != MVT::iPTR) {
+ if (VT != MVT::iPTR) {
Ty = MVT::getTypeForValueType(VT);
} else if (SV) {
const PointerType *PT = dyn_cast<PointerType>(SV->getType());
@@ -2271,7 +2284,7 @@ SDOperand SelectionDAG::getTruncStore(SDOperand Chain, SDOperand Val,
if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0;
- if (VT != MVT::Vector && VT != MVT::iPTR) {
+ if (VT != MVT::iPTR) {
Ty = MVT::getTypeForValueType(VT);
} else if (SV) {
const PointerType *PT = dyn_cast<PointerType>(SV->getType());
@@ -2462,7 +2475,18 @@ SDOperand SelectionDAG::getNode(unsigned Opcode, SDVTList VTList,
}
SDVTList SelectionDAG::getVTList(MVT::ValueType VT) {
- return makeVTList(SDNode::getValueTypeList(VT), 1);
+ if (!MVT::isExtendedValueType(VT))
+ return makeVTList(SDNode::getValueTypeList(VT), 1);
+
+ for (std::list<std::vector<MVT::ValueType> >::iterator I = VTList.begin(),
+ E = VTList.end(); I != E; ++I) {
+ if (I->size() == 1 && (*I)[0] == VT)
+ return makeVTList(&(*I)[0], 1);
+ }
+ std::vector<MVT::ValueType> V;
+ V.push_back(VT);
+ VTList.push_front(V);
+ return makeVTList(&(*VTList.begin())[0], 1);
}
SDVTList SelectionDAG::getVTList(MVT::ValueType VT1, MVT::ValueType VT2) {
@@ -2496,7 +2520,7 @@ SDVTList SelectionDAG::getVTList(MVT::ValueType VT1, MVT::ValueType VT2,
SDVTList SelectionDAG::getVTList(const MVT::ValueType *VTs, unsigned NumVTs) {
switch (NumVTs) {
case 0: assert(0 && "Cannot have nodes without results!");
- case 1: return makeVTList(SDNode::getValueTypeList(VTs[0]), 1);
+ case 1: return getVTList(VTs[0]);
case 2: return getVTList(VTs[0], VTs[1]);
case 3: return getVTList(VTs[0], VTs[1], VTs[2]);
default: break;
@@ -3394,30 +3418,16 @@ std::string SDNode::getOperationName(const SelectionDAG *G) const {
case ISD::FDIV: return "fdiv";
case ISD::FREM: return "frem";
case ISD::FCOPYSIGN: return "fcopysign";
- case ISD::VADD: return "vadd";
- case ISD::VSUB: return "vsub";
- case ISD::VMUL: return "vmul";
- case ISD::VSDIV: return "vsdiv";
- case ISD::VUDIV: return "vudiv";
- case ISD::VAND: return "vand";
- case ISD::VOR: return "vor";
- case ISD::VXOR: return "vxor";
case ISD::SETCC: return "setcc";
case ISD::SELECT: return "select";
case ISD::SELECT_CC: return "select_cc";
- case ISD::VSELECT: return "vselect";
case ISD::INSERT_VECTOR_ELT: return "insert_vector_elt";
- case ISD::VINSERT_VECTOR_ELT: return "vinsert_vector_elt";
case ISD::EXTRACT_VECTOR_ELT: return "extract_vector_elt";
- case ISD::VEXTRACT_VECTOR_ELT: return "vextract_vector_elt";
- case ISD::VCONCAT_VECTORS: return "vconcat_vectors";
- case ISD::VEXTRACT_SUBVECTOR: return "vextract_subvector";
+ case ISD::CONCAT_VECTORS: return "concat_vectors";
+ case ISD::EXTRACT_SUBVECTOR: return "extract_subvector";
case ISD::SCALAR_TO_VECTOR: return "scalar_to_vector";
- case ISD::VBUILD_VECTOR: return "vbuild_vector";
case ISD::VECTOR_SHUFFLE: return "vector_shuffle";
- case ISD::VVECTOR_SHUFFLE: return "vvector_shuffle";
- case ISD::VBIT_CONVERT: return "vbit_convert";
case ISD::CARRY_FALSE: return "carry_false";
case ISD::ADDC: return "addc";
case ISD::ADDE: return "adde";
@@ -3456,7 +3466,6 @@ std::string SDNode::getOperationName(const SelectionDAG *G) const {
// Other operators
case ISD::LOAD: return "load";
case ISD::STORE: return "store";
- case ISD::VLOAD: return "vload";
case ISD::VAARG: return "vaarg";
case ISD::VACOPY: return "vacopy";
case ISD::VAEND: return "vaend";