有些時候我們需要查看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
