不幸的是,我们得到了PermgenError。jmap -permstat返回如下内容:
0x00000006c17f8520 1 1968 0x00000006ad000000 dead sun/reflect/DelegatingClassLoader@0x00000007e00686e0
0x00000006babab308 3 19920 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006bca26800 3 15776 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006bb84db80 3 16176 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006b71dffd0 3 19272 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb802小时后jmap -permstat返回:
0x00000006c17f8520 1 1968 0x00000006ad000000 dead sun/reflect/DelegatingClassLoader@0x00000007e00686e0
0x00000006babab308 3 19920 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006bca26800 43 437232 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006bb84db80 3 16176 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80
0x00000006b71dffd0 7 16176 0x00000006b6874f88 dead groovy/lang/GroovyClassLoader$InnerLoader@0x00000007e975bb80如您所见,classLoader加载的类的数量增加了,例如从3个增加到43个。这只是permstat的一小段-(总数= 4676 53521 436264528 alive=1,dead=4675)。我们使用参数运行java:
-XX:+DisableExplicitGC -server -XX:+UseConcMarkSweepGC -XX:+UseParNewGC -XX:MaxGCPauseMillis=800 -XX:+CMSParallelRemarkEnabled -XX:CMSFullGCsBeforeCompaction=1 -XX:+CMSClassUnloadingEnabled但是在permstat中,所有的类加载器都死了。我们解析groovy类的代码:
class GroovyInvoker {
private static GroovyClassLoader gcl = new GroovyClassLoader(Thread.currentThread()
.getContextClassLoader());
protected static GroovyInvoker getInstance(String fileName, String className)
throws BaseScriptingException {
GroovyInvoker instance = new GroovyInvoker();
instance.setFileName(fileName);
instance.setClassName(className);
Class clazz;
clazz = GroovyInvoker.gcl.parseClass(instance.getFile(fileName));
Script aScript = (Script) clazz.newInstance();
instance.setScript(aScript);
return instance;
}
}我读过这个主题:Locating code that is filling PermGen with dead Groovy code和answer with metaClassRegistry problem,但我们现在不能在prod服务器上测试它。我的问题是:当GroovyClassLoader使用缓存时,为什么Groovy加载的类数量在增加?这个数字不应该是常量吗?为什么gc不收集失效的classLoaders?
Java版本的1.6.0_26。Groovy版本1.5.8。
发布于 2014-01-14 09:25:09
我认为这与此有关:http://jira.codehaus.org/browse/GROOVY-6494
如果你不需要上下文类加载器,那么GroovyClassLoader不会泄漏。
https://stackoverflow.com/questions/20566651
复制相似问题