On Mon, May 16, 2016 at 11:56 PM, Jochen Theodorou <[email protected]> wrote:
> On 17.05.2016 07:53, Alain Stalder wrote: > >> That looks very good to me :) >> >> I will definitely try out the InvokerHelper.removeClass(clazz) with >> added ClassInfo removal plus Introspector.flushFromCaches(clazz) and see >> if I can get garbage collection before reaching the limit on Metaspace >> or Heap. >> >> And, maybe something like the following could be added to the >> GroovyClassLoader? Thinking aloud: >> >> Assuming the following is true: Any class can only be garbage collected >> once its ClassLoader can be garbage collected, because each class keeps >> a reference to its ClassLoader (so that it can use it to load further >> classes when needed when running methods). >> > > not only the class, the classloader internals also keep such a reference. > And I mean java.lang.ClassLoader here. > > So why not have the GroovyClassLoader keep a set of all classes it >> compiled itself and were loaded and offer a new ~ >> GroovyClassLoader#finalCleanup() method that removes meta information >> for all these classes so that they would become immediately eligible for >> garbage collection? (I guess InvokerHelper.removeClass(clazz) and >> Introspector.flushFromCaches(clazz), but whatever is needed...) >> > > GroovyClassLoader (GCL) actually represents a tree of class loaders. for > each compilation GCL will spawn an instance of InnerLoader. Since two > different compilations are supposed to know each others classes a list of > classes is kept in GCL itself (see classCache). The inner loader itself is > not referenced by GCL. Because of that list GCL has the clearCache method > to remove classes from previous compilations. > > Why did we use this structure? GCL is supposed to offer you the > possibility to compile the same class multiple times. That means you will > get the same class multiple times. At the same time a class must be defined > under the same name only once in a given defining class loader. As a result > trying to define a class, that already exists under that name results in an > error. A classloading constraint is actually to return the same class > instance each time you request a class with a certain name. Is implies the > error before.... it also means GCL is breaking those constraints knowingly. > > Anyway... I think such a cleanup method is misplaced in GCL, since it > spans beyond the classloader... how about GroovySystem? > > I agree that if a method were added I don't think GCL is the right place and that something like GroovySystem#removeClass(Class) or GroovySystem#flushFromCaches(Class) would be good.
