/* * Vorlesung "Vernetzte Systeme" WS 1999/2000, Prof. Dr. F. Mattern * ---------------------------------------------------------------- * Pipe.java: * Simulate a lossy, non-FIFO connection over a socket. * * Required Classes: * - PipeLineThread: * simulate lost/corrupted and delayed packages in one direction (either * up- or downstream) */ import java.net.*; import java.io.*; public class Pipe { private static double BER = 3.5; // BitErrorRate: 10-(3.5) // (error every 395 byte) private static int minDelay = 100; // in milliseconds(ms) private static int maxDelay = 1000; // in milliseconds(ms) private static boolean debug = false; private static void parseArgs (String[] args) { try { if (args.length > 0) BER = Double.valueOf(args[0]).doubleValue(); // in Java 1.2 we can do // BER = Double.parseDouble(args[0]); if (args.length > 1) minDelay = Integer.parseInt(args[1]); if (args.length > 2) maxDelay = Integer.parseInt(args[2]); if (args.length > 3) debug = true; } catch (NumberFormatException e) { System.err.println("Usage: java Pipe "+ " [debug]"); System.err.println(" : Negative Log. of BitErrorRate " + "(i.e. 10^-i). Default is " + BER); System.err.println(" : best case delay (in ms). Default " + "is " + minDelay); System.err.println(" : worst case delay (in ms). Default" + " is " + maxDelay); System.exit(-1); } } private static void showSettings() { System.err.println ("Pipe initialized:"); System.err.println (" Bit Error Rate (BER): 10^(-" + BER +")"); System.err.println (" Delay of connection (in ms): " + minDelay+ " <= delay <= " + maxDelay); System.err.println ("\nWaiting for connections..."); } public static void main(String[] args) throws Exception { parseArgs(args); /* Get forwarding info from args */ int forwardPort = 5555; /* for now let's use a fixed address */ String forwardHost = "localhost"; showSettings(); /* Open all IO-Sockets */ ServerSocket serverSocket = null; try { serverSocket = new ServerSocket(4444); } catch (IOException e) { System.err.println("Could not listen on port: 4444."); System.exit(-1); } Socket clientSocket = null; try { clientSocket = serverSocket.accept(); } catch (IOException e) { System.err.println("Accept failed."); System.exit(1); } Socket forwardSocket = null; try { forwardSocket = new Socket(forwardHost, forwardPort); } catch (IOException e) { System.err.println("Opening Forwarding Address failed."); System.exit(1); } /* Open all IO-Streams */ // Upstream (from Client through Pipe to Server) BufferedReader inUpstream = new BufferedReader(new InputStreamReader( clientSocket.getInputStream())); SyncPrintWriter outUpstream = new SyncPrintWriter(forwardSocket.getOutputStream(), true); // Downstream (from Server through Pipe to Client) BufferedReader inDownstream = new BufferedReader(new InputStreamReader( forwardSocket.getInputStream())); SyncPrintWriter outDownstream = new SyncPrintWriter(clientSocket.getOutputStream(), true); /* Start two threads for Up- and Downstream Pipelining */ PipeLineThread up = new PipeLineThread("Upstream", inUpstream, outUpstream, BER, minDelay, maxDelay, true, debug); PipeLineThread dn = new PipeLineThread("Dnstream", inDownstream, outDownstream, BER, minDelay, maxDelay, false, debug); up.start(); dn.start(); while (up.isAlive() && dn.isAlive()) {} if (up.isAlive()) { /* terminate upstream */ System.out.println("Pipe: Terminating Upstream..."); inUpstream.close(); outUpstream.close(); } else { /* terminate downstream */ System.out.println("Pipe: Terminating Downstream..."); inDownstream.close(); outDownstream.close(); } System.out.println ("Pipe: Closing server sockets."); serverSocket.close(); } }