Search code examples
javaubuntumemory-leaksnio

Java NIO causes file descriptor leak


We have a http server which is implemented based on Java NIO. It is running on Ubuntu 10.04.2 LTS with java version "1.6.0_20" Java(TM) SE Runtime Environment (build 1.6.0_20-b02) Java HotSpot(TM) Server VM (build 16.3-b01, mixed mode)

However, it leaks file descriptors, all of them are unix domain sockets.

When use the command "netstat -anp", we can find that the process only opens two unix domain socket. However, when use lsof -p , we can find that there are huge amounts of file descriptors which are unix domain socket and have the same device value and node value as the one find in netstat.

I have checked our code, and all of the SocketChannels are closed properly.

Is it a bug of Sun JDK? How can we fix it?


Solution

  • The root cause is found. In our code, when we close socketchannel, we also cancel the key. The problem is that: a. We cancel the key in the select thread, and close the socketchannel in another thread b. The socket channel is closed until the key.cancel is invoked.

    By reading the implementation of close and cancel, we can find that the unix domain socket is opened by dup2 and never closed some times (concurrent issue).