OOM内存泄露速查备忘录

本文整理了一份OOM内存泄露问题速查备忘录,详细见下文。

1、核心步骤

  1. top、free、df三连,查看CPU、内存、磁盘的大致情况。
  2. netstat -lp 查看端口占用情况。
  3. 导出内存dump文件:
ini 复制代码
# 保存了堆内存现场 
jmap -dump:format=b,file=heap.dump pid
# 强制保存了堆内存现场
jmap -F -dump:format=b,file=heap.dump pid
  1. 保存线程栈:
bash 复制代码
# 保存了线程栈的现场
jstack pid > jstack.log

2、辅助工具

  • jstat -gc[gcutil] pid [interval]查看JVM垃圾回收情况。通过 jstat 查看 GC 信息,首先就是判断 GC 时间是否较长,GC 发生是否频繁,然后看是否经常性进行 FullGC。
yaml 复制代码
# 如:jstat -gc pid 1000,持续跟踪如1S一次。查看java堆的状况,显示具体数值。
jstat -gc pid 1000
# 通过 jstat -gcutil 5 1000命令查看GC信息,其中5代表进程号,1000代表显示时间。查看堆中各个区域已使用空间占其总空间的百分比。
jstat -gcutil pid 1000
  • 借助MAT(Eclipse Memory Analyzer)工具分析dump文件,分析内存情况。
  • 直接用文本工具打开jstack文件,分析线程占用情况。
  • 借助VisualVM更直观:

3、分析过程

3.1、分析线程栈

直接通过文本工具打开jstack.log,搜索业务相关包名,应该大致能定位出问题:

3.2、分析内存

  1. 用MAT工具打开dump文件
  1. 一般打开Histogram视图,这样能快速地发现问题,也可以打开Leak Suspects(泄露嫌疑),如下图:

寻找这个对象被哪些地方引用了,如下图:

查看大对象,找出自己业务相关的关键引用:

根据上面GC Roots的结果,在结合自身的业务代码排查下,一般都会找到线索,比如:

  • 某个线程远程调用了接口返回的对象,一直被使用未能释放
  • 每次执行的数据量过大
  • 流没有关闭
  • 死循环 或者 递归次数太多
  • 定时任务执行频率过高,在任务没执行完毕时又在持续执行,导致积压了大量对象
  • ......

4、总结

本文整理了一份OOM内存泄露问题速查备忘录。核心内容是:

  • top、free、df三连,然后netstat、jstat工具跟上。
  • 紧接着赶紧jmap、jstack保存现场,然后重启应用。
  • MAT分析问题,修改问题,重新发布。

本篇完结!感谢你的阅读,欢迎点赞 关注 收藏 私信!!!

原文链接: www.mangod.top/articles/20...mp.weixin.qq.com/s/G6QEHNK4o...

相关推荐
小北方城市网31 分钟前
Redis 分布式锁高可用实现:从原理到生产级落地
java·前端·javascript·spring boot·redis·分布式·wpf
六义义1 小时前
java基础十二
java·数据结构·算法
毕设源码-钟学长2 小时前
【开题答辩全过程】以 基于SpringBoot的智能书城推荐系统的设计与实现为例,包含答辩的问题和答案
java·spring boot·后端
笨手笨脚の2 小时前
深入理解 Java 虚拟机-03 垃圾收集
java·jvm·垃圾回收·标记清除·标记复制·标记整理
莫问前路漫漫2 小时前
WinMerge v2.16.41 中文绿色版深度解析:文件对比与合并的全能工具
java·开发语言·python·jdk·ai编程
九皇叔叔3 小时前
【03】SpringBoot3 MybatisPlus BaseMapper 源码分析
java·开发语言·mybatis·mybatis plus
挖矿大亨3 小时前
c++中的函数模版
java·c++·算法
a程序小傲3 小时前
得物Java面试被问:RocketMQ的消息轨迹追踪实现
java·linux·spring·面试·职场和发展·rocketmq·java-rocketmq
青春男大4 小时前
Redis和RedisTemplate快速上手
java·数据库·redis·后端·spring·缓存
Ghost Face...4 小时前
i386 CPU页式存储管理深度解析
java·linux·服务器