2011-03-16 127 views
6

我有一個應用程序,導致創建大量的垃圾。首先(幾乎是一個)標準是低GC暫停時間。我使用visualgc工具(和gc日誌)嘗試不同的GC參數。最佳參數如下。Java CMS GC行爲

-XX:+ UseConcMarkSweepGC

-Xmx1172M

-Xms600M

-XX:+ UseParNewGC

-XX:新尺寸= 150M

我的申請使用Java 1.6.0_21在SunOS 10上運行。硬件是2個CPU四核(uname -X結果是numCPU = 8)。

問題是

觀察GC行爲,新創建的對象上伊甸園空間,直到伊甸園已滿。當伊甸園空間完整的GC運行時,清除垃圾,如果對象沒有死亡複製到舊版本(我'丟棄'從'&'到'空格),類似的舊版本已滿,GC運行CMS併發階段並清除舊的-gen空間。 CMS的某些部分是停止世界(暫停時間)。這是一個循環。

  1. 以上scenerio是真的嗎?
  2. GC清理舊版空間後,沒有足夠的空間擴展舊版空間(XMS和XMS值不同)?
  3. 完整的GC操作何時開始?如何決定?
  4. CMS併發階段持續時間取決於伊甸園空間大小,實際上我的預期是,伊甸園空間不影響CMS併發階段持續時間。與CMS-併發階段上的eden空間相關的GC發生了什麼?
  5. 還有什麼建議我最大限度地減少暫停時間?事實上,我覺得最有價值的答案:)

感謝

回答

10

您不能忽略使用CMS時的生存空間。 CMS不是一個壓縮收集器,這意味着如果你(或JVM)獲得了錯誤的持續時間門檻,那麼你將慢慢地將對象放入終身,這將增加終止片段的速度,這將導致CMS被強制的時間,因爲它沒有足夠的連續可用空間可用於處理來自倖存者空間的促銷活動,從而在沒有預先警告的情況下強制執行完整的gc循環,因此這是1 STW暫停時的全部內容。這需要多長時間取決於你的堆的大小,但有一件事情很可能,它會比正常的伊甸園收藏時間長數倍。

還有其他一些事情要注意這裏;

  1. STW暫停並不僅僅來自CMS,他們來自年輕代收集太
  2. CMS有2個STW階段(標記,備註)和3-4併發階段,第一階段STW(馬克)嚴格單線程這可能會導致問題
  3. 您可以控制沒有線程處理併發階段
  4. 您需要了解對象是如何長的壽命一般爲(在此here樣本的討論),這可能意味着使用-XX:+PrintTenuringDistribution或你可以像你做的那樣用visualgc來觀看它
  5. 然後,您可以調整這個與-XX:SurvivorRatio控制相對生存空間的大小伊甸園-XX:MaxTenuringThreshold來控制它的終身
  6. -XX:CMSInitiatingOccupancyFraction前一個對象可以多久生存的一個年輕的集合,可用於指導CMS至於如何全它需要開始之前CMS階段(得到這個錯誤,你會暫停嚴重)

最終你需要了解哪些收集器暫停,有多久,多久以及是否有任何異常暫停的原因。然後,您需要將其與每一代的大小進行比較,以查看是否可以調整參數以最大限度地減少暫停的次數(和/或持續時間)。

請記住,由於需要長時間運行測試以確定它是否會隨着時間的推移而惡化,因此可能會造成時間縮短。此外,如果沒有可重複的自動化工作負載,幾乎無法得出關於您是否真正改進了事情的確切結論。

內部總結信息的一個很好的來源是Jon Masamitsu's blog。另一個很好的介紹是GC Tuning in the HotSpot Java VM

+0

經過20個小時,gc記錄了大約5倍的完整gc運行,我猜想一些線索爲什麼運行Full GC是「升級失敗」和「併發模式失敗」。在google上搜索這些原因。稍後,爲「促銷失敗」增加舊一代大小,併爲「併發模式失敗」設置最小值XX:CMSInitiatingOccupancyFraction。我會嘗試設置XX:CMSInitiatingOccupancyFraction小值(如30或60)並增加堆。我會分享測試結果。 – 2011-03-17 09:59:23

+0

促銷失敗通常是我提到的碎片問題,它強制一個非併發的完整gc。你需要檢查你的持續時間門檻並適當調整他們的大小。將初始佔用設置爲較低值(默認值爲70 iirc)意味着更頻繁的完整gcs,這些gcs不會做太多,這並不好。你甚至有很多這樣的生活很長一段時間?你可能會發現一個巨大的伊甸園,一個小的終身制是一個不錯的選擇。 – Matt 2011-03-17 10:09:36

+0

較低的啓動佔用值是CMS更常見的,但沒有問題。最大的問題STW,而2-3秒。吞吐量或0.0x秒STW對我來說不是問題。我已經嘗試過大的伊甸園大小,但是STW的持續時間增加了:(如何設置併發階段的線程數? – 2011-03-17 12:03:38

2

,以儘量減少GC的影響,最好的辦法是minise你創建對象的對象的數量。這並不總是很容易做到或總體上最好的解決方案,但它會減少GC暫停。

如果你不能生產更少的物品,儘量讓它們足夠短暫,足夠大的伊甸園空間不要離開伊甸園的空間。 (或做很長的生活和再利用)

  1. 有三個空格擔心這裏,伊甸 - >倖存者 - >終身http://www.oracle.com/technetwork/java/gc-tuning-5-138395.html

  2. 的GC努力,以確保有足夠的自由一個完整的GC後空間和-ms-mx選項做控制,他們將有多大(前者素有-Xms-Xmx

  3. 當終身空間已滿,或suvivor空間枯竭型全GC啓動(例如,有o從eden空間複製的許多對象)或者CMS desices現在是嘗試並行清理的一個很好的方面。

  4. CMS只清理終身空間。

  5. 查看我以前的答案。

+0

我同意你關於增加伊甸園空間的決定。我已經嘗試了不同的newSize參數,並檢查從gc日誌中暫停時間該行包括「重新掃描」。更少的newSize值導致更少的暫停時間。我的推論中有3個不同的newSize值是平行的。 – 2011-03-16 09:17:24