changeset 151:1768e68ba98e

*** empty log message ***
author pin
date Tue, 05 Aug 2008 15:09:39 +0900
parents e33871f4b39a
children 09ad66f62f4a
files bin/remoteeditor/network/REP.class src/pathfinder/mergetest/EditorSimulatorWithoutMerger.java src/pathfinder/mergetest/SelectionKeySimulator.java src/pathfinder/mergetest/SelectorSimulator.java src/pathfinder/mergetest/SessionManagerSimulatorWithMerger.java src/remoteeditor/network/REP.java
diffstat 6 files changed, 210 insertions(+), 152 deletions(-) [+]
line wrap: on
line diff
Binary file bin/remoteeditor/network/REP.class has changed
--- a/src/pathfinder/mergetest/EditorSimulatorWithoutMerger.java	Mon Aug 04 20:34:09 2008 +0900
+++ b/src/pathfinder/mergetest/EditorSimulatorWithoutMerger.java	Tue Aug 05 15:09:39 2008 +0900
@@ -23,20 +23,20 @@
 				/* received Command */
 
 				ns.writeLog("\tEditor"+eid+" catch command from "+cmd.eid+" NO."+cmd.seq, 3);
-				//if (cmd.eid != -2 && eid == 0) ns.writeLog("\tEditor"+eid+" catch command from "+cmd.eid+" :"+cmd, 1);
+				//if (eid == 3) ns.writeLog("\tEditor"+eid+" catch command from "+cmd.eid+" :"+cmd, 1);
 
 				//System.out.println(eid + ":" + cmd.eid);
 
 				if (cmd.eid==eid){
 
-					text.edit(cmd);
+					//text.edit(cmd);
 					cs.write(new REPCommand(cmd));
 					
 					/* 終了条件  */
-					if (cmd.cmd==REP.SMCMD_QUIT){
-						ns.writeLog("\tEditor"+eid+" catch QUIT command emited by itself.", 3);
-						running=false; break;
-					}
+//					if (cmd.cmd==REP.SMCMD_QUIT){
+//						ns.writeLog("\tEditor"+eid+" catch QUIT command emited by itself.", 3);
+//						running=false; break;
+//					}
 				} else if (cmd.eid==-1){
 					/* 制御プロセスからの指令  */
 					ns.writeLog("\tEditor"+eid+" send command.", 2);
@@ -48,6 +48,14 @@
 				}else if(cmd.eid == -2){
 					// Merged Commands.
 					text.edit(cmd);
+					
+					/* 終了条件  */
+					if (cmd.cmd==REP.SMCMD_QUIT){
+						ns.writeLog("\tEditor"+eid+" catch QUIT command emited by itself.", 3);
+						running=false; break;
+					}else{
+						cs.write(new REPCommand(cmd));
+					}
 				} else {
 
 					ns.writeLog("\t\tEditor"+eid+" edit text and pass Cmd. " + " : " + cmd, 3);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/pathfinder/mergetest/SelectionKeySimulator.java	Tue Aug 05 15:09:39 2008 +0900
@@ -0,0 +1,28 @@
+package pathfinder.mergetest;
+
+public class SelectionKeySimulator<P> {
+
+	public static final int OP_READ = 0;
+	private ChannelSimulator<P> channel;
+
+	public SelectionKeySimulator(ChannelSimulator<P> cs) {
+		// TODO Auto-generated constructor stub
+		channel = cs;
+	}
+
+	public boolean isAcceptable() {
+		// TODO Auto-generated method stub
+		return false;
+	}
+
+	public boolean isReadable() {
+		// TODO Auto-generated method stub
+		return true;
+	}
+
+	public ChannelSimulator<P> channel() {
+		// TODO Auto-generated method stub
+		return channel;
+	}
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/pathfinder/mergetest/SelectorSimulator.java	Tue Aug 05 15:09:39 2008 +0900
@@ -0,0 +1,56 @@
+package pathfinder.mergetest;
+
+import java.util.ArrayList;
+import java.util.Set;
+
+public class SelectorSimulator<P> {
+	
+	private ArrayList<SelectionKeySimulator<P>> keyList;
+	private NetworkSimulator<P> ns;
+	private ArrayList<SelectionKeySimulator<P>> selectedKeys;
+	
+	public SelectorSimulator(NetworkSimulator<P> _ns) {
+		// TODO Auto-generated constructor stub
+		ns = _ns;
+		keyList = new ArrayList<SelectionKeySimulator<P>>();
+	}
+
+	public int select(){
+		selectedKeys = new ArrayList<SelectionKeySimulator<P>>();
+		
+		synchronized(ns){
+			boolean empty = false;
+			for(SelectionKeySimulator<P> key : keyList){
+				ChannelSimulator<P> channel = key.channel();
+				if(channel.readQisEmpty()){
+					empty = true;
+				}else{
+					empty = false;
+					//selectedKeys = key;
+					selectedKeys.add(key);
+					break;
+				}
+			}
+			
+			try {
+				if(empty) ns.wait();
+			} catch (InterruptedException e) {
+				// TODO Auto-generated catch block
+				e.printStackTrace();
+			}
+		}
+		return selectedKeys.size();
+	}
+	
+	public SelectionKeySimulator<P> register(ChannelSimulator<P> cs){
+		SelectionKeySimulator<P> key = new SelectionKeySimulator<P>(cs);
+		keyList.add(new SelectionKeySimulator<P>(cs));
+		return key;
+	}
+
+	public ArrayList<SelectionKeySimulator<P>> selectedKeys() {
+		
+		return selectedKeys;
+	}
+
+}
--- a/src/pathfinder/mergetest/SessionManagerSimulatorWithMerger.java	Mon Aug 04 20:34:09 2008 +0900
+++ b/src/pathfinder/mergetest/SessionManagerSimulatorWithMerger.java	Tue Aug 05 15:09:39 2008 +0900
@@ -1,11 +1,7 @@
 package pathfinder.mergetest;
 
 import java.util.ArrayList;
-import java.util.LinkedList;
 import java.util.List;
-import java.util.Stack;
-import java.util.concurrent.BlockingQueue;
-
 import remoteeditor.command.REPCommand;
 import remoteeditor.network.REP;
 import sample.merge.TranslaterImp1;
@@ -15,6 +11,9 @@
 	private List<TranslaterImp1> editorList;
 	private List<ArrayList<REPCommand>> mergedList;
 	//private List<LinkedList<REPCommand>> editorList2;
+	private SelectorSimulator<P> selector;
+	private List<ArrayList<REPCommand>> sentList;
+	private REPCommand quitCommand;
 
 	public SessionManagerSimulatorWithMerger(NetworkSimulator<P> _ns) {
 		super(_ns);
@@ -28,7 +27,9 @@
 		super(_ns, max_client, max_packet);
 		editorList = new ArrayList<TranslaterImp1>();
 		mergedList = new ArrayList<ArrayList<REPCommand>>();
-		//editorList2 = new ArrayList<LinkedList<REPCommand>>();
+		sentList = new ArrayList<ArrayList<REPCommand>>();
+		selector = new SelectorSimulator<P>(_ns);
+		//quitCommand = new REPCommand();
 	}
 	
 	protected void checkAccept(){
@@ -37,175 +38,137 @@
 			csList.add(cs);
 			editorList.add(new TranslaterImp1(editorList.size()));
 			mergedList.add(new ArrayList<REPCommand>());
-			//editorList2.add(new LinkedList<REPCommand>());
-			//System.out.println(csList.size() + " : " + editorList.size() + " : " + mergedList.size());
+			sentList.add(new ArrayList<REPCommand>());
+			registerChannel (selector, cs, SelectionKeySimulator.OP_READ);
 		}
 	}
 	
-	public void run(){
+	private void registerChannel(SelectorSimulator selector2, ChannelSimulator<P> cs, int key) {
+		selector.register(cs);
+	}
 
-		//int i=0;
-		int count=0;
-		P packet = null;
-		//REPCommand[] cmds;
+	public void run(){
 
 		ns.writeLog("SessionManager start.", 1);
 
 		/* Main Loop */
-		ChannelSimulator<P> cs = null; // = csList.get(i);
 		
-		try {
-			Thread.sleep(4000);
-		} catch (InterruptedException e1) {
-			e1.printStackTrace();
+		//Selectorを用いた実装
+		//while(running && (MAX_PACKET==0 || count<MAX_PACKET)){
+		while(running){
+			// Main Loop
+			selector.select();
+			for(SelectionKeySimulator<P> key : selector.selectedKeys()){
+				
+				if(key.isAcceptable()){
+					ChannelSimulator<P> channel = key.channel();
+					selector.register(channel);
+					channel = null;
+					
+				}else if(key.isReadable()){
+					ChannelSimulator<P> channel = key.channel();
+					P packet = channel.read();
+					REPCommand command = unpack(packet);
+					
+					manage(channel, command);
+				}
+			}
 		}
 		
-		while(running && (MAX_PACKET==0 || count<MAX_PACKET)){
+		ns.writeLog("SessionManager finish.", 1);
+	}
 
-			int eid = 0;
-			// should be move to NetworkSimulator.  ns.select(csList); 
-			boolean result = true;
-			synchronized(ns){
+	private void manage(ChannelSimulator<P> channel, REPCommand command) {
+		// コマンドの処理
+		int eid = csList.indexOf(channel);
+		int neid = (eid+1)%csList.size();
+		ChannelSimulator<P> nextChannel = csList.get(neid);
+		REPCommand[] cmds;
+		
+		translate(eid, neid, command);
+
+	}
 
-				for(int i = 0; i < csList.size(); i++){
-					cs = csList.get(i);
-					if((packet=cs.poll())!=null) {
-						ns.writeLog("SeMa pass packet to "+i+":>> "+packet.toString(), 3);
-						eid = i;
-						break;
+	private void translate(int eid, int neid, REPCommand command) {
+		// TODO Auto-generated method stub
+		ChannelSimulator<P> channel = csList.get(eid);
+		ChannelSimulator<P> nextChannel = csList.get(neid);
+		if(command.eid == eid){
+			if(checkOwnCommand(command)){
+				//エディタからの編集コマンドが他の全てのエディタを通って戻ってきた場合
+				if(command.cmd == REP.SMCMD_QUIT){
+					//QUITコマンドの場合
+					REPCommand tmp = new REPCommand(command);
+					tmp.eid = -2;
+					quitCommand = tmp;
+					//channel.write(pack(tmp));
+				}else{
+					//エディタからの編集コマンドが戻ってきた場合、マージしてエディタへ反映
+					REPCommand[] cmds = editorList.get(eid).catchOwnCommand(command);
+					for(REPCommand cmd : cmds){
+						REPCommand tmp2 = new REPCommand(cmd);
+						tmp2.eid = -2;
+						mergedList.get(eid).add(cmd);		//マージして送信したコマンドを覚えておくためのリスト
+						channel.write(pack(tmp2));
 					}
 				}
 				
-				if(cs == null) {
-					try { ns.wait(); } catch (InterruptedException e) { e.printStackTrace(); }
-					//continue;
-					result = false;
+			}else{
+				if(command.cmd == REP.SMCMD_QUIT){
+					//エディタからのQUITコマンド
+					sentList.get(eid).add(command);
+					nextChannel.write(pack(command));
+				}else{
+					//エディタからの新たな編集コマンド
+					if(mergedList.get(eid).size() > 0){
+						//マージの際にユーザから割り込みがあった場合
+					}
+					sentList.get(eid).add(command);
+					editorList.get(eid).transSendCmd(command);
+					nextChannel.write(pack(command));
 				}
-				if(packet == null) result = false;
 			}
-			if(!result) continue;
-			if(!running) break;
-			
-			int neid = (eid+1)%csList.size();
-
-			REPCommand[] cmds3 = receivePacket(eid, packet);
-			if(cmds3 != null) sendPacket(neid, cmds3);
-
-			
-/*			// Merge
-			REPCommand command = unpack(packet);
-			REPCommand[] cmds;
-			
-			//int neid = (eid+1)%csList.size();
-			cs = csList.get(neid);
-			
-			if(neid == command.eid){
-				
-				// コマンドが一周して戻ってきた場合
-				cmds = editorList.get(neid).catchOwnCommand(command);
-				for (int j=0; j<cmds.length; j++){
-					P tmp = (P)cmds[j];
-					P tmp2 = (P) new REPCommand(tmp);
-					tmp2.eid = -2;
-					
-					if ( !cs.write(tmp2) ){
-						ns.writeLog("Session Manager failed to write.", 0);
-					}
+		}else if(command.eid == -2){
+			//マージを行っている間にエディタからの割り込みがなかったか確認
+			mergedList.get(eid).remove(0);
+			if(mergedList.get(eid).size() == 0){
+				channel.write(pack(quitCommand));
+			}
+		}else{
+			if(command.cmd == REP.SMCMD_QUIT){
+				//QUITコマンドはマージャへ追加せずそのまま次のエディタへ送信する
+				nextChannel.write(pack(command));
+			}else{
+				//他のエディタからのコマンドはマージャへ追加しを次のエディタへ送信する
+				REPCommand[] cmds = editorList.get(eid).transReceiveCmd(command);
+				for(REPCommand cmd : cmds){
+					nextChannel.write(pack(cmd));
 				}
-				if (command.cmd==REP.SMCMD_QUIT){
-					if ( !cs.write(packet) ){
-						ns.writeLog("Session Manager failed to write.", 0);
-					}
-				}
-			}else if(eid == command.eid){
-				//editorからの最初のコマンド
-				cmds = editorList.get(eid).transSendCmd(command);
-
-				REPCommand[] cmds2 = editorList.get(neid).transReceiveCmd(command);
-				for (int j=0; j<cmds2.length; j++){
-					cs.write((P) new REPCommand(cmds2[j]));
-				}
-
-			
-			}else{
-				//それ以外の場合は隣のエディタにコマンドを転送
-
-				cmds = editorList.get(neid).transReceiveCmd(command);
-				for (int j=0; j<cmds.length; j++){
-					REPCommand cmd = cmds[j];
-					if ( !cs.write((P) new REPCommand(cmd)) ){
-						ns.writeLog("Session Manager failed to write.", 0);
-					}
-				}
-
-			}*/
-			count++;
+			}
 		}
-		ns.writeLog("SessionManager finish.", 1);
 	}
 
-	private void sendPacket(int neid, REPCommand[] cmds) {
-		ChannelSimulator<P> cs = csList.get(neid);
-		REPCommand[] cmds2;
-		
-		//QUITコマンドの場合はマージせずにそのまま送信
-		if(cmds[0].eid == neid && cmds[0].cmd == REP.SMCMD_QUIT){
-			cs.write((P) new REPCommand(cmds[0]));
-			return;
+	private boolean checkOwnCommand(REPCommand command) {
+		// TODO Auto-generated method stub
+		boolean ownCommand = false;
+		if(sentList.get(command.eid).size() > 0){
+			if(sentList.get(command.eid).get(0).seq == command.seq){
+				ownCommand = true;
+				sentList.get(command.eid).remove(0);
+			}
 		}
-		
-		//コマンドを次のエディタに送信
-		for(REPCommand command : cmds){
-			cs.write((P) new REPCommand(command));
-		}
-		
+		return ownCommand;
 	}
 
-	private REPCommand[] receivePacket(int eid, P packet) {
-		REPCommand command;
-		command = unpack(packet);
-		REPCommand[] cmds;
-		
-		
-		ArrayList<REPCommand> list = mergedList.get(eid);
-		if(list.size() > 0){
-			REPCommand command2 = list.get(0);
-			if(command2.eid == command.eid && command2.seq == command.seq){
-				//マージしてエディタへ送信したコマンドが戻ってきた場合
-				list.remove(0);
-				if(eid == 0) System.out.println(list.size());
-				return null;
-			}
-		}
-		
-		
-		//QUITコマンドの場合はマージャに追加せずそのまま次のエディタへ送信
-		if(command.cmd == REP.SMCMD_QUIT){
-			return new REPCommand[]{command};
-		}
-		
-		if(command.eid == eid) {
-			LinkedList<REPCommand> sentCmds = editorList.get(eid).getSentCmds();
-			for(REPCommand sentCommand : sentCmds){
-				if(sentCommand.seq == command.seq){
-					return editorList.get(eid).catchOwnCommand(command);
-				}
-			}
-			//ユーザからの新しい編集コマンド
-			//エディタからの編集コマンドをマージのリストに追加
-			cmds = editorList.get(eid).transSendCmd(command);
-		}else{
-			//他のエディタから転送されてきた編集コマンド
-			cmds = editorList.get(eid).transReceiveCmd(command);
-		}
-		return cmds;
+	private P pack(REPCommand command) {
+		P cmd = (P) new REPCommand(command);
+		return cmd;
 	}
 
 	private REPCommand unpack(P packet) {
 		REPCommand cmd = null;
 		if(packet instanceof REPCommand){
 			cmd = (REPCommand) packet;
-			//ns.writeLog("Error!! :Packet type is NOT REPCommand!", 1);
 		}else{
 			ns.writeLog("Error!! :Packet type is NOT REPCommand!", 1);
 		}
--- a/src/remoteeditor/network/REP.java	Mon Aug 04 20:34:09 2008 +0900
+++ b/src/remoteeditor/network/REP.java	Tue Aug 05 15:09:39 2008 +0900
@@ -37,8 +37,11 @@
 	public static final int SMCMD_GET_UNDO = 71;
 	public static final int SMCMD_GET_UNDO_ACK = 72;
 	
-    public static final int REPCMD_INSERT_UNDO	= 106;
-    public static final int REPCMD_DELETE_UNDO	= 109;
-    public static final int REPCMD_REPLACE_UNDO	= 113;
+	public static final int SMCMD_START_MERGE = 73;
+	public static final int SMCMD_START_MERGE_ACK = 74;
+	
+//    public static final int REPCMD_INSERT_UNDO	= 106;
+//    public static final int REPCMD_DELETE_UNDO	= 109;
+//    public static final int REPCMD_REPLACE_UNDO	= 113;
 
 }