Results 1 to 6 of 6
  1. #1
    kjkrum's Avatar
    kjkrum is offline Senior Member
    Join Date
    Apr 2011
    Location
    Tucson, AZ
    Posts
    1,060
    Rep Power
    6

    Default SocketTimeoutException and BufferedReader

    I'd like to wrap a socket's InputStream in a BufferedReader and use readLine(). However, readLine's behavior seems to be undefined when the underlying stream throws a SocketTimeoutException. I found this thread from someone who was seeing readLine return buffered characters even though it hadn't received a newline. In my case, it seems to be discarding any buffered characters.

    Does anyone know of a library with a version of BufferedReader that has clearly defined behavior in these circumstances? Ideally, I would like it to retain any buffered characters and return them on a subsequent call to readLine() after a newline has been received.
    Last edited by kjkrum; 06-30-2011 at 07:49 PM.
    Get in the habit of using standard Java naming conventions!

  2. #2
    doWhile is online now Moderator
    Join Date
    Jul 2010
    Location
    California
    Posts
    1,641
    Rep Power
    7

    Default

    In my case, it seems to be discarding any buffered characters.
    Define discarded - if an exception is thrown, it will propagate to a catch statement. At that point, how do you know the buffer is empty? Did you try reading it using the read method (as opposed to readLine)? I recommend posting an SSCCE to more clearly define the behavior you get, then describe the behavior you wish

  3. #3
    kjkrum's Avatar
    kjkrum is offline Senior Member
    Join Date
    Apr 2011
    Location
    Tucson, AZ
    Posts
    1,060
    Rep Power
    6

    Default

    Quote Originally Posted by doWhile View Post
    Define discarded
    Here's the situation:
    App calls BufferedReader.readLine()
    BufferedReader.readLine() calls read(byte[], int, int) on underlying stream
    read(...) returns bytes that encode to "ABC";
    BufferedReader.readLine() calls read(byte[], int, int)
    read(...) throws SocketTimeoutException which is caught outside readLine()
    App calls BufferedReader.readLine()
    BufferedReader.readLine() calls read(byte[], int, int)
    read(...) returns bytes that encode to "DEF\n";

    Expected behavior: readLine() returns "ABCDEF"
    Behavior I'm seeing: readLine() returns "DEF"
    Last edited by kjkrum; 06-30-2011 at 11:33 PM. Reason: clarity
    Get in the habit of using standard Java naming conventions!

  4. #4
    kjkrum's Avatar
    kjkrum is offline Senior Member
    Join Date
    Apr 2011
    Location
    Tucson, AZ
    Posts
    1,060
    Rep Power
    6

    Default

    Here's a SSCCE. On my system, the final line of output is "DEF". I expected "ABCDEF".

    Java Code:
    import java.io.BufferedReader;
    import java.io.InputStream;
    import java.io.InputStreamReader;
    import java.io.OutputStream;
    import java.io.OutputStreamWriter;
    import java.io.PrintWriter;
    import java.net.ServerSocket;
    import java.net.Socket;
    import java.net.SocketTimeoutException;
    
    
    public class BufferedReaderBehavior {
    
    	/**
    	 * @param args
    	 */
    	public static void main(String[] args) {
    		try {
    			// set up the writer
    			Thread t = new Thread() {
    				public void run() {
    					try {
    						Thread.sleep(2500);
    						System.out.println("writer started");
    						Socket s1 = new Socket("localhost", 12345);
    						System.out.println("writer connected");
    						OutputStream out = s1.getOutputStream();
    						PrintWriter pw = new PrintWriter(new OutputStreamWriter(out));
    						pw.print("ABC");
    						pw.flush();
    						Thread.sleep(1000);
    						pw.print("DEF\n");
    						pw.flush();
    						s1.close();
    					}
    					catch(Exception e) {
    						System.err.println("writer: " + e.getMessage());
    					}
    				}
    			};
    			t.start();
    			
    			// set up the reader
    			ServerSocket ss = new ServerSocket(12345);
    			System.out.println("reader listening");
    			Socket s2 = ss.accept();
    			s2.setSoTimeout(50);
    			InputStream in = s2.getInputStream();
    			BufferedReader br = new BufferedReader(new InputStreamReader(in));
    			while(true) {
    				try {
    					String str = br.readLine();
    					if(str != null) {
    						System.out.println(str);
    						break;
    					}
    				}
    				catch(SocketTimeoutException e) { continue; }
    			}
    		}
    		catch(Exception e) {
    			System.err.println("reader: " + e.getMessage());
    		}
    	}
    
    }
    Get in the habit of using standard Java naming conventions!

  5. #5
    doWhile is online now Moderator
    Join Date
    Jul 2010
    Location
    California
    Posts
    1,641
    Rep Power
    7

    Default

    Interesting. This seems the be the behavior of a BufferedReader (looking at the source code, the call to readLine after the exception writes over the buffer). Try writing your own buffer if you want to capture the buffered data:
    Java Code:
    	int val = 0;
    	char[] buffer = new char[256];
    	while ( val != -1 ){
    		try{
    			val =  reader.read(buffer, 0, 256);
    			String s  = new String(buffer);
    			System.out.println(s);
    		}catch(SocketTimeoutException e){
    			continue;
    		}
    	}

  6. #6
    kjkrum's Avatar
    kjkrum is offline Senior Member
    Join Date
    Apr 2011
    Location
    Tucson, AZ
    Posts
    1,060
    Rep Power
    6

    Default

    Yeah... I looked at the source for two different implementations: Sun/Oracle's and GNU's. I forget which one it was, but in one of them, readLine uses a StringBuffer which is a local variable. So if that method throws, whatever's been copied into the StringBuffer is lost.
    Get in the habit of using standard Java naming conventions!

Similar Threads

  1. java.net.SocketTimeoutException: Read timed
    By ersachinjain in forum Networking
    Replies: 0
    Last Post: 11-17-2010, 04:50 PM
  2. Replies: 0
    Last Post: 06-30-2010, 11:39 AM
  3. BufferedReader, need help!
    By zacharyrod in forum New To Java
    Replies: 10
    Last Post: 11-19-2009, 10:56 AM
  4. Replies: 0
    Last Post: 06-08-2009, 09:59 PM
  5. BufferedReader
    By vidhya.sk in forum New To Java
    Replies: 2
    Last Post: 09-18-2008, 01:57 PM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •