Eclipse Memory Analyzer分析内存使用总结
前言
内存泄露和内存溢出的区别:内存泄露从老年代的增长情况看是缓慢上升的, 最终达到老年代上限才会导致溢出,有些内存泄露可能需要很长的时间发生, 所以说内存泄露更隐蔽, 不像内存溢出那样容易暴露(内存溢出直接抛出OOM), 而且内存长时间得不到释放会导致服务性能越来越差、gc时间变长、响应变慢:
1. 安装
在Eclipse help -> Eclipse Marketplace下搜索Memory:
按照操作流程安装完成,重启Eclipse.
2.获取Heapdump 文件
方法1
**/jdk/1.7.0_95l64/bin/jmap -dump:format=b,file=heapdump_name.hprof <pid>
方法2.
如果你的是spring boot项目且暴露了actuator里面的heapdump的api. 直接用下面的命令。
*/actuator/heapdump
可以每隔一段时间获取一个heapdump文件
3. Histogram 查询
利用Elipse 里Memory Analysis view打开你想分析的heapdump文件
打开Histogram
它按类名将所有的实例对象列出来,可以点击表头进行排序,在表的第一行可以输入正则表达式来匹配结果 :
4. 使用 Compare Basket 功能分析
利用Elipse 里Memory Analysis view依次打开多个heapdump文件
1. 菜单栏 window → compare basket ,打开比较窗口(如果最下面一栏已经有compare basket则这步不需要),如下图:
2. 依次打开3个dump的dashboard面板, 在下方的 Actions一栏点击"histogram"或"dominator tree"生成对应的直方图或支配树列表,如下图:
直方图或支配树都可以列出堆中存活的所有对象,但二者的维度不同, 直方图按照类型统计, 支配树是以对象维度统计。
如果你对项目代码比较熟悉, 通过直方图定位内存泄露会更快,因为它是按照类型全部平铺开的,如果这个项目不是你负责的, 建议使用支配树的方式, 因为支配树包含了对象之间的引用关系(支配树视图可以展开查看内部引用层级)
3. 我们以支配树做比对, 在最下面一栏的"Navigation History (window → navigation history)"里(直方图类似)找到在第2步打开的支配树dominator tree图标, 右键添加到compare basket, 如下图:
添加好后,打开 Compare Basket面板,得到结果:
4. 重复上面的2, 3步骤依次把其他的dump文件添加到"compare basket"栏, 然后点击右上角的红色感叹号, 生成比较结果,如下图:
(注意比较的dump文件的顺序,时间最早的在上面,可以通过右上角的上箭头↑和下箭头↓调整顺序)
生成的比对结果如下:
Shallow Heap一列后面的序号 #0, #1, #2 分别对应:
第一个dump文件占用的shallow size, 第二个dump文件占用的shallow size , 第三个dump文件占用的shallow size
Retained Heap #0, Retained Heap #1, Retained Heap #2 这3列分别对应:
第一个dump文件占用的retained size, 第二个dump文件占用的retained size , 第三个dump文件占用的retained size
红框 圈出的是内存连续增长的对象, 可以通过右边红框的retained heap看出内存变大的趋势
绿框 圈出的是没有变化的对象(至少在这3次比较中没有变化),
蓝框 圈出的是内存占用下降的对象
一般我们主要关注红框标出的对象, 因为这部分发生内存泄露的嫌疑最大
这里先区分两个概念:
Shallow Size
对象自身占用的内存大小,不包括它引用的对象。
针对非数组类型的对象,它的大小就是对象与它所有的成员变量大小的总和。
针对数组类型的对象,它的大小是数组元素对象的大小总和。
Retained Size
Retained Size=当前对象大小+当前对象可直接或间接引用到的对象的大小总和。(间接引用的含义:A->B->C, C就是间接引用)
Retained Size就是当前对象被GC后,从Heap上总共能释放掉的内存。
因为这里我们比较的是支配树, 所以按照retained heap倒序排列, 从左到右依次为: retained heap #0 → retained heap #1 → retained heap #2(以最后一个retained heap #2 倒序, 因为这个是最后一次dump的内存快照, 这样可以看出内存泄露的增长趋势)
5. 使用 Path To Gc Root 定位业务代码
还有另外一个内存泄露的嫌疑是"com.*.common.utils.ITextRendererPoolManager
", 如上面比对结果的图:
单独在dominator tree支配树视图展开如图所示:
ITextRendererPoolManager
内部使用了apache的一个对象缓冲池, 目的可能是为了对象复用, 继续展开,如下图:
发现是pdf的一个工具类:org.xhtmlrenderer.pdf.ITextRenderer, 这个开源的pdf工具是我们项目的邮件功能在发送附件的时候生成pdf文档时引入的一个第三方jar包,开始怀疑是否是这个开源的pdf工具导致的内存泄露, 但是不清楚这个jar包是在哪里调用的?
这里可以通过"path to gc root"查看是谁在引用他, 即我们业务代码调用的地方,如下图:
这里先说下"path to gc root"选项的含义:
with all references : 所有引用, 包括强引用, 弱引用, 软引用, 虚引用
exclude weak reference : 排除弱引用
exclude soft reference : 排除软引用
。。。。
我们知道软引用, 弱引用这些在发生full gc时可能会被回收掉(回收时机不同, 具体可自行百度), 目的是不造成内存溢出。 一般引起内存溢出的都是强引用,所以你可以选择"exclude all ptantom/weak/soft reference"只查看强引用。
Eclipse Memory Analyzer分析内存使用总结相关推荐
- Memory Analyzer分析内存泄漏
Memory Analyzer分析内存泄漏 模拟一次内存溢出 程序不断地向ArrayList添加对象,直至溢出 public class User {String userName;String pa ...
- 一次使用 Eclipse Memory Analyzer 分析 Tomcat 内存溢出
最近,线上生产系统突然频繁的 JVM 内存报警!但本系统近期内并没有上线改动! 为了能查清内存报警的原因,使用 Eclipse Memory Analyzer tool(MAT)对 JVM Dump ...
- 一次使用Eclipse Memory Analyzer分析weblogic内存溢出
前言 在平时开发.测试过程中.甚至是生产环境中,有时会遇到OutOfMemoryError,Java堆溢出了,这表明程序有严重的问题.我们需要找造成OutOfMemoryError原因.一般有两种情况 ...
- Eclipse Memory Analyzer以及内存泄露的原因
Eclipse Memory Analyzer是一个非常棒的堆内存分析工具,是JDK自带的堆分析工具jhat的一个非常好的替代品,能够快速地定位Java内存泄露的原因. 可能有的同学会问, ...
- Eclipse Memory Analyzer,内存泄漏插件,安装使用
网上文档很多,但最初都有问题.整理一份,作为备份.使用过程:开发代码写完后,对可能出现内存溢出的代码,添加配置文件,生成.hprof文件,用memory Analyzer分析排查问题,且泄漏内存大小可 ...
- 使用Eclipse Memory Analyzer分析Tomcat内存溢出
本文语言逻辑转载:http://tivan.iteye.com/blog/1487855 实际分析来源于自己的实际项目. 在平时开发.测试过程中.甚至是生产环境中,有时会遇到OutOfMemoryEr ...
- 内存映像分析工具Eclipse Memory Analyzer
1. Eclipse Memory Analyzer安装 Help ->Eclipse Marketplace,搜索Memory,点击install,->confirm->同意证书内 ...
- 使用Eclipse Memory Analyzer对Tomcat进行内存分析
测试环境 Java : JDK1.6 Tomcat: Tomcat 5.5 Eclipse Memory Analyzer:EMA 1.2.1(直接去Eclipse下载,无需安装哈) 获得Heap D ...
- 使用 Eclipse Memory Analyzer 进行堆转储文件分析
概述 对于大型 JAVA 应用程序来说,再精细的测试也难以堵住所有的漏洞,即便我们在测试阶段进行了大量卓有成效的工作,很多问题还是会在生产环境下暴露出来,并且很难在测试环境中进行重现.JVM 能够记录 ...
最新文章
- 【C语言刷题】交换两个变量(包含不创建临时变量)的解法
- 记一次内存溢出的分析经历
- AI芯片初创公司单纯卖芯片还是捆绑算法的商业模式更好?
- IPSec的安全性如何?—微云MPLS
- Apache Shiro去掉URL中的JSESSIONID
- java异步执行任务
- RT-Thread pin设备驱动代码结构剖析
- 为什么你总办不到大额信用卡?
- 未发现数据源名称并且未指定默认驱动程序_看我如何发现NVIDIA GeForce Experience代码执行漏洞...
- win10多合一原版系统_手把手教你制作官方原版的WIN10系统安装盘
- 蚂蚁金服自研数据库打败Oracle拿下世界第一;三星手机全面退出中国;微软发布Windows 10X双屏系统 | 极客头条...
- 网易编程题-操作序列
- 父子组件如何实现通信
- 荣耀路由器w831刷linux,华为荣耀路由器登录入口:荣耀路由器WS831设置指南【图解】...
- 苹果应用商店审核_苹果应用商店AppStore审核规则指南
- 改编码格式_CAD多行文字编码讲解
- win10笔记本使用virtualbox鼠标失灵
- 正面管教php_我就这样走进正面管教
- Flutter 新版Navigator (一)
- 利用selenium携带cookies实现免登录