GC 永久代溢出導致服務宕機

現(xiàn)象

今天峦失, 生產(chǎn)上的springboot 應用cpu 達到200%扇丛, 即占用了2核, 線上應用奔潰尉辑, 應用無法訪問帆精。在立刻重啟應用后,應用恢復正常隧魄, 奇怪的是卓练, 在一段時間后, 服務又出現(xiàn)無法訪問的情況购啄。

問題分析

該問題可以大致上看成2類襟企, 可能也可能沒有直接關聯(lián)

  1. 服務宕機
  2. 應用占用CPU很高

排查思路及手段

因為不同的問題排查思路及方式會不同, 針對本次服務宕機的排查問題追溯如下:
通過jps查看應用是否運行 > 通過Top查看系統(tǒng)運行狀況 > 查看錯誤日志 >

排查細節(jié):

1狮含、 使用jps查看是哪個進程編號pid 對應哪個應用

jps: Java Virtual Machine Process Status Tool

[root@localhost ~]#  jps             
26610 Bootstrap
28877 jar
18039 TSDMain
26091 Kafka
19456 Jps

如果發(fā)現(xiàn)應用不在列表中顽悼, 則本次服務無法訪問則是因為應用未啟動造成, 則需要排查是什么原因造成服務未啟動几迄。
可能原因:

  1. linux oom killer 將應用殺死
  2. 人為殺死(可能性很形盗)
  3. 操作系統(tǒng)宕機等原因(如果操作系統(tǒng)在云服務上,可能性極杏承病)

此時坤溃, 我發(fā)現(xiàn)應用還在列表中屯断。

2. 查看錯誤日志

java 應用在線上會以文件的形式記錄warn級別及以上的錯誤日志诽俯, 發(fā)現(xiàn)有大量以下內容的錯誤日志:

   "Cannot serialize; nested exception is 
   org.springframework.core.serializer.support.SerializationFailedException: Failed to 
   serialize object using DefaultSerializer; nested exception is java.lang.OutOfMemoryError: 
   PermGen space"

以上錯誤很明顯了: 內存溢出, 永久代內存空間不足务荆。

2.1查看應用永久代內存空間大小
 >   jstat -gcpermcapacity pid                      #perm對象的信息及其占用量
  PGCMN      PGCMX       PGC         PC      YGC   FGC    FGCT     GCT   
   21504.0    83968.0    83968.0    83968.0   361     2    0.906   39.789

# 同時我們可以通過jstat -gcutil來動態(tài)查看gc的狀態(tài)
> jstat -gcutil pid 
大致情況如下:
  S0     S1     E      O      P     YGC     YGCT    FGC    FGCT     GCT   
  0.00  11.13  11.97  40.61  33.67   5508   44.783    22   10.686   55.469
(以上是jvm參數(shù)加入后的狀態(tài), 之前看到P是99%以上)

經(jīng)過換算穷遂, 發(fā)現(xiàn)perm代的最大容量才81M函匕。

本次解決辦法:

設置jvm參數(shù), 增大永久代內存的大小
(java -XX:MaxPermSize=512M -jar xxxx.jar &)
之后服務不再出現(xiàn)無法提供服務的問題蚪黑。

事后回顧及思考:

應用通過jenkins發(fā)布盅惜, 構建后執(zhí)行腳本運行springboot的應用, 采用的是java -jar xxx.jar 忌穿, 故采用默認配置抒寂, 從而忽略了生產(chǎn)對于內存要求的苛刻性。
所以對于生產(chǎn)環(huán)境的配置掠剑, 往往要結合并分析實際業(yè)務場景屈芜, 選擇適合的配置, 當然有時候不能盲目加入硬件配置朴译, 也可以通過一定的邏輯優(yōu)化來解決問題井佑。

知識補充:(針對該現(xiàn)象)

  1. 內存中什么對象是永久代
    有時候把永生代和方法區(qū)對等, 方法區(qū)是多個線程共享的區(qū)域眠寿, 存儲常量信息躬翁,類信息,方法信息盯拱。
截取自《深入理解java虛擬機 JVM高級特性與最佳實踐》2.2.5
  1. JVM性能調優(yōu)監(jiān)控工具 使用
    往往大多數(shù)程序員忽視了這方面的知識盒发, 對關于jvm的問題束手無策, 其實jdk中為我們提供了大量的jvm調優(yōu)及監(jiān)控工具狡逢, 比如jps宁舰、jstack、jmap奢浑、jhat明吩、jstat。
    在本次我們使用了jps和jstat來查看問題殷费, 當然這些命令還有其他參數(shù),如果感興趣的話可以在網(wǎng)上搜索低葫。

針對CPU占用高的問題

系統(tǒng)CPU占用高曾經(jīng)也出現(xiàn)過详羡,所以很快能夠排查出大致問題所在。

大致思路

1. 檢查是哪個進程占用了高cpu

>  top              # top命令經(jīng)常用來監(jiān)控linux的系統(tǒng)狀況
top命令示意圖

有時候會看到mysql進程占用很高cpu
一般mysql的配置dba會配置好嘿悬,往往不是mysql配置的問題实柠, 所以 對于開發(fā)人員來說, 首先看慢sql日志善涨。如果此時發(fā)現(xiàn)有大量慢sql日志產(chǎn)生窒盐, 則需要結合實際業(yè)務場景進行相應的sql及邏輯優(yōu)化草则, 有必要的話可以通過一些緩存手段來解決問題。

如果是java 應用占用很高cpu

2 java應用CPU占用高

這時候我們開始對具體的應用進行分析了蟹漓, 我們可以借用一些工具來分析java進程炕横。如
jstack、jmap葡粒、jhat份殿、hprof。

我的做法是首先定位占用高cpu的線程:
步驟如下:

  1. 通過jps獲取進程id
  2. 通過jstack 查找線程dump
>  ps -mp pid  -o THREAD,tid,time
線程
將線程id轉換為16進制(以方便找到dump中對應的線程)
> printf "%x\n" tid
>  jstack pid |grep tid -A 60      這里的tid為轉換的16進制嗽交, grep -A  n 為匹配的行數(shù)后n條

查詢結果大致如下:

"container-0" prio=10 tid=0x00007f9a14e1e800 nid=0x465a waiting on condition [0x00007f9a6dc57000]
   java.lang.Thread.State: TIMED_WAITING (sleeping)
    at java.lang.Thread.sleep(Native Method)
    at org.apache.catalina.core.StandardServer.await(StandardServer.java:427)
    at org.springframework.boot.context.embedded.tomcat.TomcatEmbeddedServletContainer$1.run(TomcatEmbeddedServletContainer.java:177)
"VM Thread" prio=10 tid=0x00007f9a7812f800 nid=0x45ec runnable 
"GC task thread#0 (ParallelGC)" prio=10 tid=0x00007f9a7801e000 nid=0x45dd runnable 

如果定位發(fā)現(xiàn)cpu高的線程為GC卿嘲, 很有可能是GC出現(xiàn)了問題。
如果線程dump中執(zhí)行的是某業(yè)務代碼夫壁, 可能是發(fā)生了死循環(huán)之類的拾枣。

參考:
[1] jstat 命令詳解
[2] Java SE Specifications Chapter 2. The Structure of the Java Virtual Machine
[3] 《深入理解java虛擬機 JVM高級特性與最佳實踐》

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市盒让,隨后出現(xiàn)的幾起案子梅肤,更是在濱河造成了極大的恐慌,老刑警劉巖糯彬,帶你破解...
    沈念sama閱讀 222,681評論 6 517
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件凭语,死亡現(xiàn)場離奇詭異,居然都是意外死亡撩扒,警方通過查閱死者的電腦和手機似扔,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 95,205評論 3 399
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來搓谆,“玉大人炒辉,你說我怎么就攤上這事∪郑” “怎么了黔寇?”我有些...
    開封第一講書人閱讀 169,421評論 0 362
  • 文/不壞的土叔 我叫張陵,是天一觀的道長斩萌。 經(jīng)常有香客問我缝裤,道長,這世上最難降的妖魔是什么颊郎? 我笑而不...
    開封第一講書人閱讀 60,114評論 1 300
  • 正文 為了忘掉前任憋飞,我火速辦了婚禮,結果婚禮上姆吭,老公的妹妹穿的比我還像新娘榛做。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 69,116評論 6 398
  • 文/花漫 我一把揭開白布检眯。 她就那樣靜靜地躺著厘擂,像睡著了一般。 火紅的嫁衣襯著肌膚如雪锰瘸。 梳的紋絲不亂的頭發(fā)上刽严,一...
    開封第一講書人閱讀 52,713評論 1 312
  • 那天,我揣著相機與錄音获茬,去河邊找鬼港庄。 笑死,一個胖子當著我的面吹牛恕曲,可吹牛的內容都是我干的鹏氧。 我是一名探鬼主播,決...
    沈念sama閱讀 41,170評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼佩谣,長吁一口氣:“原來是場噩夢啊……” “哼把还!你這毒婦竟也來了?” 一聲冷哼從身側響起茸俭,我...
    開封第一講書人閱讀 40,116評論 0 277
  • 序言:老撾萬榮一對情侶失蹤吊履,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后调鬓,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體艇炎,經(jīng)...
    沈念sama閱讀 46,651評論 1 320
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 38,714評論 3 342
  • 正文 我和宋清朗相戀三年腾窝,在試婚紗的時候發(fā)現(xiàn)自己被綠了缀踪。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,865評論 1 353
  • 序言:一個原本活蹦亂跳的男人離奇死亡虹脯,死狀恐怖驴娃,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情循集,我是刑警寧澤唇敞,帶...
    沈念sama閱讀 36,527評論 5 351
  • 正文 年R本政府宣布,位于F島的核電站咒彤,受9級特大地震影響疆柔,放射性物質發(fā)生泄漏。R本人自食惡果不足惜镶柱,卻給世界環(huán)境...
    茶點故事閱讀 42,211評論 3 336
  • 文/蒙蒙 一婆硬、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧奸例,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,699評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至逻卖,卻和暖如春宋列,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背评也。 一陣腳步聲響...
    開封第一講書人閱讀 33,814評論 1 274
  • 我被黑心中介騙來泰國打工炼杖, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人盗迟。 一個月前我還...
    沈念sama閱讀 49,299評論 3 379
  • 正文 我出身青樓坤邪,卻偏偏與公主長得像,于是被迫代替她去往敵國和親罚缕。 傳聞我的和親對象是個殘疾皇子艇纺,可洞房花燭夜當晚...
    茶點故事閱讀 45,870評論 2 361

推薦閱讀更多精彩內容

  • R:創(chuàng)建共同目的 總而言之,當你感到對方和你的目的不一致時邮弹,應當這樣做:暫停充滿爭議的對話內容黔衡,關注對方的真正目的...
    涵媽秀秀閱讀 506評論 0 0
  • 意念這個東西是真的講究配得的,今天就有一個感受腌乡,本來計劃的目標是兩個店共同達成1.5萬的銷售盟劫,后來我想嘗試著向三萬...
    馬駿輝閱讀 322評論 0 1
  • 人生要敢愛、敢恨与纽、感悟人生侣签、感悟經(jīng)歷、感悟傷痛渣锦。點點滴滴成就永恒硝岗,累積成就記憶!
    一夢一醒閱讀 142評論 0 0
  • 繼去年走進博物館參加《永恒之城—古羅馬的輝煌》展覽后袋毙,尼采讀書會第二次走進博物館看展覽《山東歷史文化展》型檀。 有人說...
    蘇步哲閱讀 1,405評論 0 0