I have a webapp that is subject to class loader leak(s), as PermGen runs out of memory after a number of re-deployments of the webapp.
Google and a couple of helpful persons on the web taught me that the way to investigate such an issue is to open a memory dump in a profiler, locate the faulty class loader, and look at the GC root paths that lead to this loader. Doing so with Yourkit, I could find a leak due to the CompositeClassLoader of Drools, and even managed to work around it. I think.
But after applying the fix, I still see the class loader not GC'ed after a redeploy. When I ask to Yourkit the paths to the loader, it can show literally hundreds of them. Please don't tell me this is the number of leaks I have to investigate!
(The first two paths are the ones from Drools, I took the snapshot before my fix. I also hid my company package names, just to avoid any complaint.)
And what's even more confusing, I don't get the same paths if I use the tab Paths to loader (Alt+3) than if I use the command Paths from GC roots (Ctrl+P) which opens a new tab:
So I would like to understand:
- What does exactly this Paths to loader tab show? The list of classes that have a reference to this class loader? But then what is the difference with the Class list tab? And what is Merged paths? What is the difference between Paths to loader and Paths from GC roots? I am having trouble understanding precisely what these tabs show, and the documentation of Yourkit doesn't say much more than "The paths to loader tab shows the paths to the loader."...
- More generally, how do I find the culprit(s) in this quantity of data?
I am mentioning Yourkit because this is what I use and am familiar with (at least for other profiling tasks) in case there is anything particular with it, but I would assume this is pretty much similar with other memory dump analyzers. The version of Yourkit I have is 8.0.