I ran into an "interesting" issue with sqlmaps today. I've been trying to get a webapp into a state where it can be reloaded repeatedly without eventually failing but this turns out to be almost impossible (see http://www.szegedi.org/articles/memleak.html for an entertaining write up). The JDK has various places that can hold references to classes loaded by a webapp classloader, which prevents the webapp classloader from being garbage collected (see http://www.docjar.com/docs/api/sun/net/www/http/HttpClient.html and http://www.docjar.com/html/api/sun/net/www/http/KeepAliveCache.java.html for examples). Eventually the (Sun) JVM runs out of PermGen space, throws an OutOfMemoryError and all is lost.
Tomcat 5.5 tries to clean up various things in the clearReferences method of its WebappClassLoader, like deregistering jdbc drivers, clearing various IntrospectionUtils caches, releasing the commons logging LogFactory, etc. but there are so many different things that hold references it is fighting a losing battle. In trying to rearrange various jars in the app I'm working with to avoid holding references from outside the webapp classloader to classes inside the webapp classloader I noticed that sqlmaps has similar issues. The ClassInfo CLASS_INFO_MAP holds onto a static map keyed by class. If the sqlmap jars are loaded from outside the webapp classloader (in Tomcat's common or shared libs) this map can hold references to classes loaded by the webapp classloader. These references keep the webapp classloader live in the eye of the garbage collector and it will never be reclaimed. This keeps all the classes loaded by the webapp classloader live and eats up PermGen space fairly quickly. Here's another good link that notes problems with sqlmaps as well http://www.java-community.de/archives/140-Memory-leaks-et-alii.html There are so many other places that do similar things that fixing sqlmaps probably won't help the situation much, but it sure can't hurt. It would be nice if sqlmaps could be changed to use weak references to the cached reflection information so that it isn't the reason a webapp classloader can't be reclaimed by the garbage collector. Cheers, Derek