16

Java服务,CPU100%问题如何快速定位?

 4 years ago
source link: https://www.tuicool.com/articles/M363YrM
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

上篇《 Java服务,内存OOM问题如何快速定位? 》发布后,有朋友在评论留言,问CPU100%的性能问题,如何 找到相关服务 ,如何 定位问题代码 ,也非常考验技术人的功底,今天简单说下思路。

假设,服务器上部署了若干Java站点服务,以及若干Java微服务,突然收到运维的CPU异常告警。 如何定位是 哪个服务进程 导致CPU过载, 哪个线程 导致CPU过载, 哪段代码 导致CPU过载?

简要步骤如下:

(1)找到最耗CPU的 进程

(2)找到最耗CPU的 线程

(3)查看 堆栈 ,定位线程在干嘛,定位对应 代码

步骤一、找到最耗CPU的进程

工具 top

方法

  • 执行 top -c ,显示进程运行信息列表

  • 键入P (大写p),进程按照CPU使用率排序

图示:

AnmIzuV.jpg!web

如上图,最耗CPU的进程PID为10765。

步骤二: 找到最耗CPU的线程

工具 top

方法

  • top -Hp 10765 ,显示一个进程的线程运行信息列表

  • 键入P (大写p),线程按照CPU使用率排序

图示:

f2IbuyB.jpg!web

如上图,进程10765内,最耗CPU的线程PID为10804。

步骤三: 查看堆栈,定位线程在干嘛,定位对应代码

首先, 将线程PID转化为16进制

工具 printf

方法 printf "%x\n" 10804

图示:

jM7FfyY.png!web

如上图,10804对应的16进制是0x2a34,当然,这一步可以用计算器。

之所以要转化为16进制,是因为堆栈里,线程id是用16进制表示的。

接着, 查看堆栈,找到线程在干嘛

工具 jstack

方法 jstack 10765 | grep '0x2a34' -C5 --color

  • 打印进程堆栈

  • 通过线程id,过滤得到线程堆栈

图示:

vINbIzQ.jpg!web

如上图,找到了耗CPU高的线程对应的线程名称“AsyncLogger-1”,以及看到了该线程正在执行代码的堆栈。

最后,

根据堆栈里的信息,找到对应的代码 ,搞定!

希望对经常进行线上CPU问题排查的同学有帮助,如果有更好的实践,也欢迎分享。

相关文章:

Java服务,内存OOM问题如何快速定位?

调研:你遇到过奇葩的CPU100%问题么?


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK