Implement LegalizeTypes support for softfloat LOAD.

In order to handle indexed nodes I had to introduce
a new constructor, and since I was there I factorized
the code in the various load constructors.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@48894 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Duncan Sands 2008-03-27 20:23:40 +00:00
parent 86e1ebf9bb
commit 14ea39cf3c
4 changed files with 73 additions and 82 deletions

View File

@ -379,6 +379,11 @@ public:
unsigned Alignment=0); unsigned Alignment=0);
SDOperand getIndexedLoad(SDOperand OrigLoad, SDOperand Base, SDOperand getIndexedLoad(SDOperand OrigLoad, SDOperand Base,
SDOperand Offset, ISD::MemIndexedMode AM); SDOperand Offset, ISD::MemIndexedMode AM);
SDOperand getAnyLoad(ISD::MemIndexedMode AM, ISD::LoadExtType ExtType,
MVT::ValueType VT, SDOperand Chain,
SDOperand Ptr, SDOperand Offset,
const Value *SV, int SVOffset, MVT::ValueType EVT,
bool isVolatile=false, unsigned Alignment=0);
/// getStore - Helper function to build ISD::STORE nodes. /// getStore - Helper function to build ISD::STORE nodes.
/// ///

View File

@ -310,6 +310,7 @@ private:
SDOperand FloatToIntRes_BIT_CONVERT(SDNode *N); SDOperand FloatToIntRes_BIT_CONVERT(SDNode *N);
SDOperand FloatToIntRes_BUILD_PAIR(SDNode *N); SDOperand FloatToIntRes_BUILD_PAIR(SDNode *N);
SDOperand FloatToIntRes_FCOPYSIGN(SDNode *N); SDOperand FloatToIntRes_FCOPYSIGN(SDNode *N);
SDOperand FloatToIntRes_LOAD(SDNode *N);
// Operand Float to Integer Conversion. // Operand Float to Integer Conversion.
bool FloatToIntOperand(SDNode *N, unsigned OpNo); bool FloatToIntOperand(SDNode *N, unsigned OpNo);

View File

@ -53,6 +53,7 @@ void DAGTypeLegalizer::FloatToIntResult(SDNode *N, unsigned ResNo) {
case ISD::BIT_CONVERT: R = FloatToIntRes_BIT_CONVERT(N); break; case ISD::BIT_CONVERT: R = FloatToIntRes_BIT_CONVERT(N); break;
case ISD::BUILD_PAIR: R = FloatToIntRes_BUILD_PAIR(N); break; case ISD::BUILD_PAIR: R = FloatToIntRes_BUILD_PAIR(N); break;
case ISD::FCOPYSIGN: R = FloatToIntRes_FCOPYSIGN(N); break; case ISD::FCOPYSIGN: R = FloatToIntRes_FCOPYSIGN(N); break;
case ISD::LOAD: R = FloatToIntRes_LOAD(N); break;
} }
// If R is null, the sub-method took care of registering the result. // If R is null, the sub-method took care of registering the result.
@ -111,6 +112,16 @@ SDOperand DAGTypeLegalizer::FloatToIntRes_FCOPYSIGN(SDNode *N) {
return DAG.getNode(ISD::OR, LVT, LHS, SignBit); return DAG.getNode(ISD::OR, LVT, LHS, SignBit);
} }
SDOperand DAGTypeLegalizer::FloatToIntRes_LOAD(SDNode *N) {
MVT::ValueType NVT = TLI.getTypeToTransformTo(N->getValueType(0));
LoadSDNode *L = cast<LoadSDNode>(N);
return DAG.getAnyLoad(L->getAddressingMode(), L->getExtensionType(),
NVT, L->getChain(), L->getBasePtr(), L->getOffset(),
L->getSrcValue(), L->getSrcValueOffset(),
L->getMemoryVT(), L->isVolatile(), L->getAlignment());
}
//===----------------------------------------------------------------------===// //===----------------------------------------------------------------------===//
// Operand Float to Integer Conversion.. // Operand Float to Integer Conversion..

View File

@ -2447,10 +2447,12 @@ SDOperand SelectionDAG::getAtomic(unsigned Opcode, SDOperand Chain,
return SDOperand(N, 0); return SDOperand(N, 0);
} }
SDOperand SelectionDAG::getLoad(MVT::ValueType VT, SDOperand
SDOperand Chain, SDOperand Ptr, SelectionDAG::getAnyLoad(ISD::MemIndexedMode AM, ISD::LoadExtType ExtType,
const Value *SV, int SVOffset, MVT::ValueType VT, SDOperand Chain,
bool isVolatile, unsigned Alignment) { SDOperand Ptr, SDOperand Offset,
const Value *SV, int SVOffset, MVT::ValueType EVT,
bool isVolatile, unsigned Alignment) {
if (Alignment == 0) { // Ensure that codegen never sees alignment 0 if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0; const Type *Ty = 0;
if (VT != MVT::iPTR) { if (VT != MVT::iPTR) {
@ -2459,69 +2461,38 @@ SDOperand SelectionDAG::getLoad(MVT::ValueType VT,
const PointerType *PT = dyn_cast<PointerType>(SV->getType()); const PointerType *PT = dyn_cast<PointerType>(SV->getType());
assert(PT && "Value for load must be a pointer"); assert(PT && "Value for load must be a pointer");
Ty = PT->getElementType(); Ty = PT->getElementType();
} }
assert(Ty && "Could not get type information for load"); assert(Ty && "Could not get type information for load");
Alignment = TLI.getTargetData()->getABITypeAlignment(Ty); Alignment = TLI.getTargetData()->getABITypeAlignment(Ty);
} }
SDVTList VTs = getVTList(VT, MVT::Other);
SDOperand Undef = getNode(ISD::UNDEF, Ptr.getValueType());
SDOperand Ops[] = { Chain, Ptr, Undef };
FoldingSetNodeID ID;
AddNodeIDNode(ID, ISD::LOAD, VTs, Ops, 3);
ID.AddInteger(ISD::UNINDEXED);
ID.AddInteger(ISD::NON_EXTLOAD);
ID.AddInteger((unsigned int)VT);
ID.AddInteger(Alignment);
ID.AddInteger(isVolatile);
void *IP = 0;
if (SDNode *E = CSEMap.FindNodeOrInsertPos(ID, IP))
return SDOperand(E, 0);
SDNode *N = new LoadSDNode(Ops, VTs, ISD::UNINDEXED,
ISD::NON_EXTLOAD, VT, SV, SVOffset, Alignment,
isVolatile);
CSEMap.InsertNode(N, IP);
AllNodes.push_back(N);
return SDOperand(N, 0);
}
SDOperand SelectionDAG::getExtLoad(ISD::LoadExtType ExtType, MVT::ValueType VT, if (VT == EVT) {
SDOperand Chain, SDOperand Ptr, ExtType = ISD::NON_EXTLOAD;
const Value *SV, } else if (ExtType == ISD::NON_EXTLOAD) {
int SVOffset, MVT::ValueType EVT, assert(VT == EVT && "Non-extending load from different memory type!");
bool isVolatile, unsigned Alignment) { } else {
// If they are asking for an extending load from/to the same thing, return a // Extending load.
// normal load. if (MVT::isVector(VT))
if (VT == EVT) assert(EVT == MVT::getVectorElementType(VT) && "Invalid vector extload!");
return getLoad(VT, Chain, Ptr, SV, SVOffset, isVolatile, Alignment); else
assert(MVT::getSizeInBits(EVT) < MVT::getSizeInBits(VT) &&
if (MVT::isVector(VT)) "Should only be an extending load, not truncating!");
assert(EVT == MVT::getVectorElementType(VT) && "Invalid vector extload!"); assert((ExtType == ISD::EXTLOAD || MVT::isInteger(VT)) &&
else "Cannot sign/zero extend a FP/Vector load!");
assert(MVT::getSizeInBits(EVT) < MVT::getSizeInBits(VT) && assert(MVT::isInteger(VT) == MVT::isInteger(EVT) &&
"Should only be an extending load, not truncating!"); "Cannot convert from FP to Int or Int -> FP!");
assert((ExtType == ISD::EXTLOAD || MVT::isInteger(VT)) &&
"Cannot sign/zero extend a FP/Vector load!");
assert(MVT::isInteger(VT) == MVT::isInteger(EVT) &&
"Cannot convert from FP to Int or Int -> FP!");
if (Alignment == 0) { // Ensure that codegen never sees alignment 0
const Type *Ty = 0;
if (VT != MVT::iPTR) {
Ty = MVT::getTypeForValueType(VT);
} else if (SV) {
const PointerType *PT = dyn_cast<PointerType>(SV->getType());
assert(PT && "Value for load must be a pointer");
Ty = PT->getElementType();
}
assert(Ty && "Could not get type information for load");
Alignment = TLI.getTargetData()->getABITypeAlignment(Ty);
} }
SDVTList VTs = getVTList(VT, MVT::Other);
SDOperand Undef = getNode(ISD::UNDEF, Ptr.getValueType()); bool Indexed = AM != ISD::UNINDEXED;
SDOperand Ops[] = { Chain, Ptr, Undef }; assert(Indexed || Offset.getOpcode() == ISD::UNDEF &&
"Unindexed load with an offset!");
SDVTList VTs = Indexed ?
getVTList(VT, Ptr.getValueType(), MVT::Other) : getVTList(VT, MVT::Other);
SDOperand Ops[] = { Chain, Ptr, Offset };
FoldingSetNodeID ID; FoldingSetNodeID ID;
AddNodeIDNode(ID, ISD::LOAD, VTs, Ops, 3); AddNodeIDNode(ID, ISD::LOAD, VTs, Ops, 3);
ID.AddInteger(ISD::UNINDEXED); ID.AddInteger(AM);
ID.AddInteger(ExtType); ID.AddInteger(ExtType);
ID.AddInteger((unsigned int)EVT); ID.AddInteger((unsigned int)EVT);
ID.AddInteger(Alignment); ID.AddInteger(Alignment);
@ -2529,39 +2500,42 @@ SDOperand SelectionDAG::getExtLoad(ISD::LoadExtType ExtType, MVT::ValueType VT,
void *IP = 0; void *IP = 0;
if (SDNode *E = CSEMap.FindNodeOrInsertPos(ID, IP)) if (SDNode *E = CSEMap.FindNodeOrInsertPos(ID, IP))
return SDOperand(E, 0); return SDOperand(E, 0);
SDNode *N = new LoadSDNode(Ops, VTs, ISD::UNINDEXED, ExtType, EVT, SDNode *N = new LoadSDNode(Ops, VTs, AM, ExtType, EVT, SV, SVOffset,
SV, SVOffset, Alignment, isVolatile); Alignment, isVolatile);
CSEMap.InsertNode(N, IP); CSEMap.InsertNode(N, IP);
AllNodes.push_back(N); AllNodes.push_back(N);
return SDOperand(N, 0); return SDOperand(N, 0);
} }
SDOperand SelectionDAG::getLoad(MVT::ValueType VT,
SDOperand Chain, SDOperand Ptr,
const Value *SV, int SVOffset,
bool isVolatile, unsigned Alignment) {
SDOperand Undef = getNode(ISD::UNDEF, Ptr.getValueType());
return getAnyLoad(ISD::UNINDEXED, ISD::NON_EXTLOAD, VT, Chain, Ptr, Undef,
SV, SVOffset, VT, isVolatile, Alignment);
}
SDOperand SelectionDAG::getExtLoad(ISD::LoadExtType ExtType, MVT::ValueType VT,
SDOperand Chain, SDOperand Ptr,
const Value *SV,
int SVOffset, MVT::ValueType EVT,
bool isVolatile, unsigned Alignment) {
SDOperand Undef = getNode(ISD::UNDEF, Ptr.getValueType());
return getAnyLoad(ISD::UNINDEXED, ExtType, VT, Chain, Ptr, Undef,
SV, SVOffset, EVT, isVolatile, Alignment);
}
SDOperand SDOperand
SelectionDAG::getIndexedLoad(SDOperand OrigLoad, SDOperand Base, SelectionDAG::getIndexedLoad(SDOperand OrigLoad, SDOperand Base,
SDOperand Offset, ISD::MemIndexedMode AM) { SDOperand Offset, ISD::MemIndexedMode AM) {
LoadSDNode *LD = cast<LoadSDNode>(OrigLoad); LoadSDNode *LD = cast<LoadSDNode>(OrigLoad);
assert(LD->getOffset().getOpcode() == ISD::UNDEF && assert(LD->getOffset().getOpcode() == ISD::UNDEF &&
"Load is already a indexed load!"); "Load is already a indexed load!");
MVT::ValueType VT = OrigLoad.getValueType(); return getAnyLoad(AM, LD->getExtensionType(), OrigLoad.getValueType(),
SDVTList VTs = getVTList(VT, Base.getValueType(), MVT::Other); LD->getChain(), Base, Offset, LD->getSrcValue(),
SDOperand Ops[] = { LD->getChain(), Base, Offset }; LD->getSrcValueOffset(), LD->getMemoryVT(),
FoldingSetNodeID ID; LD->isVolatile(), LD->getAlignment());
AddNodeIDNode(ID, ISD::LOAD, VTs, Ops, 3);
ID.AddInteger(AM);
ID.AddInteger(LD->getExtensionType());
ID.AddInteger((unsigned int)(LD->getMemoryVT()));
ID.AddInteger(LD->getAlignment());
ID.AddInteger(LD->isVolatile());
void *IP = 0;
if (SDNode *E = CSEMap.FindNodeOrInsertPos(ID, IP))
return SDOperand(E, 0);
SDNode *N = new LoadSDNode(Ops, VTs, AM,
LD->getExtensionType(), LD->getMemoryVT(),
LD->getSrcValue(), LD->getSrcValueOffset(),
LD->getAlignment(), LD->isVolatile());
CSEMap.InsertNode(N, IP);
AllNodes.push_back(N);
return SDOperand(N, 0);
} }
SDOperand SelectionDAG::getStore(SDOperand Chain, SDOperand Val, SDOperand SelectionDAG::getStore(SDOperand Chain, SDOperand Val,