学习 尚硅谷 宋红康 JVM从入门到精通 的学习笔记
概述
jmap全称 JVM Memory Map.作用之一是获取dump文件(堆转储快照文件,二进制文件),还可以获取目标Java进程的内存相关信息,包括Java堆各区域的使用情况、堆中对象的统计信息,类加载信息等等。
dump文件(堆转储快照文件,二进制文件)是当前时刻内存中的一些对象一些数据占用内存的大小的记录这样的情况,是一个二进制的文件,需要用专门的工具来打开。
基本语法
1.使用语法可以通过在DOS窗口中使用jmap/jmap -h/jmap -help查看
2.
3.[server_id@]<……>是为远程连接准备的
基本语法
-dump
生成Java堆转储快照:dump文件
特别的:-dump:live只保存堆中的存活对象
-heap
输出整个堆空间的详细信息,包括GC的使用、堆配置信息,以及内存的使用信息等
-histo
输出堆中对象的同级信息,包括类、实例数量和合计容量
特别的:-histo:live只统计堆中的存活对象
-permstat
以ClassLoader为统计口径输出永久代的内存状态信息
仅linux/solaris平台有效
-finalizerinfo
显示在F-Queue中等待Finalizer线程执行finalize方法的对象
仅linux/solaris平台有效
-F
当虚拟机进程对-dump选项没有任何响应时,可使用此选项强制执行生成dump文件
-h | -help
jamp工具使用的帮助命令
-J
传递参数给jmap启动的jvm
演示
使用1:导出内存映像文件(dump文件)
注意:
- 对于以上说明中的第1点是自动方式才会这样做,而手动不会在Full GC之后生成Dump
- 使用手动方式生成dump文件,一般指令执行之后就会生成,不用等到快出现OOM的时候
- 使用自动方式生成dump文件,当出现OOM之前先生成dump文件
- 如果使用手动方式,一般使用第2种,毕竟生成堆中存活对象的dump文件是比较小的,便于传输和分析
手动的方式
jmap -dump:format=b,file=<filename.hprof> <pid><br /> jmap -dump:live,format=b,file=<filename.hprof> <pid><br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/350923/1655095553951-50df318e-7936-46ff-9c73-ec6ffaf1dd86.png#clientId=u35603e1f-a89e-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=293&id=u036fa32e&margin=%5Bobject%20Object%5D&name=image.png&originHeight=293&originWidth=763&originalType=binary&ratio=1&rotation=0&showTitle=false&size=244592&status=done&style=none&taskId=u3b110770-7558-4f5a-9764-a52d67d2cb2&title=&width=763)
生产dump文件
你会发现导出的hprof文件会越来越大,就是因为随着应用的执行,相关的数据也会越来越多,当然如果你参数配置带有-dump:live参数的话,代表hprof只保存堆中存货的对象. , 那么你生成的hprof文件也有可能会变小.
在实际的生产环境中,你生成的hprof文件可能会有几百mb大小,这样文件就有点大了,dump指令如果带有live之后,这样hprof文件可能就不会那么大了, 实际情况下oom 情况大多数原因是gc回收不走的对象存活导致的,所以实际生产环境,绝大多数都是用-dump:live指令
自动的方式
当程序发生oom退出应用的时候,一些顺势信息都会随着程序的终止而消失,这样重现oom问题就比较困难了,如果能在发生oom的时候,自动导出dump文件就更好了.
-XX:+HeapDumpOnOutOfMemoryError:在程序发生oom的时候,导出应用程序的当前dump文件.<br /> -XX:HeapDumpPath=<filename.hprof> 指定堆快照的保存位置..
比如:
-Xmx100m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=D:\m.hprof
具体使用如下:
启动程序之后等待
当发生oom的一瞬间,立马就生成了一个hprof文件出来
使用2:显示堆内存相关信息
jmap -heap 进程id
jmap -heap 进程id只是时间点上的堆信息,而jstat后面可以添加参数,可以指定时间动态观察数据改变情况,而图形化界面工具,例如jvisualvm等,它们可以用图表的方式动态展示出相关信息,更加直观明了
例子如下:
文件内容:
文件内容有堆空间的配置信息, 新生代和老年代的占用情况,
jmap -histo 进程id
输出堆中对象的同级信息,包括类、实例数量和合计容量,也是这一时刻的内存中的对象信息
例子如下: