Tuesday, July 19, 2005
File.deleteOnExit is evil
I was dealing with a JVM crash on Linux recently. During a load test, the JVM ran out of native heap and died. That is, it ran out of heap memory used by native code, not the Java heap.
After looking at an mtrace log, I found the culprit: a large number of calls to File.deleteOnExit which was used in conjunction with File.createTempFile to create a temporary file and then mark it for deletion. No, I didn't write this code!
How does File.deleteOnExit work? It adds the file's pathname to a list of pathnames to delete when the JVM exits. But when will that happen? It could be weeks from now. In the meantime, pathnames accumulate in memory. This approach is evil. It should never be used in a server application. There are alternatives such as a file deletion queue and reaper thread that removes old temporary files. Or better yet, more careful analysis of a temporary file's lifecycle so that you delete it when it's no longer needed.
More info on the problems with File.deleteOnExit can be found in Sun's Bug Database: Bug ID: 4513817 File.deleteOnExit consumes memory.
After looking at an mtrace log, I found the culprit: a large number of calls to File.deleteOnExit which was used in conjunction with File.createTempFile to create a temporary file and then mark it for deletion. No, I didn't write this code!
How does File.deleteOnExit work? It adds the file's pathname to a list of pathnames to delete when the JVM exits. But when will that happen? It could be weeks from now. In the meantime, pathnames accumulate in memory. This approach is evil. It should never be used in a server application. There are alternatives such as a file deletion queue and reaper thread that removes old temporary files. Or better yet, more careful analysis of a temporary file's lifecycle so that you delete it when it's no longer needed.
More info on the problems with File.deleteOnExit can be found in Sun's Bug Database: Bug ID: 4513817 File.deleteOnExit consumes memory.
RSS 0.92 Feed