Узкое место в куче Java - как определить причину? - PullRequest
3 голосов
/ 26 июля 2010

У меня работает J2EE-проект на JBoss с максимальным размером кучи 2048 м, что дает странные результаты при нагрузочном тестировании.Я провел сравнительный анализ использования кучи и процессора и получил следующие результаты (серия 1 - использование кучи, серия 2 - использование процессора):

http://i29.tinypic.com/m9ul1e.png

Кажется, что кучапри правильном использовании и правильном сборе мусора вокруг A. Однако, когда он добирается до B, появляется какое-то узкое место, так как имеется свободное пространство в куче, но оно никогда не нарушает эту воображаемую линию.В то же время, в C, использование процессора резко падает.В течение этого периода мы также получаем «OutOfMemoryError (превышен лимит накладных расходов GC)», который не имеет большого смысла для меня, поскольку есть доступное пространство в куче.

Я предполагаю, что существует какое-то узкое место, ночто именно я даже не могу себе представить.Как бы вы посоветовали найти причину проблемы?Я профилировал использование памяти и заметил, что существует довольно много экземпляров одного класса (около миллиона), но общий размер этих экземпляров довольно мал (около 50 МБ, если я правильно помню).

Редактировать: Сервер выделен для этого приложения, и использование ЦП указано только для JVM (не должно быть значительного использования ЦП вне JVM).Использование памяти только для кучи, оно не включает пространство permgen.Эта проблема воспроизводима.Моя главная проблема заключается в том, чтобы ограничить предел B, для которого я еще не нашел правдоподобного объяснения.

Вывод: Оказывается, это было вызвано тем, что куча долго выполняющихся SQL-запросовназывается одновременно.Возвращенные ResultSets также были очень большими, возможно, объясняя OOME.У меня до сих пор нет разумного объяснения, почему, по-видимому, существует определенный предел в B.

Ответы [ 2 ]

2 голосов
/ 26 июля 2010

Из сообщения об ошибке видно, что JVM использует алгоритм параллельного мусорщика для сбора мусора. Сообщение сбрасывается вместе с ошибкой OOME, когда много времени тратится на сборку мусора, но не много кучи восстанавливается .

В документе Sun не указывается, следует ли считать 98% от общего времени, потребляемого процессором, как 98% загрузки ЦП процесса или самого ЦП. В любом случае я должен сделать следующие выводы (с ограниченной информацией):

  • У сборщика мусора или процесса JVM недостаточно загрузки ЦП, скорее всего, из-за того, что другие процессы одновременно используют ЦП.
  • У сборщика мусора недостаточно загрузки ЦП, поскольку он является потоком с низким приоритетом, и другой поток, интенсивно использующий память (но не интенсивно использующий ЦП), в JVM выполняет работу в то же время, что приводит к отказу выделить память.

Исходя из вышеизложенных выводов (все, одно или ни одно из них может быть правдой), было бы целесообразно сопоставить полученный график с поведением приложения во время выполнения для пользователей. Другими словами, вам может быть полезно определить, запускаются ли другие процессы (когда возникает ваша проблема) или какая часть приложения работает (опять же, когда возникает проблема).

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

РЕДАКТИРОВАТЬ: Если проблема возникает периодически и может быть воспроизведена, это может оказаться утечка памяти, в противном случае (т.е. это происходит спорадически), вам лучше настроить алгоритм GC или даже меняя его.

0 голосов
/ 26 июля 2010

Если я хочу знать, где «узкие места», я просто получаю несколько стеков. Там нет необходимости удивляться и угадывать и играть в детектива. Они просто скажут вам.

Обычно проблемы с памятью и проблемы с производительностью идут рука об руку, поэтому, если вы исправите проблемы с производительностью, вы также исправите проблемы с памятью (хотя и не наверняка).

...