/* * Java Network Programming * Copyright (C) 2000 by Jeffrey E. Care (carej@ieee.org) * David Hollinger (hollingd@cs.rpi.edu) * * This library is free software; you can redistribute it and/or modify it under * the terms of the GNU Lesser General Public License as published by the Free * Software Foundation; either version 2 of the License, or (at your option) any * later version. * * This library is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more * details. * * You should have received a copy of the GNU Lesser General Public License * along with this library; if not, write to * * Free Software Foundation, Inc. * 59 Temple Place, Suite 330 * Boston, MA 02111-1307 * USA */ //package edu.rpi.cs.netprog.tcp; import java.io.InputStreamReader; import java.io.IOException; import java.io.OutputStreamWriter; import java.io.Reader; import java.io.Writer; import java.net.ServerSocket; import java.net.Socket; public final class TCPEchoServer { //---------------------------------------------------------------------------- // Private Constants //---------------------------------------------------------------------------- // the default port for the TCP echo service // private static final int defaultPort = 7; //---------------------------------------------------------------------------- // Public Constructors //---------------------------------------------------------------------------- public TCPEchoServer (int port) { // allocate a TCP server socket to listen for connections // ServerSocket server = null; // create a new server socket; if there are any problems with the creation // we can simply exit after printing diagnostic info // try { server = new ServerSocket (port); log ("Server started on port " + port); } catch (IOException exp) { log ("Error opening server socket: " + exp.getMessage ()); exp.printStackTrace (); System.exit (0); } // wait for connections; once a new connection comes in accept it and // spawn a new thread to handle it // while (true) { try { new EchoConnection (server.accept ()); } catch (IOException exp) { log ("Error waiting for connection."); } } } //---------------------------------------------------------------------------- // Private Class Methods //---------------------------------------------------------------------------- private static final void log (String message) { System.err.println (message); } //---------------------------------------------------------------------------- // Main //---------------------------------------------------------------------------- public static void main (String[] argv) { int port = defaultPort; // check if a port was supplied on the command line // int argc = argv.length; if (argc > 0) { try { port = Integer.parseInt (argv[0]); } catch (Exception exp) { log ("Error parsing command line, defaulting to port " + defaultPort); port = defaultPort; } } new TCPEchoServer (port); } //---------------------------------------------------------------------------- // Private Helper Classes //---------------------------------------------------------------------------- // handle echo-request connections - this is an auto-starting thread // private class EchoConnection extends Thread { //-------------------------------------------------------------------------- // Private Data Members //-------------------------------------------------------------------------- private Socket sock; // client this connection is talking to private Reader reader; // character stream from the client private Writer writer; // character stream to the client //-------------------------------------------------------------------------- // Public Constructor //-------------------------------------------------------------------------- public EchoConnection (Socket client) { // try to create character streams, if there are any problems just never // start this thread // try { sock = client; log ("request received"); reader = new InputStreamReader (sock.getInputStream ()); writer = new OutputStreamWriter (sock.getOutputStream ()); start (); } catch (IOException exp) { log ("Error creating read/write streams: " + exp.getMessage ()); exp.printStackTrace (); return; } } //-------------------------------------------------------------------------- // Public Overridden Thread Methods //-------------------------------------------------------------------------- public void run () { final int max = 100; char[] data; int read; while (true) { try { data = new char[max]; read = reader.read (data, 0, max); if (read == -1) return; if (read > 0) { log (new String (data, 0, read - 2)); writer.write (data, 0, read); writer.flush (); } } catch (IOException exp) { log ("closed by peer"); return; } } } //-------------------------------------------------------------------------- // Public Methods //-------------------------------------------------------------------------- public void log (String message) { System.err.print ("<" + sock.getInetAddress ().getHostName () + ">: "); System.err.println (message); } public void log (char[] message) { System.err.print ("<" + sock.getInetAddress ().getHostName () + ">: "); System.err.println (message); } public void log (Throwable t) { System.err.print ("<" + sock.getInetAddress ().getHostName () + ">: "); System.err.println (t.getMessage ()); t.printStackTrace (); } } }