JVM内存泄露排查

本文介绍如何配置Tomcat以支持jconsole远程监控,包括设置jmxremote.password文件、修改catalina.sh参数及使用jconsole工具进行远程连接。同时介绍了利用jmap命令导出堆内存使用详情的方法,并通过MemoryAnalyzer工具分析潜在的内存泄露问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一:tomcat配置jconsole远程连接

1. jdk配置jmxremote.password

cp jmxremote.password.template jmxremote.password

2.jmxremote.password最后增加下列内容

monitorRole  QED

controlRole   password1111


3.tomcat服务bin/catalina.sh文件增加下列内容

JAVA_OPTS="$JAVA_OPTS -Djava.rmi.server.hostname=10.10.77.145 -Dcom.sun.management.jmxremote"
JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.port=12345"
JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.authenticate=true"
JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.ssl=false"

JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.pwd.file=/home/jdk1.7.0_71/jre/lib/management/jmxremote.password"


10.10.77.145:当前tomcat服务机器的IP地址

12345:jconsole远程服务开放的端口

重启tomcat服务

二:jconsole工具远程连接

打开本地windows机器jdk安装目录bin/jconsole.exe工具



连接成功后出现下列图表



打开内存图表,我这里配置了CMS(concurrentMarkSweep)垃圾回收机制,所以显示的是CMS Old Gen,如果没配置CMS,应该是perm Old Gen(老年代区)。

当验证程序是否有内存泄露时,可以高并发的发送请求让服务程序一直在处理请求,可以看见下列的线条一直处于上升状态,当过一会儿后(时间可以长一点),点击执行GC,当内存使用率没有下降,则大致表明有内存泄露。这里可以让程序多调试几次,确定是否是由于内存泄露导致的。 如果程序无内存泄露,则正确的线条状态应如下所示。


三:jmap命令导出堆内存使用情况

jmap -heap pid       查看jvm堆内存使用情况

pid表示tomcat服务进程号,我配置了CMS垃圾回收机制,如果不配置,应该是 perm old generation,表示老年代堆区(jvm老年代区自行百度),如果是内存泄露,这里的内存会一直上升,直到100,就算调用gc,内存使用率也不会下降。



jmap -dump:format=b,file=./heap.bin pid  导出堆使用详情文件

pid表示tomcat服务进程号,为了更能排查那里出现了内存泄露,等到老年代内存使用率达到90%以上最佳,等一会就导出完成


四:MAT图形化查看堆内存使用情况

下载MemoryAnalyzer工具 http://www.eclipse.org/mat/downloads.php 点击打开链接

解压文件,打开mat目录下文件MemoryAnalyzer.exe工具


导入刚才堆内存文件heap.bin



打开详情,从上图可知类DubboFilterUtil有问题,从下图可知对象RequestInfo占用了太多的内存,剩下的就只需要定位到代码排查原因即可



### 排查Java应用中的内存泄漏 #### 工具介绍 多种工具可用于检测和分析Java应用程序中的内存泄漏。常用的工具有Java VisualVM、Eclipse Memory Analyzer Tool (MAT),以及 JProfiler。 - **Java VisualVM** 是一个集成了多个命令行工具的可视化界面,提供了丰富的功能来监视、剖析本地或远程的应用程序性能状况,支持线程栈跟踪查看、垃圾收集日志分析等功能[^4]。 - **Eclipse MAT** 可用于深入分析堆转储数据,帮助识别未释放的对象引用链路,定位潜在的内存泄漏源码位置[^2]。 - **JProfiler** 提供了全面的性能调优解决方案,不仅限于内存问题还包括启动时间测量等方面的支持;它能实时追踪对象分配情况,并提供直观图表展示内存变化趋势[^3]。 #### 实践操作指南 当怀疑存在内存泄漏时,可以采取如下措施: 1. 设置 JVM 参数 `-XX:+HeapDumpOnOutOfMemoryError` 和 `-XX:HeapDumpPath=<path>` 来确保在发生 `OutOfMemoryError` 错误时自动生成堆转储文件[^5]; 2. 利用上述提到的各种工具加载该堆转储文件进行进一步调查。例如,在VisualVM中可以通过“Heap Dump”选项获取当前时刻完整的堆状态快照,之后借助其内置插件如 "Leak Suspects Report" 自动找出可疑区域; 3. 对比不同时间段内的heap dump差异,观察是否有异常增长的趋势,特别是关注那些长期存活却不再使用的实例集合[^1]; 4. 结合静态代码审查与动态运行时监测手段相结合的方式,寻找可能导致内存泄漏的设计缺陷或者编程错误,比如监听器注册而忘记注销等问题。 ```bash # 启动带有 HeapDump 配置参数的 Java 应用程序示例 java -XX:HeapDumpPath=/tmp/heapdumps MyApplication ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值