JAVA语言之在JVM heap dump里查找没有关闭文件的引用的方法实例
小标 2018-09-11 来源 : 阅读 1322 评论 0

摘要:本文主要向大家介绍了JAVA语言之在JVM heap dump里查找没有关闭文件的引用的方法实例,通过具体的内容向大家展示,希望对大家学习JAVA语言有所帮助。

本文主要向大家介绍了JAVA语言之在JVM heap dump里查找没有关闭文件的引用的方法实例,通过具体的内容向大家展示,希望对大家学习JAVA语言有所帮助。

背景
最近排查一个文件没有关闭的问题,记录一下。
哪些文件没有关闭是比较容易找到的,查看进程的fd(File Descriptor)就可以。但是确定fd是在哪里被打开,在哪里被引用的就复杂点,特别是在没有重启应用的情况下。
在JVM里可以通过heap dump比较方便地反查对象的引用,从而找到泄露的代码。
以下面简单的demo为例,Demo会创建一个临时文件,并且没有close掉:
import java.io.File;import java.io.FileInputStream;import java.io.IOException;public class Test { public static void main(String[] args) throws IOException {  File tempFile = File.createTempFile("test", "ttt");  FileInputStream fi = new FileInputStream(tempFile);   System.in.read(); }}
通过文件名查找对应的fd
进程打开的文件在OS里有对应的fd(File Descriptor),可以用lsof命令或者直接在linux下到/proc目录下查看。
以demo为例,可以找到test文件的fd是12:
$ ls -alh /proc/11278/fd/total 0dr-x------ 2 admin users  0 Jun 30 18:20 .dr-xr-xr-x 8 admin users  0 Jun 30 18:20 ..lrwx------ 1 admin users 64 Jun 30 18:20 0 -> /dev/pts/0lrwx------ 1 admin users 64 Jun 30 18:20 1 -> /dev/pts/0lr-x------ 1 admin users 64 Jun 30 18:24 11 -> /dev/urandomlr-x------ 1 admin users 64 Jun 30 18:24 12 -> /tmp/test7607712940880692142ttt
对进程进行heap dump
使用jmap命令:
jmap -dump:live,format=b,file=heap.bin 11278
通过OQL查询java.io.FileDescriptor对象
对于每一个打开的文件在JVM里都有一个java.io.FileDescriptor对象。查看下源码,可以发现FileDescriptor里有一个fd字段:
public final class FileDescriptor { private int fd;
所以需要查找到fd等于12的FileDescriptor,QOL语句:
select s from java.io.FileDescriptor s where s.fd == 12
使用VisualVM里的OQL控制台查询
在jdk8里自带VisualVM,jdk9之后可以单独下载:https://visualvm.github.io/
把heap dump文件导入VisualVM里,然后在“OQL控制台”查询上面的语句,结果是:
再可以查询到parent,引用相关的对象。
使用jhat查询
除了VisualVM还有其它很多heap dump工具,在jdk里还自带一个jhat工具,尽管在jdk9之后移除掉了,但是个人还是比较喜欢这个工具,因为它是一个web接口的。
jhat -port 7000 heap.bin
访问 https://localhost:7000/oql/ ,可以在浏览器里查询OQL:
总结
先找出没有关闭文件的fd 从heap dump里据fd找出对应的java.io.FileDescriptor对象,再找到相关引用    

本文由职坐标整理并发布,希望对同学们有所帮助。了解更多详情请关注编程语言JAVA频道!

本文由 @小标 发布于职坐标。未经许可,禁止转载。
喜欢 | 0 不喜欢 | 0
看完这篇文章有何感觉?已经有0人表态,0%的人喜欢 快给朋友分享吧~
评论(0)
后参与评论

您输入的评论内容中包含违禁敏感词

我知道了

助您圆梦职场 匹配合适岗位
验证码手机号,获得海同独家IT培训资料
选择就业方向:
人工智能物联网
大数据开发/分析
人工智能Python
Java全栈开发
WEB前端+H5

请输入正确的手机号码

请输入正确的验证码

获取验证码

您今天的短信下发次数太多了,明天再试试吧!

提交

我们会在第一时间安排职业规划师联系您!

您也可以联系我们的职业规划师咨询:

小职老师的微信号:z_zhizuobiao
小职老师的微信号:z_zhizuobiao

版权所有 职坐标-一站式IT培训就业服务领导者 沪ICP备13042190号-4
上海海同信息科技有限公司 Copyright ©2015 www.zhizuobiao.com,All Rights Reserved.
 沪公网安备 31011502005948号    

©2015 www.zhizuobiao.com All Rights Reserved

208小时内训课程