mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-12-02 16:36:40 +00:00
Initial support for nested CALLSEQ_START/CALLSEQ_END constructs in LegalizeDAG.
Necessary for byval support on ARM. Radar 7662569. llvm-svn: 121412
This commit is contained in:
parent
fe4b9ee934
commit
f7bba0cfe3
@ -252,8 +252,10 @@ void SelectionDAGLegalize::LegalizeDAG() {
|
||||
|
||||
/// FindCallEndFromCallStart - Given a chained node that is part of a call
|
||||
/// sequence, find the CALLSEQ_END node that terminates the call sequence.
|
||||
static SDNode *FindCallEndFromCallStart(SDNode *Node) {
|
||||
if (Node->getOpcode() == ISD::CALLSEQ_END)
|
||||
static SDNode *FindCallEndFromCallStart(SDNode *Node, int depth = 0) {
|
||||
if (Node->getOpcode() == ISD::CALLSEQ_START)
|
||||
depth++;
|
||||
if ((Node->getOpcode() == ISD::CALLSEQ_END) && (depth == 1))
|
||||
return Node;
|
||||
if (Node->use_empty())
|
||||
return 0; // No CallSeqEnd
|
||||
@ -284,7 +286,7 @@ static SDNode *FindCallEndFromCallStart(SDNode *Node) {
|
||||
SDNode *User = *UI;
|
||||
for (unsigned i = 0, e = User->getNumOperands(); i != e; ++i)
|
||||
if (User->getOperand(i) == TheChain)
|
||||
if (SDNode *Result = FindCallEndFromCallStart(User))
|
||||
if (SDNode *Result = FindCallEndFromCallStart(User, depth))
|
||||
return Result;
|
||||
}
|
||||
return 0;
|
||||
@ -293,12 +295,26 @@ static SDNode *FindCallEndFromCallStart(SDNode *Node) {
|
||||
/// FindCallStartFromCallEnd - Given a chained node that is part of a call
|
||||
/// sequence, find the CALLSEQ_START node that initiates the call sequence.
|
||||
static SDNode *FindCallStartFromCallEnd(SDNode *Node) {
|
||||
int nested = 0;
|
||||
assert(Node && "Didn't find callseq_start for a call??");
|
||||
if (Node->getOpcode() == ISD::CALLSEQ_START) return Node;
|
||||
|
||||
assert(Node->getOperand(0).getValueType() == MVT::Other &&
|
||||
"Node doesn't have a token chain argument!");
|
||||
return FindCallStartFromCallEnd(Node->getOperand(0).getNode());
|
||||
while (Node->getOpcode() != ISD::CALLSEQ_START || nested) {
|
||||
Node = Node->getOperand(0).getNode();
|
||||
assert(Node->getOperand(0).getValueType() == MVT::Other &&
|
||||
"Node doesn't have a token chain argument!");
|
||||
switch (Node->getOpcode()) {
|
||||
default:
|
||||
break;
|
||||
case ISD::CALLSEQ_START:
|
||||
if (!nested)
|
||||
return Node;
|
||||
nested--;
|
||||
break;
|
||||
case ISD::CALLSEQ_END:
|
||||
nested++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/// LegalizeAllNodesNotLeadingTo - Recursively walk the uses of N, looking to
|
||||
|
Loading…
Reference in New Issue
Block a user