use of org.jikesrvm.compilers.opt.depgraph.DepGraphNode in project JikesRVM by JikesRVM.
the class MinimalBURS method buildTree.
// //////////////////////////////
// Implementation
// //////////////////////////////
/**
* Build a BURS Tree for each Instruction.
* Complete BURS trees by adding leaf nodes as needed, and
* creating tree edges by calling insertChild1() or insertChild2()
* This step is also where we introduce intermediate tree nodes for
* any LIR instruction that has > 2 "real" operands e.g., a CALL.
*
* @param s The instruction for which a tree must be built
* @return the root of the newly constructed tree
*/
private AbstractBURS_TreeNode buildTree(Instruction s) {
AbstractBURS_TreeNode root = AbstractBURS_TreeNode.create(new DepGraphNode(s));
AbstractBURS_TreeNode cur = root;
for (Enumeration<Operand> uses = s.getUses(); uses.hasMoreElements(); ) {
Operand op = uses.nextElement();
if (op == null)
continue;
// Set child = AbstractBURS_TreeNode for operand op
AbstractBURS_TreeNode child;
if (op instanceof RegisterOperand) {
if (op.asRegister().getRegister().isValidation())
continue;
child = Register;
} else if (op instanceof IntConstantOperand) {
child = new BURS_IntConstantTreeNode(((IntConstantOperand) op).value);
} else if (op instanceof LongConstantOperand) {
child = LongConstant;
} else if (op instanceof AddressConstantOperand) {
child = AddressConstant;
} else if (op instanceof BranchOperand && s.isCall()) {
child = BranchTarget;
} else if (op instanceof InlinedOsrTypeInfoOperand && s.isYieldPoint()) {
child = NullTreeNode;
} else {
continue;
}
// Attach child as child of cur_parent in correct position
if (cur.child1 == null) {
cur.child1 = child;
} else if (cur.child2 == null) {
cur.child2 = child;
} else {
// Create auxiliary node so as to represent
// a instruction with arity > 2 in a binary tree.
AbstractBURS_TreeNode child1 = cur.child2;
AbstractBURS_TreeNode aux = AbstractBURS_TreeNode.create(OTHER_OPERAND_opcode);
cur.child2 = aux;
cur = aux;
cur.child1 = child1;
cur.child2 = child;
}
}
// patch for calls & return
switch(s.getOpcode()) {
case CALL_opcode:
case SYSCALL_opcode:
case YIELDPOINT_OSR_opcode:
if (cur.child2 == null) {
cur.child2 = NullTreeNode;
}
// fall through
case RETURN_opcode:
if (cur.child1 == null) {
cur.child1 = NullTreeNode;
}
}
return root;
}
use of org.jikesrvm.compilers.opt.depgraph.DepGraphNode in project JikesRVM by JikesRVM.
the class NormalBURS method generateTree.
// Generate code for a single tree root.
// Also process inter-tree dependencies from this tree to other trees.
private void generateTree(AbstractBURS_TreeNode k, BURS_StateCoder burs) {
AbstractBURS_TreeNode child1 = k.child1;
AbstractBURS_TreeNode child2 = k.child2;
if (child1 != null) {
if (child2 != null) {
// determine order that minimizes register pressure
if (k.isSuperNodeRoot()) {
byte act = action(k.rule(k.getNonTerminal()));
if ((act & BURS_StateCoder.LEFT_CHILD_FIRST) != 0) {
// rule selected forces order of evaluation
generateTree(child1, burs);
generateTree(child2, burs);
} else if ((act & BURS_StateCoder.RIGHT_CHILD_FIRST) != 0) {
// rule selected forces order of evaluation
generateTree(child2, burs);
generateTree(child1, burs);
} else if (child2.numRegisters() > child1.numRegisters()) {
generateTree(child2, burs);
generateTree(child1, burs);
} else {
generateTree(child1, burs);
generateTree(child2, burs);
}
} else {
if (child2.numRegisters() > child1.numRegisters()) {
generateTree(child2, burs);
generateTree(child1, burs);
} else {
generateTree(child1, burs);
generateTree(child2, burs);
}
}
} else {
generateTree(child1, burs);
}
} else if (child2 != null) {
generateTree(child2, burs);
}
if (k.isSuperNodeRoot()) {
int nonterminal = k.getNonTerminal();
int rule = k.rule(nonterminal);
burs.code(k, nonterminal, rule);
if (DEBUG)
VM.sysWriteln(k + " " + debug(rule));
}
DepGraphNode dgnode = k.dg_node;
if (dgnode != null) {
SpaceEffGraphNode source = dgnode.nextSorted;
for (SpaceEffGraphEdge out = dgnode.firstOutEdge(); out != null; out = out.getNextOut()) {
SpaceEffGraphNode dest = out.toNode().nextSorted;
if (source != dest) {
castNode(dest).decPredecessorCount();
int count = castNode(dest).getPredecessorCount();
if (DEBUG)
VM.sysWriteln(count + ": edge " + source + " to " + dest);
if (count == 0) {
readySetInsert(castNode(dest).getCurrentParent());
}
}
}
}
}
use of org.jikesrvm.compilers.opt.depgraph.DepGraphNode in project JikesRVM by JikesRVM.
the class NormalBURS method buildTrees.
/**
* Stage 1: Complete the expression trees and identify tree roots.
* Complete BURS trees by adding leaf nodes as needed, and
* creating tree edges by calling insertChild1() or insertChild2()
* This step is also where we introduce intermediate tree nodes for
* any LIR instruction that has > 2 "real" operands e.g., a CALL.
* We also mark nodes that must be tree roots.
*
* @param dg The dependence graph.
*/
private void buildTrees(DepGraph dg) {
DepGraphNode bbNodes = (DepGraphNode) dg.firstNode();
for (DepGraphNode n = bbNodes; n != null; n = (DepGraphNode) n.getNext()) {
// Initialize n.treeNode
AbstractBURS_TreeNode cur_parent = AbstractBURS_TreeNode.create(n);
castNode(n).setCurrentParent(cur_parent);
Instruction instr = n.instruction();
// loop for USES of an instruction
for (Enumeration<Operand> uses = instr.getUses(); uses.hasMoreElements(); ) {
// Create tree edge for next use.
Operand op = uses.nextElement();
if (op == null)
continue;
// Set child = AbstractBURS_TreeNode for operand op
AbstractBURS_TreeNode child;
if (op instanceof RegisterOperand) {
RegisterOperand regOp = (RegisterOperand) op;
// ignore validation registers
if (regOp.getRegister().isValidation())
continue;
DepGraphEdge e = DepGraphEdge.findInputEdge(n, op);
if (e == null) {
// operand is leaf
child = Register;
} else {
child = castNode(e.fromNode()).getCurrentParent();
}
} else if (op instanceof IntConstantOperand) {
child = new BURS_IntConstantTreeNode(((IntConstantOperand) op).value);
} else if (op instanceof LongConstantOperand) {
child = LongConstant;
} else if (op instanceof AddressConstantOperand) {
child = AddressConstant;
} else if (op instanceof BranchOperand && instr.isCall()) {
child = BranchTarget;
} else if (op instanceof InlinedOsrTypeInfoOperand && instr.isYieldPoint()) {
child = NullTreeNode;
} else {
continue;
}
// Attach child as child of cur_parent in correct position
if (cur_parent.getChild1() == null) {
cur_parent.setChild1(child);
} else if (cur_parent.getChild2() == null) {
cur_parent.setChild2(child);
} else {
// Create auxiliary node so as to represent
// a instruction with arity > 2 in a binary tree.
AbstractBURS_TreeNode child1 = cur_parent.getChild2();
AbstractBURS_TreeNode aux = AbstractBURS_TreeNode.create(OTHER_OPERAND_opcode);
cur_parent.setChild2(aux);
cur_parent = aux;
cur_parent.setChild1(child1);
cur_parent.setChild2(child);
}
}
// patch for calls & return
switch(instr.getOpcode()) {
case CALL_opcode:
case SYSCALL_opcode:
case YIELDPOINT_OSR_opcode:
if (cur_parent.getChild2() == null) {
cur_parent.setChild2(NullTreeNode);
}
// fall through
case RETURN_opcode:
if (cur_parent.getChild1() == null) {
cur_parent.setChild1(NullTreeNode);
}
}
if (mustBeTreeRoot(n)) {
makeTreeRoot(castNode(n).getCurrentParent());
}
}
}
Aggregations