changeset 84:c0575f877591

add debug engine
author one
date Sun, 07 Feb 2010 20:55:12 +0900
parents dce00142f374
children d0d8aeaebccf
files src/fdl/test/debug/ConfigurationManager.java src/fdl/test/debug/ConfigurationManagerEngine.java src/fdl/test/debug/ConnectionXMLBuilder.java src/fdl/test/debug/FDLindaNode.java src/fdl/test/debug/MetaProtocolEngine.java src/fdl/test/debug/NodeInfo.java src/fdl/test/debug/Routing.java src/fdl/test/debug/RoutingXMLBuilder.java src/fdl/test/debug/XMLBuilder.java
diffstat 9 files changed, 622 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/ConfigurationManager.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,39 @@
+package fdl.test.debug;
+
+import java.io.IOException;
+
+import fdl.MetaEngine;
+
+/**
+* ConfigurationManager
+*
+* @author Kazuki Akamine
+*
+* FDLindaNode を管理する Server
+*  
+*/
+
+public class ConfigurationManager {
+	private static int nodeNum = 2;
+	private static String usageString
+		= "ConfigurationManager -nodes NODENUM";
+	
+	public static void main(String[] args) {
+		for (int i = 0; i < args.length; i++) {
+			if ("-nodes".equals(args[i])) {
+				nodeNum = Integer.parseInt(args[++i]);
+			} else {
+				System.err.println(usageString);
+			}
+		}
+		try {
+			FDLindaNode manager = new FDLindaNode(FDLindaNode.DEFAULTPORT);
+			MetaEngine me = new ConfigurationManagerEngine(manager.getMetaLinda(), nodeNum);
+			manager.setMetaEngine(me);
+			manager.mainLoop();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/ConfigurationManagerEngine.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,158 @@
+package fdl.test.debug;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+
+import fdl.*;
+
+public class ConfigurationManagerEngine implements MetaEngine {
+	public static final int DEFAULTPORT = 10000;
+
+	// tuple id
+	public static final int MANAGE = 60000;
+	public static final int DEBUG = 61000;
+	
+	public static final int TREETOP = MANAGE + 1;
+	public static final int TREELEFT = MANAGE + 2;
+	public static final int TREERIGHT = MANAGE + 3;
+
+	public static final int RINGLEFT = DEBUG + 1;
+	public static final int RINGRIGHT = DEBUG + 2;
+	
+	private int nodeNum = 0;
+	private MetaLinda ml;
+	private NodeInfo[] nodes;
+	private boolean running = true;
+	
+	private class AcceptNewNode implements PSXCallback {
+		int count = 0;
+		public void callback(ByteBuffer reply) {
+			String[] hostData = new String(reply.array()).split(":");
+			String hostName = hostData[0];
+			int	port = DEFAULTPORT;
+			if (hostData.length > 1)
+				port = new Integer(hostData[1]).intValue();
+			nodes[count] = new NodeInfo(hostName, port);
+			try {
+				nodes[count].linda = ml.open(hostName, port);
+			} catch (IOException e) {
+				e.printStackTrace();
+			}
+			if (++count < nodeNum) {
+				ml.in(MANAGE, this);
+			} else {
+				linkNodes();
+				ml.in(MANAGE, new ConfirmConnectionNode());
+			}
+		}
+	}
+	
+	private class ConfirmConnectionNode implements PSXCallback {
+		int count = 0;
+		public void callback(ByteBuffer reply) {
+			if (++count < nodeNum) {
+				ml.in(MANAGE, this);
+			} else {
+				routingNodes();
+				ml.in(MANAGE, new ConfirmRoutingNode());
+			}
+		}
+
+	}
+
+	private class ConfirmRoutingNode implements PSXCallback {
+		int count = 0;
+		public void callback(ByteBuffer reply) {
+			if (++count < nodeNum) {
+				ml.in(MANAGE, this);
+			} else {
+				print("All link configured!");
+			}
+		}
+
+	}
+	
+	public ConfigurationManagerEngine(MetaLinda metaLinda, int nodeNum) {
+		// initialize
+		this.ml = metaLinda;
+		this.nodeNum = nodeNum;
+		nodes = new NodeInfo[nodeNum];
+	}
+
+	public void mainLoop() {
+		// regist poll tuple id
+		ml.in(MANAGE, new AcceptNewNode());
+		while (running)
+			ml.sync();
+	}
+	
+	private void linkNodes() {
+		for (int i = 0; i < nodes.length; i++) {
+			// XML for Tree Topology
+			ConnectionXMLBuilder tree = new ConnectionXMLBuilder(i);
+			int k;
+			if (i != 0) { // TOP
+				k = (i-1)/2;
+				tree.appendConnection(TREETOP, nodes[k].host, nodes[k].port, (i%2 == 0) ? TREERIGHT : TREELEFT);
+			}
+			if ((k = 2*i+1) < nodes.length) // LEFT
+				tree.appendConnection(TREELEFT, nodes[k].host, nodes[k].port, TREETOP);
+			if ((k = 2*i+2) < nodes.length) // RIGHT
+				tree.appendConnection(TREERIGHT, nodes[k].host, nodes[k].port, TREETOP);
+			nodes[i].connectionXML = tree.createXML();
+			nodes[i].linda.out(MANAGE, ByteBuffer.wrap(nodes[i].connectionXML.getBytes()));
+			print(nodes[i].connectionXML);
+			
+			// XML for Ring Debug Topology
+			ConnectionXMLBuilder debug = new ConnectionXMLBuilder(i);
+			int left = (nodes.length + i - 1) % nodes.length;
+			int right = (i + 1) % nodes.length;
+			debug.appendConnection(RINGLEFT, nodes[left].host, nodes[left].port, RINGRIGHT);
+			debug.appendConnection(RINGRIGHT, nodes[right].host, nodes[right].port, RINGLEFT);
+			nodes[i].debugConnectionXML = debug.createXML();
+			nodes[i].linda.out(DEBUG, ByteBuffer.wrap(nodes[i].debugConnectionXML.getBytes()));
+			print(nodes[i].debugConnectionXML);
+			try {
+				nodes[i].linda.sync(1);
+			} catch (IOException e) {
+				e.printStackTrace();
+			}
+		}
+	}
+	
+	private void routingNodes() {
+		for (int i = 0; i < nodes.length; i++) {
+			RoutingXMLBuilder tree = new RoutingXMLBuilder();
+			if (i != 0) { // TOP
+				if (2*i+1 < nodes.length) { // LEFT
+					tree.appendRoutingTable(TREETOP, TREELEFT);
+					tree.appendRoutingTable(TREELEFT, TREETOP);
+				}
+				if (2*i+2 < nodes.length) { // RIGHT
+					tree.appendRoutingTable(TREETOP, TREERIGHT);
+					tree.appendRoutingTable(TREERIGHT, TREETOP);
+				}
+			}
+			nodes[i].routingXML = tree.createXML();
+			nodes[i].linda.out(MANAGE, ByteBuffer.wrap(nodes[i].routingXML.getBytes()));
+			print(nodes[i].routingXML);
+			
+			RoutingXMLBuilder debug = new RoutingXMLBuilder();
+			debug.appendRoutingTable(RINGLEFT, RINGRIGHT);
+			debug.appendRoutingTable(RINGRIGHT, RINGLEFT);
+			nodes[i].debugRoutingXML = debug.createXML();
+			nodes[i].linda.out(DEBUG, ByteBuffer.wrap(nodes[i].debugRoutingXML.getBytes()));
+			print(nodes[i].debugRoutingXML);
+			try {
+				nodes[i].linda.sync(1);
+			} catch (IOException e) {
+				e.printStackTrace();
+			}
+		}
+	}
+	
+	void print(String str) {
+		System.err.println("[DEBUG] ConfigurationManager: " + str);
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/ConnectionXMLBuilder.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,31 @@
+package fdl.test.debug;
+
+import org.w3c.dom.*;
+
+public class ConnectionXMLBuilder extends XMLBuilder {
+	private Element connections;
+	
+	public ConnectionXMLBuilder(int id) {
+		super();
+		connections = document.createElement("connections");
+		connections.setAttribute("id", new Integer(id).toString());
+		document.appendChild(connections);
+	}
+	
+	public void appendConnection(int mytid, String host, int port, int tid){
+		Element connection = document.createElement("connection");
+		connection.setAttribute("id", new Integer(mytid).toString());
+		Element h = document.createElement("host");
+		h.setTextContent(host);
+		Element p = document.createElement("port");
+		p.setAttribute("id", new Integer(port).toString());
+		Element t = document.createElement("tid");
+		t.setAttribute("id", new Integer(tid).toString());
+
+		connections.appendChild(connection);
+		connection.appendChild(h);
+		connection.appendChild(p);
+		connection.appendChild(t);
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/FDLindaNode.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,75 @@
+package fdl.test.debug;
+
+import java.io.IOException;
+
+import fdl.FDLindaServ;
+import fdl.MetaLinda;
+import fdl.MetaEngine;
+
+/**
+* FDLindaNode
+*
+* @author Kazuki Akamine
+*
+* Federated Linda の Topology Node
+* 接続する機能までを実装 MetaEngine は外部から提供される
+*  
+*/
+
+public class FDLindaNode extends FDLindaServ {
+	// Fields
+	private MetaLinda ml;
+	public static final int DEFAULTPORT = 10000;
+	private static String manager;
+	private final static String usageString
+		= "Usage: FDLindaNode -manager SERVERNAME:PORT";
+
+	// Constructor
+	public FDLindaNode(int port) throws IOException {
+		super(port);
+		this.ml = new MetaLinda(tupleSpace, this);
+	}
+	
+	@Override public void mainLoop() {
+		me.mainLoop();
+	}
+	public void setMetaEngine(MetaEngine me) {
+		this.me = me; 
+	}
+	public MetaLinda getMetaLinda() {
+		return ml;
+	}
+	
+	// main routine
+	public static void main(String[] args) {
+		int port = DEFAULTPORT;
+		for (int i = 0; i < args.length; i++) {
+			if ("-manager".equals(args[i])) {
+				manager = args[++i];
+			} else if ("-p".equals(args[i])) {
+				port = new Integer(args[++i]).intValue();
+			} else {
+				System.err.println(usageString);
+			}
+		}
+		
+		String[] managerData = manager.split(":");
+		String managerHostName = managerData[0];
+		int managerPort;
+		if (managerData.length > 1) {
+			managerPort = new Integer(managerData[1]).intValue();
+		} else {
+			managerPort = DEFAULTPORT; 
+		}
+		
+		try {
+			FDLindaNode node = new FDLindaNode(DEFAULTPORT);
+			MetaEngine me = new MetaProtocolEngine(port, node.getMetaLinda(), managerHostName, managerPort);
+			node.setMetaEngine(me);
+			node.mainLoop();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/MetaProtocolEngine.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,209 @@
+package fdl.test.debug;
+
+import java.io.*;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+
+import java.nio.ByteBuffer;
+import java.util.*;
+
+import javax.xml.parsers.*;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.NodeList;
+import org.xml.sax.SAXException;
+
+import fdl.*;
+
+/**
+* MetaProtocolEngine
+*
+* @author Kazuki Akamine
+* 
+* 接続する機能までを実装した MetaEngine
+* これを継承して、具体的な処理を書く
+*  
+*/
+
+public class MetaProtocolEngine implements MetaEngine {
+	// Fields
+	public static final int DEFAULTPORT = 10000;
+	public static final int MANAGE = 60000;
+	public static final int DEBUG = 61000;
+	
+	private MetaLinda ml;
+	private String localHostName;
+	private int localPort;
+	private PSXLinda manager;
+	private String managerHostName;
+	private int managerPort = DEFAULTPORT;
+	private boolean running = true;
+	private boolean connected = false;
+	private boolean debugConnected = false;
+	private int nodeId;
+	private HashMap<Integer, Routing> nodes, debugNodes;
+	
+	// Callback class
+	class AcceptXMLCallback implements PSXCallback {
+		int tid;
+		
+		private DocumentBuilderFactory dbFactory = null;
+		private DocumentBuilder docBuilder = null;
+		protected Document document;
+		
+		public AcceptXMLCallback(int tid) {
+			this.tid = tid;
+			dbFactory = DocumentBuilderFactory.newInstance();
+			try {
+				docBuilder = dbFactory.newDocumentBuilder();
+			} catch (ParserConfigurationException e) {
+				e.printStackTrace();
+			}
+
+		}
+		public void callback(ByteBuffer reply) {
+			String xml = new String(reply.array());
+			print(xml);
+			parseXML(xml);
+			
+			ml.in(tid, this);
+		}
+		@SuppressWarnings("deprecation")
+		protected void parseXML(String xml) {
+			Document doc = null;
+			try {
+				doc = docBuilder.parse(new StringBufferInputStream(xml));
+			} catch (SAXException e) {
+				e.printStackTrace();
+			} catch (IOException e) {
+				e.printStackTrace();
+			}
+			
+			Element root = doc.getDocumentElement();
+			if(root.getTagName().equals("connections")) {
+				nodeId = new Integer(root.getAttribute("id")).intValue();
+				NodeList connections = root.getElementsByTagName("connection");
+				for (int i = 0; i < connections.getLength(); i++) {
+					Element connection = (Element)connections.item(i);
+					Element host = (Element)connection.getElementsByTagName("host").item(0);
+					Element port = (Element)connection.getElementsByTagName("port").item(0);
+					Element t = (Element)connection.getElementsByTagName("tid").item(0);
+					int srcId = new Integer(connection.getAttribute("id")).intValue();
+					String dstHostName = host.getTextContent();
+					int dstPort = new Integer(port.getAttribute("id")).intValue();
+					int dstId = new Integer(t.getAttribute("id")).intValue();
+					try {
+						PSXLindaImpl linda = (PSXLindaImpl) ml.open(dstHostName, dstPort);
+						Routing r = new Routing(linda, dstId);
+						if (tid == MANAGE)
+							nodes.put(new Integer(srcId), r);
+						else if (tid == DEBUG)
+							debugNodes.put(new Integer(srcId), r);
+						// TODO: implements PSXCallback
+						ml.in(srcId);
+					} catch (IOException e) {
+						e.printStackTrace();
+					}
+				}
+			} else if (root.getTagName().equals("routing")) {
+				print("Routing xml received!");
+				HashMap<Integer, Routing> n;
+				if (tid == MANAGE) {
+					n = nodes;
+				} else if (tid == DEBUG) {
+					n = debugNodes;
+				}
+				NodeList routing = root.getElementsByTagName("source");
+				for (int i = 0; i < routing.getLength(); i++) {
+					Element src = (Element) routing.item(i);
+					int srcId = new Integer(src.getAttribute("id"));
+					NodeList dest = src.getElementsByTagName("dest");
+					for (int j = 0; j < dest.getLength(); i++) {
+						Element dst = (Element) dest.item(i);
+						int dstId = new Integer(dst.getAttribute("id"));
+					}
+					print("");
+				}
+				//n.get(key);
+				
+				
+				
+			}
+			if (tid == MANAGE) connected = true;
+			else if (tid == DEBUG) debugConnected = true;
+			if (connected && debugConnected) {
+				sendLocalHostName();
+				print("Send local host name");
+				connected = debugConnected = false;
+			}
+		}
+		
+	} 
+
+	// Constructor
+	public MetaProtocolEngine(int port, MetaLinda ml, String managerHostName, int managerPort) {
+		this.ml = ml;
+		this.localPort = port;
+		this.managerHostName = managerHostName;
+		this.managerPort = managerPort;
+		this.nodes = new HashMap<Integer, Routing>();
+		this.debugNodes = new HashMap<Integer, Routing>();
+		try {
+			this.localHostName = InetAddress.getLocalHost().getHostName();
+		} catch (UnknownHostException e) {
+			e.printStackTrace();
+		}
+		manager = connectServer(managerHostName, managerPort);
+		sendLocalHostName();
+	}
+
+	public void mainLoop() {
+		initPoller();
+		while (running) {
+			ml.sync();
+		}
+	}
+	
+	protected void initPoller() {
+		ml.in(MANAGE, new AcceptXMLCallback(MANAGE));
+		ml.in(DEBUG, new AcceptXMLCallback(DEBUG));
+		//ml.in(debugId, new ConnectServerCallback(debugId, psxDebugServers, null));
+		//ml.in(registId, new RegistServerCallback());
+	}
+	
+	protected void sendLocalHostName() {
+		// TopologyManager に自分のホストネームを送信して、起動を伝える
+		ByteBuffer local;
+		local = ByteBuffer.wrap((localHostName + ":" + new Integer(localPort).toString()).getBytes());
+		manager.out(MANAGE, local);
+		try {
+			manager.sync(1);
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+	}
+
+	protected PSXLinda connectServer(String hostName, int port) {
+		PSXLinda linda = null;
+		boolean connectPSX = true;
+		while (connectPSX) {
+			try {
+				linda = ml.open(hostName, port);
+				connectPSX = false;
+			} catch (IOException e) {
+				try {
+					Thread.sleep(40);
+				} catch (InterruptedException e1) {
+				}
+			}
+		}
+		print("Connect to " + hostName);
+		return linda;
+	}
+	
+	void print(String str) {
+		System.err.println("[DEBUG] " + localHostName + ": " + str);
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/NodeInfo.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,17 @@
+package fdl.test.debug;
+
+import fdl.PSXLinda;
+
+public class NodeInfo {
+	public String host;
+	public int port;
+	public PSXLinda linda;
+	public String connectionXML, debugConnectionXML;
+	public String routingXML, debugRoutingXML;
+	
+	public NodeInfo(String host, int port) {
+		this.host = host;
+		this.port = port;
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/Routing.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,17 @@
+package fdl.test.debug;
+
+import java.util.LinkedList;
+
+import fdl.*;
+
+public class Routing {
+	PSXLinda linda;
+	int dstId;
+	LinkedList<Integer> route;
+	
+	public Routing(PSXLinda linda, int dstId) {
+		this.linda = linda;
+		this.dstId = dstId;
+		this.route = new LinkedList<Integer>();
+	}
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/RoutingXMLBuilder.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,36 @@
+package fdl.test.debug;
+
+import java.util.*;
+
+import org.w3c.dom.Element;
+
+public class RoutingXMLBuilder extends XMLBuilder {
+	private Element routing;
+	private HashMap<Integer, Element> routingTable;
+	
+	public RoutingXMLBuilder() {
+		super();
+		routing = document.createElement("routing");
+		document.appendChild(routing);
+		routingTable = new HashMap<Integer, Element>();
+	}
+	
+	private Element createRoutingTable(int src) {
+		Integer tupleId = new Integer(src);
+		Element source = document.createElement("source");
+		source.setAttribute("id", tupleId.toString());
+		routing.appendChild(source);
+		routingTable.put(tupleId, source);
+		return source;
+	}
+	
+	public void appendRoutingTable(int src, int dst) {
+		Element source = routingTable.get(new Integer(src));
+		if (source == null)
+			source = createRoutingTable(src);
+		Element dest = document.createElement("dest");
+		dest.setAttribute("id", new Integer(dst).toString());
+		source.appendChild(dest);
+	}
+	
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/fdl/test/debug/XMLBuilder.java	Sun Feb 07 20:55:12 2010 +0900
@@ -0,0 +1,40 @@
+package fdl.test.debug;
+
+import java.io.*;
+import javax.xml.parsers.*;
+import javax.xml.transform.*;
+import javax.xml.transform.dom.DOMSource;
+import javax.xml.transform.stream.StreamResult;
+import org.w3c.dom.*;
+
+public class XMLBuilder {
+	protected Document document;
+	protected Transformer transformer;
+	public XMLBuilder() {
+		DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
+		DocumentBuilder docBuilder = null;
+		try {
+			docBuilder = dbFactory.newDocumentBuilder();
+		} catch (ParserConfigurationException e) {
+			e.printStackTrace();
+		}
+		document = docBuilder.newDocument();
+		TransformerFactory tFactory = TransformerFactory.newInstance();
+		try {
+			transformer = tFactory.newTransformer();
+			transformer.setOutputProperty(OutputKeys.INDENT, "yes");
+		} catch (TransformerConfigurationException e) {
+			e.printStackTrace();
+		}
+	}
+	
+	public String createXML() {
+		StringWriter sw = new StringWriter();
+		try {
+			transformer.transform(new DOMSource(document), new StreamResult(sw));
+		} catch (TransformerException e) {
+			e.printStackTrace();
+		}
+		return sw.toString();
+	}
+}