幽兰生空谷
--绝世独自开

那年二月二十八,我开始接触JVM调优之Java进程占用内存不断增长,cpu利用率却很低的分析

背景介绍:

之前开发xxl-job的项目时,从来没有考虑过JVM调优的问题。以至于,积小成大,问题出现了,随着部署的项目越来越多,服务器内存的占用率越来越高。这也属于正常现象,可是原本在mule上运行时明明可以部署同样的项目,内存还绰绰有余,为什么改成xxl-job就不行了呢?

经过观察发现项目的占用内存在不断的增长,但cpu利用率却很低。如下图所示:

重启后可以降低内存占用,但随着运行时间变长,内存占用率也在持续增加,而CPU利用率却很低。

小白分析:

Tip: 因为没有关注过这一块儿,所以也不知道从何下手,故分析的过程和结果只是个人理解~,以下用到的工具命令什么的都是现学的,简单了解一下吧。

起初:

同事告诉我服务器上的项目内存一直在不断的增长,让我看看什么原因。

我第一反应可能是代码里面我是不是写了什么流没关闭,什么for循环的,或者内存泄漏啥的,可这些咱也不懂啊。

然后走的弯路: 就~~~~~~~~~~~很长。

研究——–

中间:

工具Arthas(阿尔萨斯)

curl -O https://arthas.aliyun.com/arthas-boot.jar
java -jar arthas-boot.jar

选择要查看的 java 进程:

jvm 相关
  • dashboard – 当前系统的实时数据面板
  • getstatic – 查看类的静态属性
  • heapdump – dump java heap, 类似 jmap 命令的 heap dump 功能
  • jvm – 查看当前 JVM 的信息
  • logger – 查看和修改 logger
  • mbean – 查看 Mbean 的信息
  • memory – 查看 JVM 的内存信息
  • ognl – 执行 ognl 表达式
  • perfcounter – 查看当前 JVM 的 Perf Counter 信息
  • sysenv – 查看 JVM 的环境变量
  • sysprop – 查看和修改 JVM 的系统属性
  • thread – 查看当前 JVM 的线程堆栈信息
  • vmoption – 查看和修改 JVM 里诊断相关的 option
  • vmtool – 从 jvm 里查询对象,执行 forceGc
dashboard – 当前系统的实时数据面板

看点:使用上面的工具分析,发现进程的大部分时间,内存实际占用率(used)并没有查出来的RES值那么高,排除内存溢出。(到这里还不知道RES值的计算方式)

RES = heap +nonheap + code_cache + metaspace + compressed_class_space

了解到这里,还是不知道原因。

继续研究,了解到了Xms和Xmx两个参数,再结合上面的数据,可以看出分配的内存并没有及时释放掉,到这里思路就明确了,开始考虑jvm垃圾回收类型

常用命令分析:
  • 根据进程号pid查看多少次内的GC记录
jstat -gc pid 3000 30

ps:3000是间隔时间,30是次数

这里的FGC时间过长,有问题
  • 根据pid查看JVM启动参数
jcmd pid VM.flags
-XX:CICompilerCount=3 -XX:InitialHeapSize=262144000 -XX:MaxHeapSize=4181721088 -XX:MaxNewSize=1393557504 -XX:MinHeapDeltaBytes=524288 -XX:NewSize=87031808 -XX:OldSize=175112192 -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:+UseParallelGC

经过查阅资料发现,可以将垃圾回收类型换成-XX:+UseG1GC

借助工具VisualVM分析一下-XX:+UseParallelGC和-XX:+UseG1GC

启动参数:-Xms10m -Xmx1024m -XX:+UseG1GC

启动参数:-Xms10m -Xmx1024m -XX:+UseParallelGC

总结:

可以看出UseG1GC内存占用率比较低。

ps:垃圾回收器类型,算法百度了解一下就可以,还有各项参数也可以了解一下。

Tip:
  • 内存是否归还系统,取决于Xms和Xmx两个参数是否相等。(相等可以避免内存抖动现象,不相等可以释放内存)
  • 内存什么时候归还,取决于垃圾回收器类型。
  • Xms一般取值系统内存的1/64,Xmx一般取值系统内存的1/4
  • 堆内内存实际使用内存(used)低于分配内存(total)的30%会释放内存,重新分配到Xms的值,剩余分配内存低于40%会提前申请内存,直到Xmx的值,超过就会内存溢出。

更换垃圾回收器类型后的数据

内存打下来了,开心~

扩展命令:

查询堆内存前20的占用对象

jmap -histo:live pid | head -20

赞(1) 打赏
版权声明:本文采用知识共享 署名4.0国际许可协议 [BY-NC-SA] 进行授权
文章名称:《那年二月二十八,我开始接触JVM调优之Java进程占用内存不断增长,cpu利用率却很低的分析》
文章链接:https://www.itheibai.com/archives/1173
免责声明:根据《计算机软件保护条例》第十七条规定“为了学习和研究软件内含的设计思想和原理,通过安装、显示、传输或者存储软件等方式使用软件的,可以不经软件著作权人许可,不向其支付报酬。”您需知晓本站所有内容资源均来源于网络,仅供用户交流学习与研究使用,版权归属原版权方所有,版权争议与本站无关,用户本人下载后不能用作商业或非法用途,需在24个小时之内从您的电脑中彻底删除上述内容,否则后果均由用户承担责任;如果您访问和下载此文件,表示您同意只将此文件用于参考、学习而非其他用途,否则一切后果请您自行承担,如果您喜欢该程序,请支持正版软件,购买注册,得到更好的正版服务。
本站是非经营性个人站点,所有软件信息均来自网络,所有资源仅供学习参考研究目的,并不贩卖软件,不存在任何商业目的及用途,网站会员捐赠是您喜欢本站而产生的赞助支持行为,仅为维持服务器的开支与维护,全凭自愿无任何强求。

评论 抢沙发

评论前必须登录!

 

养成“打赏”的好习惯,从我做起!

非常感谢你的打赏,我们将继续给力更多优质内容,让我们一起创建更加美好的网络世界!

支付宝扫一扫

微信扫一扫

登录

找回密码

注册