Флаг JVM ClassUnloadingWithConcurrentMark

У меня есть вопрос о флаге ClassUnloadingWithConcurrentMark, так как я нигде не нашел полезной помощи. Если мы используем G1GC, по умолчанию установлено значение true (-XX:+ClassUnloadingWithConcurrentMark). Если я использую флаг -XX:-ClassUnloadingWithConcurrentMark, чтобы отключить выгрузку класса после одновременной отметки G1, где тогда выполняется выгрузка класса (какая фаза)? Я где-то читал, что это происходит, когда полный сборщик мусора активируется, что, если полный сборщик мусора никогда не запускается? У меня проблемы с длинными фазами комментариев - выгрузка в приведенном ниже примере заняла более 3 секунд:

2015-06-08T08:09:16.318+0200: 572818.729: [GC remark 572818.729: [Finalize Marking, 0.0002590 secs] 572818.729: [GC ref-proc, 0.4479462 secs] 572819.177: [Unloading, 3.2004912 secs], 3.6499382 secs]
 [Times: user=0.20 sys=0.08, real=3.64 secs] 

Будет ли мне полезно использовать -XX:-ClassUnloadingWithConcurrentMark для сокращения времени выгрузки классов? Я боюсь, что если я воспользуюсь этой опцией, у меня будет еще больше проблем (например, исключения из памяти,...), если выгрузка класса никогда не произойдет.

РЕДАКТИРОВАТЬ: если мы используем -XX:+ClassUnloadingWithConcurrentMark (опция по умолчанию), запускается ли выгрузка класса каждый раз, когда происходит фаза замечания GC? В журналах у меня есть некоторая GC с причиной GC: Порог GC метаданных, но у других нет этой причины, но выгрузка все еще происходит на этапе примечания. Почему это так?


person user4341206    schedule 08.06.2015    source источник
comment
пожалуйста, не повторяйте вопросы, вы уже задавали то же самое здесь, что просто дублирует усилия людей.   -  person the8472    schedule 08.06.2015
comment
Я задал новый вопрос, потому что еще нет вопроса о ClassUnloadingWithConcurrentMark, и я думаю, что почти никто не заметит тот комментарий, который я задавал ранее.   -  person user4341206    schedule 08.06.2015
comment
Вы могли бы удалить комментарий тогда, чтобы избежать дублирования   -  person the8472    schedule 08.06.2015


Ответы (2)


Боюсь, что если я воспользуюсь этой опцией, у меня будет еще больше проблем

Почему бы вам просто не настроить тестовую среду для таких вещей и не протестировать ее самостоятельно?

В любом случае, как уже было сказано здесь, виртуальная машина выполнит некоторые последние - откажитесь от героизма (1-2 полных GC, полная очистка мягкой ссылки), чтобы убедиться, что ситуация не может быть восстановлена, прежде чем бросать OOM.

Будет ли мне полезно использовать -XX:-ClassUnloadingWithConcurrentMark для сокращения времени выгрузки классов?

Сократит ли это их, я не знаю, наверное, нет. Это то, что вы должны будете попробовать сами. Но это может надолго отсрочить неизбежное.

если мы используем -XX:+ClassUnloadingWithConcurrentMark (опция по умолчанию), запускается ли выгрузка класса каждый раз, когда происходит фаза замечания GC?

да, это было добавлено с помощью JDK-8049421 и флага для его отключения снова с JDK-8051607.

Все, что вам нужно сделать, это найти «выгрузка классов» в системе отслеживания ошибок openjdk и/или в списках рассылки hotspot-gc-dev. Это все публичная информация.


Вместо этого вы можете попробовать установить -XX:MinMetaspaceFreeRatio=20 -XX:MaxMetaspaceFreeRatio=30. Это вызовет выгрузку класса раньше и, как мы надеемся, сократит цикл.

person the8472    schedule 08.06.2015
comment
Я использовал -XX:-ClassUnloadingWithConcurrentMark, но я все еще получаю выгрузку на этапе замечания GC: [замечание GC 58.309: [Завершить маркировку, 0,0004742 секунды] 58.310: [GC ref-proc, 0,0007091 секунды] 58.310: [Выгрузка, 0,0000030 секунд ], 0,0016268 с]. Мне интересно, предназначена ли эта выгрузка для выгрузки класса или это что-то еще (я проверил размер метапространства, когда это произошло, и он вообще не изменился!)? У меня были проблемы с этой выгрузкой (длительные паузы), я думал, что флаг -XX:-ClassUnloadingWithConcurrentMark больше не будет запускать выгрузку, но это все еще происходит. - person user4341206; 09.06.2015
comment
0,0000030 с в чем проблема? - person the8472; 09.06.2015
comment
Да, здесь было 0,0000030 с, но здесь это не важно (низкие паузы выгрузки уже были до первого крупного GC, но затем время выгрузки было намного выше в следующем крупном GC) - вопрос в том, почему выгрузка все еще происходит на фазе замечаний, если я используется флаг -XX:-ClassUnloadingWithConcurrentMark? Если я правильно вас понял, выгрузка не должна была срабатывать здесь, а только тогда, когда срабатывал полный сборщик мусора? - person user4341206; 10.06.2015
comment
но это здесь не важно, да. вашей исходной проблемой было большое время паузы. Я дал вам кое-что для экспериментов. Так что просто проводите свои эксперименты. Если вы не испытываете больших пауз, это успех. - person the8472; 10.06.2015
comment
Как я уже сказал: выгрузка была быстрой в исходных задачах в первых нескольких выгрузках: [выгрузка, 0,0055955 сек], [выгрузка, 0,0074093 сек], [выгрузка, 0,0133418 сек], [выгрузка, 0,0150455 сек], [выгрузка, 0,0290516 сек] , [Выгрузка, 0,9739555 сек], [Выгрузка, 3,2004912 сек] - как видите Выгрузка становилась все медленнее и медленнее. Поэтому я хочу иметь классы выгрузки, когда запускается полный сборщик мусора, но у меня все еще есть это на этапе замечаний (если эта выгрузка вообще такая же, как выгрузка класса). Не могли бы вы ответить на отредактированную часть вопроса, если вы, возможно, знаете ответ. Спасибо. - person user4341206; 10.06.2015
comment
Спасибо за ваш отредактированный ответ, поэтому эта опция еще не работает, она будет доступна в JDK9. Так что -XX:-ClassUnloadingWithConcurrentMark бесполезен. - person user4341206; 10.06.2015
comment
Теперь я смущен. В JDK-8051607 (Добавить флаг для отключения выгрузки класса после одновременной отметки G1) сказано, что это перенесено в JDK 9, поэтому я предполагаю, что этот флаг еще недоступен. Если я использую флаг o -XX:-ClassUnloadingWithConcurrentMark, он тоже не работает (выгрузка все еще находится в стадии замечаний). - person user4341206; 10.06.2015
comment
Вы не смотрели на соответствующую ошибку. - person the8472; 10.06.2015

G1 выполняет выгрузку класса во время фазы замечания STW, это поведение по умолчанию. Вы не можете предотвратить выгрузку класса, потому что это в конечном итоге приведет к ошибкам «Недостаточно памяти».

Единственный способ смягчить эту проблему — изменить код, чтобы прекратить использование динамической генерации классов.

person Ayoross    schedule 25.04.2019