PermGen内存溢出的原因

6
我经常在我的环境中检测到PermGen的OOM问题:
  1. java 6
  2. jboss-4.2.3
  3. 不是一个大型web应用程序
我知道String.intern()问题 - 但我没有足够有价值的使用它。 增加MaxPermGen大小并没有起作用(从128 MB增加到256 MB)。
什么其他原因会引起PermGen的OOM? 在这种情况下,什么样的调查方案(策略、工具等)最好?
谢谢任何帮助
2个回答

13

请查看此注释

  • 将JDBC驱动程序放入common/lib中(如Tomcat文档所述),而不是WEB-INF/lib中。
  • 不要将commons-logging放入WEB-INF/lib,因为Tomcat已经引导它。

新的类对象被放置在PermGen中,因此占用越来越多的空间。无论您将PermGen空间设置多大,它都将在足够的部署后达到顶峰。您需要采取措施清除PermGen,以便稳定其大小。有两个JVM标志可以处理此清除:

-XX:+CMSPermGenSweepingEnabled

此设置将PermGen包括在垃圾回收运行中。默认情况下,PermGen空间永远不会被包括在垃圾回收中(因此会无限增长)。

-XX:+CMSClassUnloadingEnabled

该设置告诉PermGen垃圾回收扫描在类对象上执行操作。默认情况下,即使在垃圾回收期间访问PermGen空间时,类对象也会获得豁免。


3
CMSPermGenSweepingEnabled自JDK6起已被弃用,此外,只有在启用+UseConcMarkSweepGC时,+CMSPermGenSweepingEnabled才有用,否则它是无用的。 - UBIK LOAD PACK
@PMDUBIK-INGENIERIE,您是我的英雄,在搜寻了2个小时后,您的+UseConcMarkSweepGC的评论使permgen扫描确实起作用了。有这么多答案告诉人们使用CMSPermGenSweepingEnabled,但似乎没人提到您必须实际添加另一个标志……Tomcat实际上可以重新部署而不会耗尽permgen空间。 - ug_

8

当您重新部署应用程序时,通常会遇到此错误,因为存在classloader泄漏,这意味着所有类都被重新加载,而旧版本仍然存在。

有两种解决方案:

  • 重新启动应用服务器而不是重新部署应用程序-简单但麻烦
  • 使用分析器调查和修复泄漏。不幸的是,类加载器泄漏可能非常难以确定。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接