All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.dragome.compiler.graph.Node Maven / Gradle / Ivy

There is a newer version: 0.96-beta4
Show newest version
/*
 * Copyright 2005 by Wolfgang Kuehn
 * Created on 12.11.2005
 */
package com.dragome.compiler.graph;

import java.util.Collection;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.Set;

import com.dragome.compiler.ast.ASTNodeStack;
import com.dragome.compiler.ast.Block;
import com.dragome.compiler.ast.Expression;
import com.dragome.compiler.ast.IfStatement;
import com.dragome.compiler.graph.transformation.Transformation;

public class Node
{

	public class Reference
	{
		public Node source;

		public boolean isBackward= false;
	}

	public static int NON_HEADER= 0;

	public static int REDUCIBLE= 1;

	public static int IRREDUCIBLE= 2;

	String id;

	Set inEdges= new LinkedHashSet();

	Set outEdges= new LinkedHashSet();

	Graph graph;

	private int currentPc= -1;

	private int initialPc= -1;

	public ASTNodeStack stack= new ASTNodeStack();

	public Block block= new Block();

	public boolean closed= false;

	protected int preOrderIndex= -1;

	private Node domParent;

	private Set domChildren= new LinkedHashSet();

	IfStatement ifStmt;

	public Expression switchExpression;

	public Transformation trans;

	public Collection jsrCallers= new LinkedHashSet();

	public boolean isSwitchHeader= false;

	public Node(Graph theGraph, int pc)
	{
		this(theGraph);
		setInitialPc(pc);
	}

	public Node(Graph theGraph)
	{
		graph= theGraph;
	}

	public int getComplexity()
	{
		Node node= this;
		int complexity= 0;
		while (node.trans != null)
		{
			complexity++;
			node= node.trans.header;
		}
		return complexity;
	}

	public int getCurrentPc()
	{
		return currentPc;
	}

	public void setCurrentPc(int pc)
	{
		currentPc= pc;
	}

	public void close()
	{
		closed= true;
	}

	public void addEdge(Edge e)
	{
		if (e.source == this)
		{
			if (!outEdges.add(e))
			{
				throw new RuntimeException("\n" + this + "\nalready bound to " + e);
			}
		}

		if (e.target == this)
		{
			if (!inEdges.add(e))
			{
				throw new RuntimeException("" + this + " already bound to " + e);
			}
		}
	}

	public String toString()
	{
		String s= getClass().getName();

		s= s.replaceFirst(".*\\.", "");

		s+= " " + id + "[" + initialPc + ", " + currentPc + "]";

		if (domParent != null)
			s+= " dominated by " + domParent.id;
		if (isLoopHeader())
			s+= " LH";
		return s;
	}

	public String describe()
	{
		String s= toString();
		Iterator iter= outEdges.iterator();
		while (iter.hasNext())
		{
			Edge e= (Edge) iter.next();
			s+= "\n\t" + e;
		}
		return s;
	}

	public Set getInEdges()
	{
		return inEdges;
	}

	public Edge getSelfEdge()
	{
		Iterator iterator= inEdges.iterator();
		while (iterator.hasNext())
		{
			Edge edge= (Edge) iterator.next();
			if (edge.source == this)
				return edge;
		}
		return null;
	}

	public Set getOutEdges()
	{
		return outEdges;
	}

	public Edge[] getOutEdgesArray()
	{
		return outEdges.toArray(new Edge[outEdges.size()]);
	}

	public Edge[] getInEdgesArray()
	{
		return inEdges.toArray(new Edge[inEdges.size()]);
	}

	public int getPreOrderIndex()
	{
		return preOrderIndex;
	}

	public void setPreOrderIndex(int thePreOrderIndex)
	{
		preOrderIndex= thePreOrderIndex;
	}

	public Set succs()
	{
		Set list= new LinkedHashSet();
		Edge[] edges= getOutEdgesArray();
		for (int i= edges.length - 1; i >= 0; i--)
		{
			list.add(edges[i].target);
		}
		return list;
	}

	public Set preds()
	{
		Set list= new LinkedHashSet();
		Iterator iter= inEdges.iterator();
		while (iter.hasNext())
		{
			Edge e= (Edge) iter.next();
			list.add(e.source);
		}
		return list;
	}

	public Node getPred()
	{
		int count= inEdges.size();
		if (count != 1)
			throw new RuntimeException("Requested unique predecessor, found " + count);
		return inEdges.iterator().next().source;
	}

	public Node getSucc()
	{
		return getOutEdge().target;
	}

	public Edge getLocalOutEdgeOrNull()
	{
		Edge outEdge= null;
		Iterator iter= outEdges.iterator();
		while (iter.hasNext())
		{
			Edge edge= (Edge) iter.next();
			if (outEdge != null)
				new RuntimeException("Found multiple local out-edges");
			outEdge= edge;
		}
		return outEdge;
	}

	public Edge getOutEdge()
	{
		int count= outEdges.size();
		if (count != 1)
			throw new RuntimeException("Requested unique successor, found " + count);
		return outEdges.iterator().next();
	}

	public boolean isDomAncestor(Node node)
	{
		do
		{
			if (node == null)
				return false;
			if (node == this)
				return true;
			node= node.getDomParent();
		}
		while (true);
	}

	public Set getDomChildren()
	{
		return domChildren;
	}

	public Node getDomChild()
	{
		if (domChildren.size() != 1)
			throw new RuntimeException("Node must have single child");
		return getDomChildren().iterator().next();
	}

	public Node getDomParent()
	{
		return domParent;
	}

	public void setDomParent(Node newDomParent)
	{

		if (domParent != null)
		{
			domParent.domChildren.remove(this);
		}

		domParent= newDomParent;

		// Add this Block to its new dominator's children.
		if (domParent != null)
		{
			domParent.domChildren.add(this);
		}
	}

	public boolean isBranch()
	{
		Edge[] edges= getOutEdgesArray();
		if (edges.length != 2)
			return false;
		if (edges[0] instanceof ConditionalEdge && edges[1] instanceof ConditionalEdge)
			return true;
		if ((edges[0] instanceof ConditionalEdge) || (edges[1] instanceof ConditionalEdge))
			throw new RuntimeException("Node must not have mixed edges");
		return false;
	}

	public ConditionalEdge getConditionalEdge(boolean trueFalse)
	{
		if (!isBranch())
			throw new RuntimeException("Node must be a branch");
		Iterator iter= outEdges.iterator();
		Edge edge= iter.next();
		if (!trueFalse)
			edge= iter.next();
		return (ConditionalEdge) edge;
	}

	public String getId()
	{
		return id;
	}

	public int getInitialPc()
	{
		return initialPc;
	}

	public Graph getGraph()
	{
		return graph;
	}

	public void setInitialPc(int theInitialPc)
	{
		initialPc= theInitialPc;
		currentPc= theInitialPc;
	}

	public boolean isLoopHeader()
	{
		Iterator iter= inEdges.iterator();
		while (iter.hasNext())
		{
			Edge edge= (Edge) iter.next();
			if (edge.isBackEdge())
				return true;
		}
		return false;
	}

	public boolean hasSelfEdges()
	{
		Iterator iter= outEdges.iterator();
		while (iter.hasNext())
		{
			Edge edge= (Edge) iter.next();
			if (edge.target == this)
				return true;
		}
		return false;
	}

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy