objectInputStream = new ObjectInputStream(new BufferedInputStream(inputStream)) hangs, also readObject hangs

0

Problem 1  Hangs at

objectInputStream = new ObjectInputStream(new BufferedInputStream(inputStream))

I was trying to figure out why one of my responses from the server was getting delayed for about 3-4 seconds. Some googleing, hinted that I should try bufferedstreams. So I modified my code to
On the client side I have

objectOutputStream = new ObjectOutputStream(new BufferedOutputStream(outputStream));
// objectOutputStream.flush() ;
objectInputStream = new ObjectInputStream(new BufferedInputStream(inputStream));

On the server side I  have

inputObjectStream = new ObjectInputStream(new BufferedInputStream(clientSocket.getInputStream()));
outputObjectStream = new ObjectOutputStream(new BufferedOutputStream(clientSocket.getOutputStream()));

I started to get hangs on the client side at

objectInputStream = new ObjectInputStream(new BufferedInputStream(inputStream));

The fix to this is 2 fold
1) Create your OutStreams before your Instream
2) And flush your OutStream before createing your Instream

On the client side I have

objectOutputStream = new ObjectOutputStream(new BufferedOutputStream(outputStream));
objectOutputStream.flush() ;
objectInputStream = new ObjectInputStream(new BufferedInputStream(inputStream));

On the server side I  have

outputObjectStream = new ObjectOutputStream(new BufferedOutputStream(clientSocket.getOutputStream()));
outputObjectStream.flush() ;
inputObjectStream = new ObjectInputStream(new BufferedInputStream(clientSocket.getInputStream()));

Problem 2  Hangs at readObject

I realized that I was not flushing all my objectstreams after writeObject call. Its more important to flush after a writeObject when you start using a BufferedStream. Since this is the only way the readObject will know that no more is expected at this time.

Edited
So the flushing and BufferedIOStreams helped performance big time. But I realized that readObject was holding up the object, but comparing the in time of the response using wireshark. Smart move I must say :). Now that know the packet is waiting, I was able to narrow down to Serialization as the root cause. So, I removed the List, ArrayList, replaced them with simple []’s. And WOW, worked like a charm. Performance improved big big time, CPU utilization was down from 100% to 25% (at 50 clients at a time loads) and 50% with 100 clients concurrently. WOW, this is fun.

2 Takeaways
– Serialization is a killer, so stick to primitives as much as possible
– BufferedIOStreams and flushing at the right places

Someday, I will try externalization too. Hopefully that will further improve performance :). Will report back

Advertisements