mirror of
https://github.com/RPCSX/llvm.git
synced 2025-01-27 07:12:06 +00:00
* Remove instruction fields hasInFlag / hasOutFlag and added SNDPInFlag and
SNDPOutFlag to DAG nodes. These properties do not belong to target specific instructions. * Added DAG node property SNDPOptInFlag. It's same as SNDPInFlag except it's optional. Used by ret / call, etc. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@25154 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
baec98d00b
commit
51fecc80f7
@ -85,8 +85,6 @@ namespace llvm {
|
|||||||
bool usesCustomDAGSchedInserter;
|
bool usesCustomDAGSchedInserter;
|
||||||
bool hasVariableNumberOfOperands;
|
bool hasVariableNumberOfOperands;
|
||||||
bool hasCtrlDep;
|
bool hasCtrlDep;
|
||||||
bool hasInFlag;
|
|
||||||
bool hasOutFlag;
|
|
||||||
bool noResults;
|
bool noResults;
|
||||||
|
|
||||||
CodeGenInstruction(Record *R, const std::string &AsmStr);
|
CodeGenInstruction(Record *R, const std::string &AsmStr);
|
||||||
|
@ -271,8 +271,6 @@ CodeGenInstruction::CodeGenInstruction(Record *R, const std::string &AsmStr)
|
|||||||
hasDelaySlot = R->getValueAsBit("hasDelaySlot");
|
hasDelaySlot = R->getValueAsBit("hasDelaySlot");
|
||||||
usesCustomDAGSchedInserter = R->getValueAsBit("usesCustomDAGSchedInserter");
|
usesCustomDAGSchedInserter = R->getValueAsBit("usesCustomDAGSchedInserter");
|
||||||
hasCtrlDep = R->getValueAsBit("hasCtrlDep");
|
hasCtrlDep = R->getValueAsBit("hasCtrlDep");
|
||||||
hasInFlag = R->getValueAsBit("hasInFlag");
|
|
||||||
hasOutFlag = R->getValueAsBit("hasOutFlag");
|
|
||||||
noResults = R->getValueAsBit("noResults");
|
noResults = R->getValueAsBit("noResults");
|
||||||
hasVariableNumberOfOperands = false;
|
hasVariableNumberOfOperands = false;
|
||||||
|
|
||||||
|
@ -283,6 +283,12 @@ SDNodeInfo::SDNodeInfo(Record *R) : Def(R) {
|
|||||||
Properties |= 1 << SDNPAssociative;
|
Properties |= 1 << SDNPAssociative;
|
||||||
} else if (PropList[i]->getName() == "SDNPHasChain") {
|
} else if (PropList[i]->getName() == "SDNPHasChain") {
|
||||||
Properties |= 1 << SDNPHasChain;
|
Properties |= 1 << SDNPHasChain;
|
||||||
|
} else if (PropList[i]->getName() == "SDNPOutFlag") {
|
||||||
|
Properties |= 1 << SDNPOutFlag;
|
||||||
|
} else if (PropList[i]->getName() == "SDNPInFlag") {
|
||||||
|
Properties |= 1 << SDNPInFlag;
|
||||||
|
} else if (PropList[i]->getName() == "SDNPOptInFlag") {
|
||||||
|
Properties |= 1 << SDNPOptInFlag;
|
||||||
} else {
|
} else {
|
||||||
std::cerr << "Unknown SD Node property '" << PropList[i]->getName()
|
std::cerr << "Unknown SD Node property '" << PropList[i]->getName()
|
||||||
<< "' on node '" << R->getName() << "'!\n";
|
<< "' on node '" << R->getName() << "'!\n";
|
||||||
@ -1779,29 +1785,29 @@ Record *DAGISelEmitter::getSDNodeNamed(const std::string &Name) const {
|
|||||||
return N;
|
return N;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// NodeHasChain - return true if TreePatternNode has the property
|
/// NodeHasProperty - return true if TreePatternNode has the specified
|
||||||
/// 'hasChain', meaning it reads a ctrl-flow chain operand and writes
|
/// property.
|
||||||
/// a chain result.
|
static bool NodeHasProperty(TreePatternNode *N, SDNodeInfo::SDNP Property,
|
||||||
static bool NodeHasChain(TreePatternNode *N, DAGISelEmitter &ISE)
|
DAGISelEmitter &ISE)
|
||||||
{
|
{
|
||||||
if (N->isLeaf()) return false;
|
if (N->isLeaf()) return false;
|
||||||
Record *Operator = N->getOperator();
|
Record *Operator = N->getOperator();
|
||||||
if (!Operator->isSubClassOf("SDNode")) return false;
|
if (!Operator->isSubClassOf("SDNode")) return false;
|
||||||
|
|
||||||
const SDNodeInfo &NodeInfo = ISE.getSDNodeInfo(Operator);
|
const SDNodeInfo &NodeInfo = ISE.getSDNodeInfo(Operator);
|
||||||
return NodeInfo.hasProperty(SDNodeInfo::SDNPHasChain);
|
return NodeInfo.hasProperty(Property);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool PatternHasCtrlDep(TreePatternNode *N, DAGISelEmitter &ISE)
|
static bool PatternHasProperty(TreePatternNode *N, SDNodeInfo::SDNP Property,
|
||||||
|
DAGISelEmitter &ISE)
|
||||||
{
|
{
|
||||||
if (NodeHasChain(N, ISE))
|
if (NodeHasProperty(N, Property, ISE))
|
||||||
return true;
|
return true;
|
||||||
else {
|
|
||||||
for (unsigned i = 0, e = N->getNumChildren(); i != e; ++i) {
|
for (unsigned i = 0, e = N->getNumChildren(); i != e; ++i) {
|
||||||
TreePatternNode *Child = N->getChild(i);
|
TreePatternNode *Child = N->getChild(i);
|
||||||
if (PatternHasCtrlDep(Child, ISE))
|
if (PatternHasProperty(Child, Property, ISE))
|
||||||
return true;
|
return true;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@ -1891,7 +1897,7 @@ public:
|
|||||||
|
|
||||||
// Emit code to load the child nodes and match their contents recursively.
|
// Emit code to load the child nodes and match their contents recursively.
|
||||||
unsigned OpNo = 0;
|
unsigned OpNo = 0;
|
||||||
bool HasChain = NodeHasChain(N, ISE);
|
bool HasChain = NodeHasProperty(N, SDNodeInfo::SDNPHasChain, ISE);
|
||||||
if (HasChain) {
|
if (HasChain) {
|
||||||
OpNo = 1;
|
OpNo = 1;
|
||||||
if (!isRoot) {
|
if (!isRoot) {
|
||||||
@ -1919,7 +1925,7 @@ public:
|
|||||||
OS << " if (" << RootName << OpNo << ".getOpcode() != "
|
OS << " if (" << RootName << OpNo << ".getOpcode() != "
|
||||||
<< CInfo.getEnumName() << ") goto P" << PatternNo << "Fail;\n";
|
<< CInfo.getEnumName() << ") goto P" << PatternNo << "Fail;\n";
|
||||||
EmitMatchCode(Child, RootName + utostr(OpNo), FoundChain);
|
EmitMatchCode(Child, RootName + utostr(OpNo), FoundChain);
|
||||||
if (NodeHasChain(Child, ISE)) {
|
if (NodeHasProperty(Child, SDNodeInfo::SDNPHasChain, ISE)) {
|
||||||
FoldedChains.push_back(std::make_pair(RootName + utostr(OpNo),
|
FoldedChains.push_back(std::make_pair(RootName + utostr(OpNo),
|
||||||
CInfo.getNumResults()));
|
CInfo.getNumResults()));
|
||||||
}
|
}
|
||||||
@ -2078,13 +2084,16 @@ public:
|
|||||||
const DAGInstruction &Inst = ISE.getInstruction(Op);
|
const DAGInstruction &Inst = ISE.getInstruction(Op);
|
||||||
bool HasImpInputs = Inst.getNumImpOperands() > 0;
|
bool HasImpInputs = Inst.getNumImpOperands() > 0;
|
||||||
bool HasImpResults = Inst.getNumImpResults() > 0;
|
bool HasImpResults = Inst.getNumImpResults() > 0;
|
||||||
bool HasInFlag = II.hasInFlag || HasImpInputs;
|
bool HasOptInFlag = isRoot &&
|
||||||
bool HasOutFlag = II.hasOutFlag || HasImpResults;
|
NodeHasProperty(Pattern, SDNodeInfo::SDNPOptInFlag, ISE);
|
||||||
bool HasChain = II.hasCtrlDep;
|
bool HasInFlag = isRoot &&
|
||||||
|
NodeHasProperty(Pattern, SDNodeInfo::SDNPInFlag, ISE);
|
||||||
|
bool HasOutFlag = HasImpResults ||
|
||||||
|
(isRoot && PatternHasProperty(Pattern, SDNodeInfo::SDNPOutFlag, ISE));
|
||||||
|
bool HasChain = II.hasCtrlDep ||
|
||||||
|
(isRoot && PatternHasProperty(Pattern, SDNodeInfo::SDNPHasChain, ISE));
|
||||||
|
|
||||||
if (isRoot && PatternHasCtrlDep(Pattern, ISE))
|
if (HasOutFlag || HasInFlag || HasOptInFlag || HasImpInputs)
|
||||||
HasChain = true;
|
|
||||||
if (HasInFlag || HasOutFlag)
|
|
||||||
OS << " SDOperand InFlag = SDOperand(0, 0);\n";
|
OS << " SDOperand InFlag = SDOperand(0, 0);\n";
|
||||||
|
|
||||||
// Determine operand emission order. Complex pattern first.
|
// Determine operand emission order. Complex pattern first.
|
||||||
@ -2121,8 +2130,16 @@ public:
|
|||||||
// Emit all the chain and CopyToReg stuff.
|
// Emit all the chain and CopyToReg stuff.
|
||||||
if (HasChain)
|
if (HasChain)
|
||||||
OS << " Chain = Select(Chain);\n";
|
OS << " Chain = Select(Chain);\n";
|
||||||
if (HasInFlag)
|
if (HasImpInputs)
|
||||||
EmitInFlags(Pattern, "N", HasChain, II.hasInFlag, true);
|
EmitCopyToRegs(Pattern, "N", HasChain, true);
|
||||||
|
if (HasInFlag || HasOptInFlag) {
|
||||||
|
unsigned FlagNo = (unsigned) HasChain + Pattern->getNumChildren();
|
||||||
|
if (HasOptInFlag)
|
||||||
|
OS << " if (N.getNumOperands() == " << FlagNo+1 << ") ";
|
||||||
|
else
|
||||||
|
OS << " ";
|
||||||
|
OS << "InFlag = Select(N.getOperand(" << FlagNo << "));\n";
|
||||||
|
}
|
||||||
|
|
||||||
unsigned NumResults = Inst.getNumResults();
|
unsigned NumResults = Inst.getNumResults();
|
||||||
unsigned ResNo = TmpNo++;
|
unsigned ResNo = TmpNo++;
|
||||||
@ -2164,7 +2181,7 @@ public:
|
|||||||
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
||||||
OS << ", Tmp" << Ops[i];
|
OS << ", Tmp" << Ops[i];
|
||||||
if (HasChain) OS << ", Chain";
|
if (HasChain) OS << ", Chain";
|
||||||
if (HasInFlag) OS << ", InFlag";
|
if (HasInFlag || HasImpInputs) OS << ", InFlag";
|
||||||
OS << ");\n";
|
OS << ");\n";
|
||||||
|
|
||||||
unsigned ValNo = 0;
|
unsigned ValNo = 0;
|
||||||
@ -2191,8 +2208,10 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
// User does not expect that the instruction produces a chain!
|
// User does not expect that the instruction produces a chain!
|
||||||
bool AddedChain = HasChain && !NodeHasChain(Pattern, ISE);
|
bool NodeHasChain =
|
||||||
if (NodeHasChain(Pattern, ISE))
|
NodeHasProperty(Pattern, SDNodeInfo::SDNPHasChain, ISE);
|
||||||
|
bool AddedChain = HasChain && !NodeHasChain;
|
||||||
|
if (NodeHasChain)
|
||||||
OS << " CodeGenMap[N.getValue(" << ValNo++ << ")] = Chain;\n";
|
OS << " CodeGenMap[N.getValue(" << ValNo++ << ")] = Chain;\n";
|
||||||
|
|
||||||
if (FoldedChains.size() > 0) {
|
if (FoldedChains.size() > 0) {
|
||||||
@ -2230,7 +2249,7 @@ public:
|
|||||||
OS << ", MVT::Flag";
|
OS << ", MVT::Flag";
|
||||||
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
||||||
OS << ", Tmp" << Ops[i];
|
OS << ", Tmp" << Ops[i];
|
||||||
if (HasInFlag)
|
if (HasInFlag || HasImpInputs)
|
||||||
OS << ", InFlag";
|
OS << ", InFlag";
|
||||||
OS << ");\n";
|
OS << ");\n";
|
||||||
OS << " } else {\n";
|
OS << " } else {\n";
|
||||||
@ -2242,7 +2261,7 @@ public:
|
|||||||
OS << ", MVT::Flag";
|
OS << ", MVT::Flag";
|
||||||
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
for (unsigned i = 0, e = Ops.size(); i != e; ++i)
|
||||||
OS << ", Tmp" << Ops[i];
|
OS << ", Tmp" << Ops[i];
|
||||||
if (HasInFlag)
|
if (HasInFlag || HasImpInputs)
|
||||||
OS << ", InFlag";
|
OS << ", InFlag";
|
||||||
OS << ");\n";
|
OS << ");\n";
|
||||||
OS << " }\n";
|
OS << " }\n";
|
||||||
@ -2282,7 +2301,8 @@ public:
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned OpNo = (unsigned) NodeHasChain(Pat, ISE);
|
unsigned OpNo =
|
||||||
|
(unsigned) NodeHasProperty(Pat, SDNodeInfo::SDNPHasChain, ISE);
|
||||||
for (unsigned i = 0, e = Pat->getNumChildren(); i != e; ++i, ++OpNo)
|
for (unsigned i = 0, e = Pat->getNumChildren(); i != e; ++i, ++OpNo)
|
||||||
if (InsertOneTypeCheck(Pat->getChild(i), Other->getChild(i),
|
if (InsertOneTypeCheck(Pat->getChild(i), Other->getChild(i),
|
||||||
Prefix + utostr(OpNo)))
|
Prefix + utostr(OpNo)))
|
||||||
@ -2291,16 +2311,17 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/// EmitInFlags - Emit the flag operands for the DAG that is
|
/// EmitCopyToRegs - Emit the flag operands for the DAG that is
|
||||||
/// being built.
|
/// being built.
|
||||||
void EmitInFlags(TreePatternNode *N, const std::string &RootName,
|
void EmitCopyToRegs(TreePatternNode *N, const std::string &RootName,
|
||||||
bool HasChain, bool HasInFlag, bool isRoot = false) {
|
bool HasChain, bool isRoot = false) {
|
||||||
const CodeGenTarget &T = ISE.getTargetInfo();
|
const CodeGenTarget &T = ISE.getTargetInfo();
|
||||||
unsigned OpNo = (unsigned) NodeHasChain(N, ISE);
|
unsigned OpNo =
|
||||||
|
(unsigned) NodeHasProperty(N, SDNodeInfo::SDNPHasChain, ISE);
|
||||||
for (unsigned i = 0, e = N->getNumChildren(); i != e; ++i, ++OpNo) {
|
for (unsigned i = 0, e = N->getNumChildren(); i != e; ++i, ++OpNo) {
|
||||||
TreePatternNode *Child = N->getChild(i);
|
TreePatternNode *Child = N->getChild(i);
|
||||||
if (!Child->isLeaf()) {
|
if (!Child->isLeaf()) {
|
||||||
EmitInFlags(Child, RootName + utostr(OpNo), HasChain, HasInFlag);
|
EmitCopyToRegs(Child, RootName + utostr(OpNo), HasChain);
|
||||||
} else {
|
} else {
|
||||||
if (DefInit *DI = dynamic_cast<DefInit*>(Child->getLeafValue())) {
|
if (DefInit *DI = dynamic_cast<DefInit*>(Child->getLeafValue())) {
|
||||||
Record *RR = DI->getDef();
|
Record *RR = DI->getDef();
|
||||||
@ -2330,12 +2351,6 @@ private:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isRoot && HasInFlag) {
|
|
||||||
OS << " SDOperand " << RootName << OpNo << " = " << RootName
|
|
||||||
<< ".getOperand(" << OpNo << ");\n";
|
|
||||||
OS << " InFlag = Select(" << RootName << OpNo << ");\n";
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// EmitCopyFromRegs - Emit code to copy result to physical registers
|
/// EmitCopyFromRegs - Emit code to copy result to physical registers
|
||||||
|
@ -102,7 +102,8 @@ namespace llvm {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// SelectionDAG node properties.
|
// SelectionDAG node properties.
|
||||||
enum SDNP { SDNPCommutative, SDNPAssociative, SDNPHasChain };
|
enum SDNP { SDNPCommutative, SDNPAssociative, SDNPHasChain,
|
||||||
|
SDNPOutFlag, SDNPInFlag, SDNPOptInFlag };
|
||||||
|
|
||||||
/// hasProperty - Return true if this node has the specified property.
|
/// hasProperty - Return true if this node has the specified property.
|
||||||
///
|
///
|
||||||
|
Loading…
x
Reference in New Issue
Block a user