利用Java heap dump查找、分析问题

开发、应用中老是会遇到OutOfMemory异常,而且常常是过一段时间内存才被吃光,这里可以利用java heap dump出jvm内存镜像,然后再对其进行分析来查找问题。
《java heap dump触发和分析》这篇文章很好的介绍了heap dump的方法和分析的工具。
平常利用 jmap -dump:format=b,file=/path/file.hprof   这个java自带的工具来dump heap很方便,但当内存溢出问题发生的比较快的情况下,该命令就有可能来不及或无效。
这个时候 在应用启动时配置相关的参数  -XX:+HeapDumpOnOutOfMemoryError 就比较方便,当然可以再加上 - XX:HeapDumpPath= /path/file.hprof  来指定文件的输出路径。
不知道怎么用这些参数?就在你启动应用的时候加,如:
/usr/lib/jvm/java-1.6.0/bin/java -server -Xms1536m -Xmx1536m -XX:NewSize=256m -XX:MaxNewSize=256m -XX:PermSize=64m -XX:MaxPermSize=64m  -XX:+HeapDumpOnOutOfMemoryError  - XX:HeapDumpPath= /path/file.hprof  -Djava.ext.dirs=/xxx/lib/ ClassName

《java heap dump触发和分析》里有介绍到分析工具,个人觉得利用java自带的  $JAVA_HOME/bin/jhat -J-Xmx512m /path/file.hprof 工具看分析结果不是很友好,当然这情况紧急、身边又没工具的情况下也是一个好的选择。但个别比较推荐里面介绍的 IBM HeapAnalyzer(没用过)和 MemoryAnalyzer,关于 MemoryAnalyzer的介绍可以看下 使用 Eclipse Memory Analyzer 进行堆转储文件分析里的介绍。


Java heap dump触发和分析

为了分析java应用的内存泄漏,使用thread dump往往解决不了问题。使用jstat【eg:jstat -gcutil pid 1000 5】工具查看运行的java应用的heap size,perm size ,survivor ratio等,当时你无法知道是什么对象把堆填满了。

     什么是 Java heap dump

      首先需要搞懂什么是java heap,java heap是分配给实例类和数组对象运行数据区,所有java线程在运行期间共享heap中的数据。Java heap dump相当于java应用在运行的时候在某个时间点上打了个快照(snapshot)。

     如果你不懂啥是snapshot,点击这里

     触发 Java heap dump

有以下方法出发heap dump

  1. 使用$JAVA_HOME/bin/jmap -dump来触发,eg:jmap -dump:format=b,file=/home/longhao/heamdump.out
  2. 使用$JAVA_HOME/bin/jcosole中的MBean,到MBean>com.sun.management>HotSpotDiagnostic>操作>dumpHeap中,点击 dumpHeap按钮。生成的dump文件在java应用的根目录下面。
  3. 在应用启动时配置相关的参数 -XX:+HeapDumpOnOutOfMemoryError,当应用抛出OutOfMemoryError时生成dump文件。
  4. 使用hprof。启动虚拟机加入-Xrunhprof:head=site,会生成java.hprof.txt文件。该配置会导致jvm运行非常的慢,不适合生产环境。


     分析 Java heap dump

     1:使用IBM HeapAnalyzer

    IBM HeapAnalyzer是一款免费的JVM内存堆的图形分析工具,它可以有效的列举堆的内存使用状况,帮助分析Java内存泄漏的原因。

    下载解压后有一个ha413.jar,执行: java -Xmx512m -jar ha413.jar /home/longhao/heapdump.out

     执行结果如图所示:


   

     2:jhat

    jhat(Java Head Analyse Tool )是用来分析java堆的命令,可以将堆中的对象以html的形式显示出来,包括对象的数量,大小等等,并支持对象查询语言OQL,分析相关的应用后,可以通过http://localhost:7000来访问分析结果。

    示例: $JAVA_HOME/bin/jhat -J-Xmx512m /home/longhao/dump.out


     3:Eclipse MemoryAnalyzer

    Eclipse Memory Analyzer是一个快速并且功能强大的Java heap分析器,能够帮助你查找内存泄漏和减少内存消耗。在File>Acquire Heap Dump>configure>HPROF jmap dump provider设置一下分析应用的JDK,点击相关应用列表来生成heap dump并分析。

    

    在socket,nio中的有些API中,申请的内存是直接向OS要的,在堆中分析内存是查看不到的,可以通过-XX:MaxDirectMemorySize=来设置应用向OS直接申请的最大内存数。

来源 http://www.blogjava.net/mlh123caoer/archive/2011/10/04/360020.html

你可能感兴趣的:(jvm)