Поўны GC становіцца вельмі частым

У мяне ёсць вэб-дадатак Java працуе на адным TOMCAT экземпляры. У гадзіны пік вэб-дадатак абслугоўвае каля 30 старонак у секунду і звычайна каля 15.

Мая асяроддзе:

O/S: SUSE Linux Enterprise Server 10 (x86_64)
RAM: 16GB

server: Tomcat 6.0.20
JVM: Java HotSpot(TM) 64-Bit Server VM 1.6.0_14
JVM options:
CATALINA_OPTS="-Xms512m -Xmx1024m -XX:PermSize=128m -XX:MaxPermSize=256m
               -XX:+UseParallelGC
               -Djava.awt.headless=true
               -verbose:gc -XX:+PrintGCDetails -XX:+PrintGCTimeStamps"
JAVA_OPTS="-server"

Праз пару дзён безотказно працы Поўны GC пачынае адбываецца часцей, і гэта становіцца сур'ёзнай праблемай даступнасці прыкладання. Пасля ката перазагрузка праблема знікне, але, вядома, вяртаецца пасля 5 да 10 або 30 дзён (не пагадзіцца).

The Full GC log before and after a restart is at http://pastebin.com/raw.php?i=4NtkNXmi

Гэта паказвае часопіс перад перазапускам на 6,6 дзён бесперабойнай працы, дзе прыкладанне пакутуе, таму што Full GC патрабуецца 2,5 секунды і адбываецца кожныя 6 секунд ~.

Затым ён паказвае часопіс толькі пасля перазагрузкі, дзе Full GC толькі адбыўся праз кожныя 5-10 хвілін.

У мяне ёсць два звалках, выкарыстоўваючы jmap -dump: Фармат = Ь, файл = dump.hprof PID , калі поўны ШС дзе сустракаецца (я не ўпэўнены, ці ёсць я іх зусім правільна, калі поўная GC адбывалася або паміж 2 Поўны ШС) і адкрылі іх у http://www.eclipse.org/mat/</а>, але не атрымаць нічога карыснага ў Leak падазраваных:

Звярніце ўвагу, што я ніколі не атрымаць OutOfMemoryError.

Любыя ідэі аб тым, дзе я павінен шукаць далей?

11
Шмат новых і выкінутых прадметаў.
дададзена аўтар Thorbjørn Ravn Andersen, крыніца
а поўны GC на вялікую кучу зойме больш часу, таму што ёсць больш рэчаў, каб сабраць, але эксперыментаваць з вялікімі значэннямі максімальнага памеру кучы можа паказаць, калі ваша дадаткам проста трэба больш прасторы ў цэлым.
дададзена аўтар matt b, крыніца
таксама @cherouvim вы бачылі oracle.com/technetwork/ Java/JavaSE/дс-цюнінг-6-140523.html ? можа быць карысным.
дададзена аўтар matt b, крыніца
Калі ў вас ёсць 16 Гб аператыўнай памяці на сэрвэры, чаму не выкарыстоўваць большы максімальны памер кучы (-Xmx)?
дададзена аўтар matt b, крыніца
«Я ніколі не атрымліваў OutOfMemoryError» - не <�я> усе </я> памяць выкарыстоўваецца, але поўны GC адбываецца таму, што старое пакаленне поўна. Вылучаючы больш памяці будзе трымаць аб'екты ў маладым гене даўжэй - больш шанцаў атрымаць ачышчаны ад нязначнай калекцыі/менш шанцаў атрымаць падвышэнне па службе.
дададзена аўтар symcbean, крыніца
Вы можаце прайграць паводзіны ў асяроддзі тэставання? Магчыма, з некаторым нагрузачным тэставаннем. Я адладжаная паводзіны, як гэта раней, але звычайна з ШМАТ дапамогай профайлер (які будзе забіваць ваш сервер у вытворчым акр).
дададзена аўтар pcalcao, крыніца
@symcbean: мае сэнс. Ці будзе паспрабаваць павялічыць кучу і пераацэньваць.
дададзена аўтар cherouvim, крыніца
б @ Matt: Гэта вырашыла яго. Калі ласка, размясціць яго ў адказ, так што я магу прыняць.
дададзена аўтар cherouvim, крыніца
@svaor: Я пагляджу. Гукі карысна. дзякуй!
дададзена аўтар cherouvim, крыніца
б @ Matt: Я буду старацца 2GBs наступны раз і паглядзець, што адбываецца.
дададзена аўтар cherouvim, крыніца
@pcalcao: Я зрабіў гэта ў мінулым, але гэта не адпавядае. На поўным дросельнай стрэс-тэставанні з JMeter Я гэта адбываецца адзін раз у 6 дзён, а другі раз у 20 дзён (!).
дададзена аўтар cherouvim, крыніца
Я ніколі не атрымліваў OutOfMemoryError, так што я падумаў, што, так як дадатак можа працаваць, то гэта нармальна. Акрамя таго, я прачытаў, што дае занадта шмат памяці для віртуальнай машыны Java будзе рабіць Full GC павольней. Гэта праўда?
дададзена аўтар cherouvim, крыніца
Як я памятаю зацьменне мат можа параўнаць два дампы адной віртуальнай машыны Java сесіі. Гэта можа паказаць вам розніцу сітуацыі, калі праблема яшчэ не існуе яшчэ і сітуацыя з часта Full ШС.
дададзена аўтар svaor, крыніца

4 адказы

Калі мы гэтае пытанне, мы ў канчатковым выніку адсочвалі яго ўніз, каб маладое пакаленне занадта мала. Хоць мы далі шмат барана маладое пакаленне не было дадзена гэта ладная доля.

Гэта азначала, што невялікія калекцыі смецця будуць адбывацца часцей і выклікаў некаторыя маладыя аб'екты, якія будуць перамешчаныя ў штатны пакаленне, якое азначае больш буйныя калекцыі смецця таксама.

Паспрабуйце выкарыстоўваць -XX: NewRatio з даволі нізкім значэннем (скажам, 2 ці 3) і паглядзець, калі гэта дапамагае.

Больш падрабязную інфармацыю можна знайсці .

6
дададзена

Я перайшоў з -Xmx1024m на -Xmx2048m і праблема сышла. Цяпер у мяне ёсць 100 дзён безотказно працы.

4
дададзена

Што можа адбывацца ў вашым выпадку з'яўляецца тое, што ў вас ёсць шмат аб'ектаў, якія жывуць трохі даўжэй, чым NewGen жыццёвага цыклу. Калі якое перажыло прастору занадта мала, яны ідуць проста да OldGen. <�Код> -XX: + PrintTenuringDistribution можа даць некаторае ўяўленне. Ваш NewGen з'яўляецца дастаткова вялікім, таму паспрабуйце паменшыць SurvivorRatio .

Акрамя таго, JConsole, верагодна, забяспечыць больш візуальнае разуменне таго, што адбываецца з вашай памяці, паспрабуйце.

3
дададзена

Акрамя налады розных варыянтаў JVM я таксама хацеў бы прапанаваць, каб перайсці на больш новы рэліз віртуальнай машыны, так як пазнейшыя версіі маюць значна лепш наладжаную зборшчыка смецця (таксама без спробы новага эксперыментальнага).

Акрамя гэтага, таксама, калі гэта (часткова) дакладна, што прызначаючы больш аператыўнай памяці для віртуальнай машыны Java можа павялічыць час, неабходнае для выканання GC ёсць кропка выбару паміж выкарыстаннем ўсяго 16 Гб памяці і павялічыць занятак памяці, так што вы можаце паспрабаваць падвойныя ўсе значэнні, пачаць

Xms1024m -Xmx2048m -XX: PermSize = 256m -XX: MaxPermSize = 512m

прывітанне

Massimo

2
дададзена
OK, абновіць JVM, а таксама. Дзякуючы.
дададзена аўтар cherouvim, крыніца
Так, часопісы паказваюць PSPermGen з каля ~ 64 МБ, якія я думаю, гэта агульная памер загружанай клас: JVM, ката, бібліятэка і маё прыкладанне. Дакладна?
дададзена аўтар cherouvim, крыніца
Я паспрабую. Але не maxperm 512 трохі занадта шмат? Экземпляр кот працуе толькі 1 дадатак з каля 40 пастаянных (Hibernate) асоб і ня спружыннай структуры. Няма пераразмеркаванне не адбываецца на гэтым ката, толькі выключэнне/запуск.
дададзена аўтар cherouvim, крыніца
Можа быць, мае прапанаваныя параметры былі проста проста здагадка. Я хацеў бы паказаць на абнаўленне віртуальнай машыны Java ў якасці лепшай рэчы, каб паспрабаваць, у нас былі падобныя праблемы (і іншых з іх таксама), і яны сышлі, калі мы абнавілі Java для абнаўлення 27. Апошняе з'яўляецца абнаўленнем 29, але ў нас былі некаторыя праблемы з ім.
дададзена аўтар user1133275, крыніца