转载自  如何使用MAT进行JVM内存泄露分析

在《Java Agent的隔离实现以及卸载时一些坑》中,卸载Agent之后,使用 jmap-histo:live pid命令验证执行FGC,相关Class是否会被回收,结果遇到了一些问题,最终通过MAT内存分析才定位到了问题,本文介绍如何使用MAT进行内存泄露分析。

MAT安装

MAT是eclipse中的一个插件,不过也提供了独立的版本,在IDEA风靡的今天,建议直接使用独立版本,官网下载地址

http://www.eclipse.org/mat/downloads.php

根据操作系统版本下载最新的MAT

MAT配置

找到MemoryAnalyzer.ini文件,该文件里面有个Xmx参数,该参数表示最大内存占用量,默认为1024m,根据堆转储文件大小修改该参数即可。

获取堆转储文件

1、如果想主动获取,可以使用jamp命令,对于部署到服务器上的程序可以采用这种方式,获取堆转储文件后scp到本地,然后本地分析。

  1. jmap -dump:format=b,file=<dumpfile.hprof> <pid>

2、如果想在发生内存溢出的时候自动dump,需要添加下面参数

  1. -XX:+HeapDumpOnOutOfMemoryError

MAT使用

打开MAT之后,加载dump文件,显示下面的界面。

一般用到比较多的2个功能 1、Histogram 2、Leak Suspects

Histogram

这个功能主要是查看类和对象关系,对象和对象之间的关系,用来定位哪些对象在FGC之后还活着,哪些对象占大部分内存。

1、点开Histogram,可列出每一个类的实例数,支持正则表达式查找,也可以计算出该类所有对象的retained size。

Shallow Heap就是对象本身占用内存的大小,不包含其引用的对象内存,实际分析中作用不大。常规对象(非数组)的ShallowSize由其成员变量的数量和类型决定。数组的shallow size有数组元素的类型(对象类型、基本类型)和数组长度决定。对象成员都是些引用,真正的内存都在堆上,看起来是一堆原生的byte[], char[], int[],对象本身的内存都很小。

Retained Heap值的计算方式是将Retained Set(当该对象被回收时那些将被GC回收的对象集合)中的所有对象大小叠加。或者说,因为X被释放,导致其它所有被释放对象(包括被递归释放的)所占的heap大小。

Retained Heap例子: 一个ArrayList对象持有100个对象,每一个占用16 bytes,如果这个list对象被回收,那么其中100个对象也可以被回收,可以回收16*100 + X的内存,X代表ArrayList的shallow大小。

所以,RetainedHeap可以更精确的反映一个对象实际占用的大小。

2、选择一个Class,右键选择List objects > with incoming references

在新页面会显示通过这个class创建的对象信息

3、选择一个对象,右键选择Path to GC Roots > **,通常在排查内存泄漏的时候,我们会选择exclude all phantom/weak/soft etc.references, 意思是查看排除虚引用/弱引用/软引用等的引用链,因为被虚引用/弱引用/软引用的对象可以直接被GC给回收,我们要看的就是某个对象否还存在Strong 引用链(在导出HeapDump之前要手动出发GC来保证),如果有,则说明存在内存泄漏,然后再去排查具体引用。

这时会拿到GC Roots到该对象的路径,通过对象之间的引用,可以清楚的看出这个对象没有被回收的原因,然后再去定位问题。

假如说上面对象此时本来应该是被GC掉的,简单的办法就是将其中的某处置为null或者remove掉,使其到GC Root无路径可达,处于不可触及状态,垃圾回收器就可以回收了。

Leak Suspects

Leak Suspects 界面提示可能存在内存的泄露。

然后接着,是问题一的描述,列出了一些比较大的实例。

点击Details可以看到细节信息

点开Details进入详情页面,在详情页面Shortest Paths To the Accumulation Point表示GC root到内存消耗聚集点的最短路径,如果某个内存消耗聚集点有路径到达GC root,则该内存消耗聚集点不会被当做垃圾被回收。

内存快照对比

为了有效的找出内存泄露的对象,一般会获取两个堆转储文件(先dump一个,隔段时间再dump一个),并同时打开两个dump文件。

打开其中一个Histogram,然后点击下面按钮。

选择另外一个需要对比的dump文件

通过对比结果可以方便的看出对象的变化情况,并快速定位问题。

还不会使用的MAT的同学,赶紧学起来,机会都是留给有准备的人。

如何使用MAT进行JVM内存泄露分析相关推荐

  1. 转自美团技术博客的jvm内存泄露分析

    Linux与JVM的内存关系分析 引言 在一些物理内存为8g的服务器上,主要运行一个Java服务,系统内存分配如下:Java服务的JVM堆大小设置为6g,一个监控进程占用大约600m,Linux自身使 ...

  2. 记录一次生产环境下的jvm内存泄露问题和分析解决过程!

    作者:未完成交响曲,资深Java工程师!目前在某一线互联网公司任职,架构师社区合伙人! 发现异常 首先通过我们内部搭建的日志平台发现我们线上环境一个java应用有大量的http接口请求超时,登录lin ...

  3. videocapture.read()解决内存泄露_只需4个步骤,分析解决在生产环境下JVM内存泄露问题...

    作者:未完成交响曲 发现异常 首先通过我们内部搭建的日志平台发现我们线上环境一个java应用有大量的http接口请求超时,登录linux服务器查看网络环境没有问题,判断是应用自身运行异常,重启应用后发 ...

  4. java内存泄露分析方案

    java内存泄露分析方案 - 准备工作 1.工具:Memory Analyzer Tool (mat); 1)安装Memory Analyzer Tool (mat) 2.原料:dump.hprof ...

  5. JAVA内存泄露分析和解决方案及WINDOWS自带查看工具

    JAVA内存泄露分析和解决方案及WINDOWS自带查看工具 Java内存泄漏是每个Java程序员都会遇到的问题,程序在本地运行一切正常,可是布署到远端就会出现内存无限制的增长,最后系统瘫痪,那么如何最 ...

  6. 记一次 JAVA 的内存泄露分析

    记一次 JAVA 的内存泄露分析 摘要:本文属于原创,欢迎转载,转载请保留出处:https://github.com/jasonGeng88/blog 当前环境 jdk == 1.8 httpasyn ...

  7. 一次.net托管内存泄露分析

    简介:一次.net托管内存泄露分析 最近协助分析了一个.net进程内存泄露的问题,过程分享给大家. 症状:客户的服务端.net进程出现分钟级的cpu抖动,接近100%后落回. 图1 分析:支持同学通过 ...

  8. 10.JVM内存简单分析

    JVM内存简单分析 一.方法区(method) 二.堆栈(stack) 2.1基本变量的存储 2.2对象引用的存储 三.堆(heap) 我见青山多妩媚,料青山见我应如是. 辛弃疾<贺新郎·甚矣吾 ...

  9. java实现初始化三角形数组_Java 数组、多维数组,动态、静态初始化,数组JVM内存模型分析...

    Java 数组.多维数组,动态.静态初始化,数组JVM内存模型分析 什么是数组 所谓数组,是具有相同数据类型的若干变量或者数据按照一定排序规则组合起来的一种数据存储格式.数组中的数据称为数组元素,我们 ...

最新文章

  1. 5月第3周业务风控关注 |网信办公布整治教育类应用的成果 关闭“作业狗”等20余款应用...
  2. smarty学习——编程知识
  3. 什么是groupid和artifactId?
  4. BZOJ 4386 Luogu P3597 [POI2015]Wycieczki (矩阵乘法)
  5. 怎么让修改的html持久化_redis持久化机制
  6. CF1458B Glass Half Spilled
  7. 五猴分桃c语言课程设计,c语言程序设计五猴分桃问题实验报告.doc
  8. UVA 514——Rails
  9. phpcmsV9 添加内容:如何“增加复选框、下拉菜单”(含案例、截图)- 教程篇
  10. C++中的错误处理方法(含示例代码)
  11. asp.net findcontrol html控件,c# – FindControl找不到控件
  12. 面试pythone_叮!你需要的Python面试指南以送到!
  13. cs客户端 实时权限_【CS学习笔记】7、SMBbean的作用
  14. Linux使用jstat命令查看jvm的GC情况(转)
  15. UniWebview Bug处理记录
  16. java自己写的网络爬虫
  17. ENVI遥感图像监督分类与出图制作
  18. 如何屏蔽迅雷9右侧广告首页
  19. 我傻眼了:一个完全由 AI 生成的播客,采访了乔布斯
  20. python爬虫可视化web展示_python爬虫可视化——小龙虾

热门文章

  1. 算法题目——二次函数三分求极值(HDU-3714)
  2. 数据结构 快速排序(详解)
  3. 岛屿类问题的广度优先深度优先双解法(Leetcode题解-Python语言)
  4. [Spring5]IOC容器_Bean管理XML方式_自动装配
  5. [mybatis]映射文件_参数处理_#和$取值区别
  6. 堆的定义与操作(C语言)
  7. [C++11]对模板右尖括号的优化
  8. [MySQL基础]MySQL常见命令介绍
  9. [蓝桥杯2016初赛]交换瓶子
  10. 添加库路经 linux,linux下的静态库与动态库