Still grappling with this… thought I’d throw some screenshots out from Eclipse MAT after analyzing my 2GB heap so you could see what I’m seeing. Mark Mandel claims this is useful but I think the CF-on-top-of-Java abstraction makes using this information incredibly difficult. Sure, I see that Transfer has 1.6GB of data locked up, but who is holding onto it?
Going through the screen shots in order:
- 93% of the heap is tied up in coldfusion.runtime.TemplateProxy and its child of coldfusion.runtime.VariableScope. Not particularly surprising that there are variables out there taking up space.
- This is the same dominator tree but expanded so you can see how the tree works. This is where I start getting lost. You can see there are a couple of hashmap entries though that are holding onto like 800mb and 500mb on their own.
- One of the techniques I read about was to use the right-click menu and choose to look at an object by Merging Shortest Path to GC Root. The GC Root is what is preventing these objects from being collected so as long as it hangs around, so does your object. This is that view. I find it strange that the root is java.util.TimerThread followed by flex.messaging.SessionMetricsTracker. I don’t use Flex anywhere in my app? Hrmm… does this have anything to do with the server monitor perhaps? I do have it enabled in “monitoring” only… no memory or profiling. Somehow this timer is connected to the Transfer CacheManager.cfc and FacadeFactory.cfc which is holding onto 1.6GB of heap.
- Right-clicking on the template proxy and listing objects with an incoming reference gives us this image. Here is where there appears to be some kind of circular reference. You can see as you drill down that the same number of objects and heap space keeps popping up in what looks like a loop. This is the kind of thing that would prevent an object from being GC’d.
So… any ideas?