TCP ServerSocket stops listening

Hello guys . I am having a really strange problem with my ServerSockets.
first, this is my code of starting a serverSocket:


ServerSocket serverSocket = new ServerSocket(P.PORT);

while (true)
 {

 ...

 Socket connectionSocket= serverSocket .accept();
//launch thread to listen to data on this connectionSocket and go to accept new connections
}

basically that’s it . It works quite fine , for a long while . It accepts the connections sends and receives a few data, then closes the connection .

But something happens that it just does not accept connections anymore . In the client, I don’t get any errors, the thread just hangs waiting for the connection (if a timeout is not set). I dont get a “Server not found”, it seems that it can see the server, but the connection is never stabilished.

Sometimes my serverSocket lasts for a week, sometimes a few days . That’s with 200 connections/day .

Anybody has an idea ?
Thanks in advance .

I have had ServerSockets listening for many months, with hundreds of connections per second, not a single problem.

Probably out of file descriptors?

For a more robust serversocket listener:

  1. ensure all connections are properly closed, no matter what
  2. prevent a flood-attack from bringing down your server (lack of file descriptors will crash other processes too)

final Semaphore preventFlooding = new Semaphore(maxConcurrentConnections);

while(true)
{
   preventFlooding.acquireUninterruptibly();
   final Socket socket;
   try {
       socket = server.accept();
   } catch(IOException exc) {
       preventFlooding.release();
       continue; // maybe next time!
   }

   Runnable task = new Runnable() {
      public void run() {
           InputStream input = null;
           OutputStream output = null;
           try {
               socket.setSoTimeout(2000); // we must receive the first byte within 2 sec, change your timeout later to something larger
               input = socket.getInputStream();
               output = socket.getOutputStream();

               DO_A_LOT_OF_WORK(socket, input, output);
           }
           finally {
               preventFlooding.release();

               try { if(input!=null) input.close(); } catch(IOException exc) { /* ignore */ }
               try { if(output!=null) output.close(); } catch(IOException exc) { /* ignore */ }
               try { socket.close(); } catch(IOException exc) { /* ignore */ }
           }
      }
   }

   // better: a thread-pool, with a few connections per second
   // creating threads really starts to drain performance
   new Thread(task).start();
}

Regarding the flood attack: I got hit by this so many times that it’s silly. Thousands of connections in a few seconds, and if you’re not careful, something breaks. Either VM heap, RAM (swapping), threads, running out of file descriptors… that is a serious issue for a server, as every process relies on them. Avoid IOException(“Too many files open”) at all cost, and my Semaphore will cap your file-descriptor count pretty well.

Riven, that way I would only accept connections after I DO_A_LOT_OF_WORK.
This is not actually desirable, since this can take several seconds, and I would be out of listeners in that interval, right ?
Of course I could start like 5 Threads of listeners but then I think it just breaks the anti-flooding strategy that the semaphore is there for .

I think I’ll stick to 1. ensure all connections are properly closed, no matter what
Come to think of it, I wrote my networking code a long time ago, so there is probably some error handling missing .

Thank you for now .

No.

You can have N (=maxConcurrentConnections) threads doing A_LOT_OF_WORK(…)

See: new Thread(task).start()

If you set maxConcurrentConnections to 100, you will at most have 100 thread handling 100 connections.

ah okay I just skipped the Semaphore(maxConcurrentConnections); and thought of a mutex .

Thanks again