Socket handler exhaustion


Well, hope I am right posting at this forum. If not please tell me which is the correct. So: ]

I’m coding a client/server application in C/C++. The client periodically opens a very simple single bracketed TCP/IP conversation with the server (connects to server, writes message, waits and receives response, closes connection). The server does the same (accepts connection, reads the message, writes the response, closes the connection). Very simple.

I use plain sockets and the expected family of functions (this is a requirement): socket, connect, etc. For each of these functions, I log the result of calling them. There is no single error, either at client or server side, for any of these functions. I first shutdown(.,…RDWR) and then close(…) the socket at each side.

I usually test with 1 sec. and up to 20 secs. of delay between each client pulse. The server IP address is resolved just once, when connecting to it for 1st time. From then on the address and port are well known (However, in real conditions this may change; the client may fail to reach the last server and connect to any other from a list it has).

As time elapses, the socket handle number (the one returned by the socket(…) function) increases and is never reused. This produces the complete socket exhaustion (at around nr. 1023). After this, it’s impossible for the client to reconnect. Please notice that netstat shows no “ghost” connections; it rather shows the last tens in FIN-WAIT status; the older ones finally disappear – which is correct. It is the socket handle in the program which is not reused.

The solution should not be, of course, to set the process or the system file handler maximum to the highest possible value, since the program will continue to consume handlers without reusing them.

Ah! And no setsockopt() at all now – have tried some but there is no specific option, seems to me.

I guess I am missing something very basic here…

¿Does anybody have any idea or any hint or help?

Thanks !

(BTW: OpenSUSe 11.0, g++ 4.3.1. (what more ? )).

You would have to post your code, but I suspect you don’t realise that on the server side after you have done an accept, the original listening socket should continue to be used and not closed. The new socket returned by the accept is closed after the transaction. Usually, unless the amount of work done is small and fast, the server forks off a process to deal with the new socket and loops back to wait for another request on the original socket with accept.

Thanks for your response.

Er… yes, of course, the server socket is never closed, except when shutting down the server application.

When accepting a connection, a thread is created and the newly obtained socket passed to it. The server returns to accept() into its original socket. This is the ‘canonical’ and almost unavoidable manner of doing it.

It is the server thread that closes its socket. In the server side there is no socket exhaustion; descriptors are reused with no problem at all. That’s why I did not mention details regarding the server side.

On the client side there is no need to shutdown the socket, just close it. Shutdown is for servers with listening sockets.

Thanks for your quick reply.

As far as IEEE / Open Group concerns and the Linux kernel doc, shutdown() is intended for sockets in general. There is no reference id docs to using it only for listening sockets. I’ve been using it both ways in other platforms before and works fine; it’s a polite way – when pertinent – to tell TCP at the other side that no more traffic is intenderd and/or accepted.

However, please take into account that the original version of my application did not include shutdowning the client socket; I put it a couple of days ago just for the sake of correctness – that you may dispute, but the app is still working the same: up to the final socket exhaustion…

Debating what you have and haven’t done in words is pointless. Post your code so that people here can see what you’ve done. Obviously there’s something you are missing since this isn’t a problem for correctly written clients.