記一次詭異的頻繁Full GC

報(bào)警了蹄梢,系統(tǒng)異常飆升到3000+傍睹。經(jīng)排查竟然是rpc接口超時(shí)了搀菩,但是服務(wù)提供方反饋系統(tǒng)1ms就返回了螃成,為什么consumer端耗時(shí)是13000+ms港令,網(wǎng)絡(luò)異常情況下的耗時(shí)也不可能這么長(zhǎng)呀,不科學(xué)~瞅了一下機(jī)器監(jiān)控锈颗,what顷霹,機(jī)器竟然一直都在full gc。立馬去機(jī)器上查看情況:用戶(hù)線程已全線暫停击吱,gc線程cpu占用率居高不下淋淀,rpc線程池堵塞。那是什么導(dǎo)致的頻繁的full gc呢覆醇?

GC日志

我們先去看看gc日志朵纷,看看是什么導(dǎo)致的頻繁full gc:

2018-10-12T12:17:35.328+0800: [Full GC (Metadata GC Threshold) 2018-10-12T12:17:35.328+0800: [CMS2018-10-12T12:17:36.998+0800: [CMS-concurrent-mark: 1.617/1.682 secs] [Times: user=1.70 sys=0.01, real=1.69 secs] 
 (concurrent mode failure): 1080352K->1080354K(2355200K), 5.0626275 secs] 1081703K->1080354K(3737600K), [Metaspace: 206712K->206712K(1282048K)], 5.0640593 secs] [Times: user=5.09 sys=0.00, real=5.06 secs] 
2018-10-12T12:17:40.393+0800: [Full GC (Last ditch collection) 2018-10-12T12:17:40.393+0800: [CMS: 1080354K->1080354K(2355200K), 3.4270709 secs] 1080354K->1080354K(3737600K), [Metaspace: 206712K->206712K(1282048K)], 3.4283073 secs] [Times: user=3.33 sys=0.11, real=3.43 secs] 
2018-10-12T12:17:43.833+0800: [Full GC (Metadata GC Threshold) 2018-10-12T12:17:43.834+0800: [CMS: 1080354K->1080354K(2355200K), 3.4584908 secs] 1080361K->1080354K(3737600K), [Metaspace: 206712K->206712K(1282048K)], 3.4598680 secs] [Times: user=3.48 sys=0.00, real=3.46 secs]

從gc日志能夠看出來(lái)炭臭,導(dǎo)致該full gc的原因是達(dá)到了metaspace的gc閾值,這里先解釋下Metadata GC ThresholdLast ditch collection

  • Metadata GC Threshold:metaspace空間不能滿(mǎn)足分配時(shí)觸發(fā)袍辞,這個(gè)階段不會(huì)清理軟引用鞋仍;
  • Last ditch collection:經(jīng)過(guò)Metadata GC Threshold觸發(fā)的full gc后還是不能滿(mǎn)足條件,這個(gè)時(shí)候會(huì)觸發(fā)再一次的gc cause為Last ditch collection的full gc搅吁,這次full gc會(huì)清理掉軟引用威创。

看到這里大家可能會(huì)有疑問(wèn)了,為啥你的gc日志打印了gc的原因呢谎懦?其實(shí)從jdk8開(kāi)始肚豺,gc日志會(huì)默認(rèn)打印gc cause,如果是jdk8之前的版本界拦,可以通過(guò)JVM參數(shù)-XX:+PrintGCCause來(lái)打印gc cause吸申。另外多嘴一句,觀察gc日志其實(shí)可以發(fā)現(xiàn)大量的gc都是因?yàn)?code>Allocation Failure觸發(fā)的享甸,大家不要以為這個(gè)不正常截碴,其實(shí)大部分的gc都是因?yàn)閮?nèi)存分配失敗觸發(fā)的

言歸正傳蛉威,既然是metaspace區(qū)域使用達(dá)到gc閾值從而觸發(fā)的full gc隐岛,那我們來(lái)看一下MetaspaceSize和MaxMetaspaceSize的設(shè)置值:都是256m,但從gc日志也可以看出來(lái)(206712K->206712K)瓷翻,發(fā)生full gc時(shí)metaspace才使用206m,并沒(méi)有達(dá)到閾值呀割坠,這就奇怪了齐帚,沒(méi)有達(dá)到閾值為什么還觸發(fā)了full gc呢?看了下JVM各個(gè)區(qū)域使用情況彼哼,發(fā)現(xiàn)metaspace committed內(nèi)存達(dá)到262144k对妄,大于gc的閾值256m,基本上到這里敢朱,也就明確原因了:metaspace的內(nèi)存碎片化導(dǎo)致了該悲劇的誕生剪菱。

導(dǎo)致Full GC的罪魁禍?zhǔn)?/h3>

對(duì)于metaspace內(nèi)存碎片化,有一個(gè)場(chǎng)景倒是可以滿(mǎn)足拴签,那就是創(chuàng)建了大量的classloader孝常。目前就一次出現(xiàn)full gc時(shí)間點(diǎn)的heap dump不太能看出來(lái)問(wèn)題,我通過(guò)增加jvm參數(shù)-XX:+HeapDumpBeforeFullGC蚓哩、-XX:+HeapDumpAfterFullGC分別在發(fā)生full gc前后做heap dump构灸。通過(guò)對(duì)比分析full gc發(fā)生前后的heap dump,發(fā)現(xiàn)在full gc前創(chuàng)建了大量的sun.reflect.DelegatingClassLoader岸梨,full gc后該classloader也減少了約1000個(gè)喜颁。

到這里稠氮,導(dǎo)致該問(wèn)題的罪魁禍?zhǔn)拙驼业搅耍蔷褪?code>sun.reflect.DelegatingClassLoader半开,但是為什么類(lèi)加載器過(guò)多就會(huì)導(dǎo)致內(nèi)存碎片化呢隔披?在類(lèi)加載器第一次加載類(lèi)的時(shí)候,都會(huì)在metaspace區(qū)域?yàn)槠浞峙湟粔K內(nèi)存寂拆,并且每個(gè)類(lèi)加載器的內(nèi)存區(qū)域都是獨(dú)立的奢米,當(dāng)然咯,一定要走出這個(gè)誤區(qū)漓库,類(lèi)加載器的內(nèi)存分配跟加載類(lèi)的數(shù)量是沒(méi)有關(guān)系的恃慧,即使類(lèi)加載器只加載一個(gè)類(lèi),也是會(huì)在metaspace為其分配一塊內(nèi)存的渺蒿。當(dāng)出現(xiàn)頻繁的類(lèi)加載器創(chuàng)建的時(shí)候痢士,這個(gè)時(shí)候就可能會(huì)出現(xiàn)metaspace內(nèi)存使用率低,但是committed的內(nèi)存已經(jīng)達(dá)到了full gc的閾值從而觸發(fā)了full gc茂装。

寫(xiě)在最后的

一次簡(jiǎn)單的線上小問(wèn)題分析怠蹂,如果項(xiàng)目有大流量入口頻繁使用反射就一定要注意了,警惕大流量帶來(lái)的大量反射類(lèi)加載器創(chuàng)建引發(fā)的頻繁full gc少态。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末城侧,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子彼妻,更是在濱河造成了極大的恐慌嫌佑,老刑警劉巖,帶你破解...
    沈念sama閱讀 211,123評(píng)論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件侨歉,死亡現(xiàn)場(chǎng)離奇詭異屋摇,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)幽邓,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,031評(píng)論 2 384
  • 文/潘曉璐 我一進(jìn)店門(mén)炮温,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人牵舵,你說(shuō)我怎么就攤上這事柒啤。” “怎么了畸颅?”我有些...
    開(kāi)封第一講書(shū)人閱讀 156,723評(píng)論 0 345
  • 文/不壞的土叔 我叫張陵担巩,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我没炒,道長(zhǎng)兵睛,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,357評(píng)論 1 283
  • 正文 為了忘掉前任,我火速辦了婚禮祖很,結(jié)果婚禮上笛丙,老公的妹妹穿的比我還像新娘。我一直安慰自己假颇,他們只是感情好胚鸯,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,412評(píng)論 5 384
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著笨鸡,像睡著了一般姜钳。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上形耗,一...
    開(kāi)封第一講書(shū)人閱讀 49,760評(píng)論 1 289
  • 那天哥桥,我揣著相機(jī)與錄音,去河邊找鬼激涤。 笑死拟糕,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的倦踢。 我是一名探鬼主播送滞,決...
    沈念sama閱讀 38,904評(píng)論 3 405
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼辱挥!你這毒婦竟也來(lái)了犁嗅?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 37,672評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤晤碘,失蹤者是張志新(化名)和其女友劉穎褂微,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體园爷,經(jīng)...
    沈念sama閱讀 44,118評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡宠蚂,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,456評(píng)論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了腮介。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,599評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡端衰,死狀恐怖叠洗,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情旅东,我是刑警寧澤灭抑,帶...
    沈念sama閱讀 34,264評(píng)論 4 328
  • 正文 年R本政府宣布,位于F島的核電站抵代,受9級(jí)特大地震影響腾节,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,857評(píng)論 3 312
  • 文/蒙蒙 一案腺、第九天 我趴在偏房一處隱蔽的房頂上張望庆冕。 院中可真熱鬧,春花似錦劈榨、人聲如沸访递。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,731評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)拷姿。三九已至,卻和暖如春旱函,著一層夾襖步出監(jiān)牢的瞬間响巢,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,956評(píng)論 1 264
  • 我被黑心中介騙來(lái)泰國(guó)打工棒妨, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留踪古,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,286評(píng)論 2 360
  • 正文 我出身青樓靶衍,卻偏偏與公主長(zhǎng)得像灾炭,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子颅眶,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,465評(píng)論 2 348

推薦閱讀更多精彩內(nèi)容