在JDK 1.4以及更早的版本, 抛出的OutOfMemoryError错误没有任何多余的信息, 因此出现这种问题时不太好分析, 对于使用了第三方代码或者不同时期不同人员开发的系统来说, 更是如此.
以前查找原因的方法是
换用IBM的JDK, 因为IBM的JDK在发生内存溢出宕机时会
生成heapdump文件, 然后用IBM的
HAT工具分析heapdump文件,通常可以找到原因.
局限是IBM只对AIX/Linux平台提供JDK.
Sun的JDK 6也有类似IBM JDK的这种功能了, 只是需要加入
-XX:+HeapDumpOnOutOfMemoryError开关激活这个功能. 更好的消息是这个开关不是JDK 6独有的, 也被Sun移植到了
JDK 5 update 7和JDK 1.4.2_12和它们以后的版本中. 它们产生的 heapdump文件统一由
JDK 6附带的jhat工具来分析.
这确实是个有用的功能, 所以贴上来备忘, 呵呵.
以下是引用来自 http://weblogs.java.net/blog/mandychung/archive/2006/12/java_se_6_monit_1.html 的内容:
OutOfMemoryError Diagnosability JDK 6 provides a better support to diagnose OutOfMemoryError. This error now includes a stack trace where the allocation failed. Another useful improvement is the
-XX:+HeapDumpOnOutOfMemoryError option which tells the HotSpot VM to generate a heap dump when an allocation from the java heap or the permanent generation cannot be satisfied. In addition, a new
-XX:OnOutOfMemoryError=<command> option is added for you to specify a command that the HotSpot VM will invoke when the OutOfMemoryError is thrown. OutOfMemoryError Improvement
HeapDumpOnOutOfMemoryError on 5.0u7 and 1.4.2_12
BTW:
1)上面表格中右边的第一个链接说明了JDK 5和6对OutOfMemoryError错误信息的改进, 其中
JDK 6已经可以包含堆栈信息了. 虽然此时堆栈信息不一定有用, 但聊胜于无, 呵呵.
2)如果应用服务器跑在JDK 5以上, ,并且在本地环境, 还可在应用服务器上启用JMX开关, 这样通
过JDK 5以上附带的jconsole连接到应用服务器, 可以实时观测内存分配情况,各线程堆栈等信息. 这对观察应用有无内存泄露也有一定用处.
(启用方法之一为添加JVM属性
:-Dcom.sun.management.jmxremote.port=1099 -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false)
JDK1.6下的这个功能,很好用。SUN的这个功能要比IBM的HeapDump好用一些,尤其是那个分析工具。