1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-11-24 11:42:57 +01:00

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.

llvm-svn: 48894
This commit is contained in:
Duncan Sands 2008-03-27 20:23:40 +00:00
parent 199ab29337
commit 3d613421f1
4 changed files with 73 additions and 82 deletions

View File

@ -379,6 +379,11 @@ public:
unsigned Alignment=0);
SDOperand getIndexedLoad(SDOperand OrigLoad, SDOperand Base,
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.
///

View File

@ -310,6 +310,7 @@ private:
SDOperand FloatToIntRes_BIT_CONVERT(SDNode *N);
SDOperand FloatToIntRes_BUILD_PAIR(SDNode *N);
SDOperand FloatToIntRes_FCOPYSIGN(SDNode *N);
SDOperand FloatToIntRes_LOAD(SDNode *N);
// Operand Float to Integer Conversion.
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::BUILD_PAIR: R = FloatToIntRes_BUILD_PAIR(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.
@ -111,6 +112,16 @@ SDOperand DAGTypeLegalizer::FloatToIntRes_FCOPYSIGN(SDNode *N) {
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..

View File

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