2014-01-22 5 views
20

Я изучаю понимание того, как распределение памяти работает в JVM. Я пишу приложение, в котором я получаю исключение из памяти: исключения в Heap Space.Понимание распределения памяти JVM и Java Недостаточно памяти: пустое пространство

Я понимаю, что могу передавать аргументы виртуальной машины, такие как Xms и Xmx, в область кучи, которую JVM выделяет для текущего процесса. Это одно из возможных решений проблемы, или я могу проверить свой код на утечки памяти и исправить проблему там.

Мои вопросы:

1) Как JVM фактически выделяет память для себя? Как это связано с тем, как ОС связывает доступную память с JVM? Или, в общем, как распределяется память для любого процесса?

2) Как виртуальная память вступает в игру? Предположим, у вас есть система с 32 ГБ физической памяти, и вы выделяете все 32 ГБ для своего Java-процесса. Предположим, что ваш процесс фактически потребляет все 32 ГБ памяти, как мы можем заставить процесс использовать виртуальную память вместо того, чтобы работать в исключениях OOM?

Спасибо.

+2

Если вы не использовали профайлер еще, как VisualVM, сделать это. Это даст вам много информации о том, что происходит внутри вашего приложения, например, какие объекты не собираются в мусор и когда выделяется память. – Kyle

ответ

20

Как виртуальная машина на самом деле выделяет память для себя?

Для кучи выделяет одну большую conitnous область памяти максимального размера. Первоначально это виртуальная память, но со временем она становится реальной памятью для используемых частей под управлением ОС

Как это связано с тем, как ОС связывает доступную память с JVM?

JVM не имеет понятия о свободной памяти в ОС.

Или, в общем, как распределяется память для любого процесса на самом деле?

В целом, он использует malloc и бесплатно.

Как виртуальная память вступает в игру?

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

Предположим, у вас есть система с 32 ГБ физической памяти, и вы выделяете все 32 ГБ для вашего Java-процесса.

Вы не можете. ОС требуется некоторая память, и в других случаях будет память. Даже в JVM куча - это только часть используемой памяти. Если у вас есть 32 ГБ памяти, я предлагаю использовать максимум в 20 ГБ.

Давайте предположим, что ваш процесс фактически потребляет всего 32 Гб памяти,

Скажем, у вас есть 48 ГБ, и вы начинаете процесс, который использует 32 ГБ оперативной памяти.

Как мы можем заставить процесс использовать виртуальную память вместо использования в исключениях OOM?

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

Вы можете использовать больше памяти, чем физическое, используя аккуратную память. Однако управляемая память должна находиться в физической памяти, поэтому, если вам нужна куча 32 ГБ, купите 64 ГБ основной памяти.

+0

Вопрос: не могли бы вы рассказать мне, почему JVM_outOfMemory - ошибка, а не исключение. –

+5

@TusharPandey Из Javadoc 8 для ошибки 'Ошибка - это подкласс Throwable, который указывает на серьезные проблемы, которые разумное приложение не должно пытаться поймать. Большинство таких ошибок являются ненормальными условиями. «Вы не хотели бы« catch (Exception e) »улавливать такие ошибки. –

2
  1. The JVM выделяет память кучи Java от операционной системы, а затем управляет кучи для приложения Java. Когда приложение создает новый объект , JVM выделяет смежную область памяти кучи на . Объект в куче, на который ссылается какой-либо другой объект , является «живым» и остается в куче, если он продолжает оставаться . Объекты, на которые больше не ссылаются, - это мусор, и можно удалить из кучи, чтобы вернуть место, которое они занимают. JVM выполняет сбор мусора (GC) для удаления этих объектов, реорганизация объектов, оставшихся в куче.
    Источник: http://pubs.vmware.com/vfabric52/index.jsp?topic=/com.vmware.vfabric.em4j.1.2/em4j/conf-heap-management.html

  2. В системе, использующей виртуальную память, физическая память делится на одинакового размера страниц. Память, адресованная процессом, также разделяется на логические страницы того же размера. Когда процесс ссылается на адрес памяти , диспетчер памяти извлекает с диска страницу, на которой содержит ссылочный адрес, и помещает его в свободную физическую страницу в ОЗУ.

Источник: http://searchstorage.techtarget.com/definition/virtual-memory

6

Виртуальная машина Java (или в этом отношении любого процесса), который хочет выделить память будет вызывать C выполнения 'malloc' функцию. Эта функция поддерживает память кучи времени выполнения C. Он, в свою очередь, получает память из ядра операционной системы - функция, используемая для этого, зависит от платформы; в Linux он может использовать системные вызовы brk or sbrk.

Как только память была получена JVM, она управляет самой памятью, выделяя ее части различным объектам, созданным запущенной программой.

Виртуальная память полностью обрабатывается ядром операционной системы.Ядро управляет отображением страниц физической памяти в адресное пространство различных процессов; если физическая память меньше, чем требуется всем процессам в системе, то ядро ​​ОС поменяет часть на диск.

Вы не можете (и не должны) принудительно использовать процессы для использования виртуальной памяти. Он прозрачен для вашего процесса.

Если вы получаете «из памяти» ошибки, то причины могут быть следующие:

  1. Пределы JVM превышены. Они контролируются различными аргументами командной строки и/или свойствами, указанными в вашем вопросе.

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

  3. Большинство ОС имеют возможности администратора ограничить объем памяти, потребляемой процессом - например, в Linux - системный вызов setrlimit и/или команду оболочки ulimit, обе из которых устанавливают пределы, которые ядро ​​будет наблюдать , Если процесс запрашивает больше памяти, чем разрешено ограничениями, попытка не удастся (обычно это приводит к сообщению из памяти).

Смежные вопросы