jstack的使用

有些时候我们需要查看jvm的线程执行情况,如:发现服务器的CPU的负载突然增高了,出现了死锁,死循环,我们该如何分析呢?这个时候就要借助jstack命令了,jstack的作用就是将正在运行的jvm的线程进行快照,并且打印出来

#用法:
jstack <pid>

#示例
jstack 2214

一、jstack 命令参数

 

 

 

二、jstack解决问题

1、死循环导致cpu飙高

死循环的例子:https://blog.csdn.net/goldenfish1919/article/details/8755378

步骤:查找进程-》查找线程-》分析threadDump日志-》找出问题代码

a、查看cpu高的java进程

     top

b、生成进程下所有线程的栈日志

     jstack 1721 > 1712.txt

c、查看进程下哪些线程占用了高的cpu

    top -p 1712 -H

d、将十进制pid转换为十六进制的pid

printf  "%x" 8247

2037

 

2、死锁问题定位

 

 

 

 

3、thread dump日志分析

jstack:
https://docs.oracle.com/javase/8/docs/technotes/tools/unix/jstack.html
java线程的状态
https://docs.oracle.com/javase/8/docs/technotes/guides/troubleshoot/tooldescr034.html
java线程状态转化:
https://mp.weixin.qq.com/s/GsxeFM7QWuR--Kbpb7At2w
https://blog.csdn.net/mynamepg/article/details/81630487
死循环导致CPU负载高
https://blog.csdn.net/goldenfish1919/article/details/8755378
正则表达式导致死循环:
https://blog.csdn.net/goldenfish1919/article/details/49123787

 

4.线程的状态

 

 做如下说明:代码中共有除RUNNING之外的6种状态,为了表示线程正在执行,特加了RUNNING这种状态。我们需要重点关注RUNNABLE、BLOCKED、WAITING和TIME_WAITING四种状态,jstack打印的线程堆栈中也会时时出现。
1)BLOCKED:很好理解,就是线程在等待获取锁进入同步块或者同步方法中。两个死锁的线程即是Blocked。
2)WAITING:比BLOCKED状态进步一些,指我已经获得锁了,但由于有些条件不满足,我自己等会,调用object.wait()方法。等条件满足了,别的线程调用notify再叫我。另外也可以调用Thread.join()方法,顾名思义就是调用别的线程的join方法,让别人join进来先执行,那我就只能等会了。但是由于wait()和notify()以及notifyAll()用于协调对共享资源的存取,所以必须在synchronized块中使用。所以即便wait状态的线程被notfiy唤醒了,也需要再次获得锁,所以唤醒后进入Blocked状态。
3)TIMED_WAITING:类比WAITING,差异是不需要notify()或者notifyAlL()方法唤醒,时间到了我自己醒了。另外sleep比较好理解,就是让当前线程睡一会,与wait的区别是它不释放锁。
4)RUNNABLE不用多说,在JAVA虚拟机中已经在运行,但是在等待操作系统资源,比如CPU时间片。

 

原文链接:https://blog.csdn.net/mynamepg/article/details/81702075

posted @ 2019-12-05 15:54  你我皆牛马  阅读(4321)  评论(0编辑  收藏  举报