Недавно я столкнулся с этой ошибкой в моем веб-приложении:
java.lang.OutOfMemoryError: пространство PermGen
Это типичное приложение Hibernate / JPA + IceFaces / JSF, работающее на Tomcat 6 и JDK 1.6. По-видимому, это может произойти после повторного развертывания приложения несколько раз.
Что вызывает это и что можно сделать, чтобы этого избежать? Как мне решить проблему?
Ответы:
Решением было добавить эти флаги в командную строку JVM при запуске Tomcat:
Это можно сделать, выключив службу tomcat, затем перейдя в каталог Tomcat / bin и запустив tomcat6w.exe. На вкладке «Java» добавьте аргументы в поле «Параметры Java». Нажмите «ОК» и перезапустите сервис.
Если вы получили сообщение об ошибке, указанная служба не существует как установленная служба, вы должны запустить:
где servicename - это имя сервера в соответствии с services.msc
Источник: комментарий orx к Agile Ответам Эрика .
источник
Лучше попробуй
-XX:MaxPermSize=128M
, чем-XX:MaxPermGen=128M
.Я не могу сказать точное использование этого пула памяти, но это связано с количеством классов, загруженных в JVM. (Таким образом, разрешение выгрузки классов для tomcat может решить эту проблему.) Если ваши приложения генерируют и компилируют классы на ходу, более вероятно, что потребуется пул памяти больше, чем по умолчанию.
источник
Ошибки PermGen сервера приложений, возникающие после нескольких развертываний, вероятнее всего вызваны ссылками, содержащимися в контейнере на загрузчики классов ваших старых приложений. Например, использование пользовательского класса уровня журнала приведет к тому, что ссылки будут храниться загрузчиком классов сервера приложений. Вы можете обнаружить эти утечки между классами загрузчика, используя современные (JDK6 +) инструменты анализа JVM, такие как jmap и jhat, чтобы посмотреть, какие классы по-прежнему хранятся в вашем приложении, и изменить или исключить их использование. Обычно подозреваемыми являются базы данных, средства ведения журнала и другие библиотеки базового уровня.
См. Утечки Classloader: страшное исключение "java.lang.OutOfMemoryError: PermGen space" , и особенно его последующий пост .
источник
Распространенные ошибки, которые делают люди, - это думать, что куча пространства и пространство permgen одно и то же, что вовсе не так. У вас может быть много свободного места в куче, но все равно может не хватить памяти в permgen.
Распространенными причинами OutofMemory в PermGen является ClassLoader. Всякий раз, когда класс загружается в JVM, все его метаданные вместе с Classloader хранятся в области PermGen, и они будут собираться мусором, когда загрузчик Classloader, который их загрузил, готов для сбора мусора. В случае, если Classloader имеет утечку памяти, все загруженные им классы останутся в памяти и вызовут излишнюю память permGen, если вы повторите это пару раз. Классическим примером является Java.lang.OutOfMemoryError: PermGen Space в Tomcat .
Теперь есть два способа решить эту проблему:
1. Найти причину утечки памяти или, если есть утечка памяти.
2. Увеличьте размер пространства PermGen с помощью параметра JVM
-XX:MaxPermSize
и-XX:PermSize
.Вы также можете проверить 2 Решение Java.lang.OutOfMemoryError в Java для более подробной информации.
источник
-XX:MaxPermSize and -XX:PermSize
?? Я не могу найтиcatalina.bat
. Моя версия кота есть5.5.26
.Используйте параметр командной строки
-XX:MaxPermSize=128m
для Sun JVM (очевидно, заменив 128 на любой нужный вам размер).источник
Попробуйте,
-XX:MaxPermSize=256m
и если это не устранено, попробуйте-XX:MaxPermSize=512m
источник
XX:MaxPermSize=1024m
:)Я добавил
-XX: MaxPermSize = 128m
(вы можете поэкспериментировать, который работает лучше всего) в VM Arguments, так как я использую Eclipse Ide. В большинстве JVM значение PermSize по умолчанию составляет около 64 МБ, что приводит к нехватке памяти, если в проекте слишком много классов или огромное количество строк.Для затмения это также описано в ответе .
ШАГ 1 : Двойной щелчок по серверу Tomcat на вкладке Servers
ШАГ 2 : Open запуск Conf и добавить
-XX: MaxPermSize = 128m
в конце существующих заданы параметры виртуальной машины .источник
Я бился головой об этой проблеме, когда развертывал и развертывал сложные веб-приложения, и думал, что добавлю объяснение и свое решение.
Когда я развертываю приложение в Apache Tomcat, для него создается новый ClassLoader. ClassLoader затем используется для загрузки всех классов приложения, а при отмене развертывания все должно пройти хорошо. Однако на самом деле все не так просто.
Один или несколько классов, созданных в течение жизни веб-приложения, содержат статическую ссылку, которая где-то вдоль линии ссылается на ClassLoader. Поскольку ссылка изначально является статической, никакие сборщики мусора не очистят эту ссылку - ClassLoader и все загруженные классы останутся здесь.
И после нескольких повторных развертываний мы сталкиваемся с ошибкой OutOfMemoryError.
Теперь это стало довольно серьезной проблемой. Я мог бы удостовериться, что Tomcat перезапускается после каждого повторного развертывания, но это приводит к отключению всего сервера, а не просто повторного развертывания приложения, что часто неосуществимо.
Поэтому вместо этого я собрал решение в коде, которое работает на Apache Tomcat 6.0. Я не тестировал ни на каких других серверах приложений и должен подчеркнуть, что, скорее всего, это не сработает без изменений на любом другом сервере приложений .
Я также хотел бы сказать, что лично я ненавижу этот код, и что никто не должен использовать его как «быстрое исправление», если существующий код может быть изменен для использования надлежащих методов выключения и очистки . Единственный раз, когда это следует использовать, это если есть внешняя библиотека, от которой зависит ваш код (в моем случае это был клиент RADIUS), который не предоставляет средства для очистки своих собственных статических ссылок.
Во всяком случае, с кодом. Это следует вызывать в тот момент, когда приложение развертывается - например, метод уничтожения сервлета или (лучший подход) метод contextDestroyed ServletContextListener.
источник
java.lang.OutOfMemoryError: PermGen
Пространство сообщений указывает на то, что площадь Постоянного Поколение в памяти будет исчерпан.Любым Java-приложениям разрешено использовать ограниченный объем памяти. Точный объем памяти, который может использовать ваше конкретное приложение, указывается при запуске приложения.
Память Java разделена на различные области, которые можно увидеть на следующем рисунке:
Metaspace: рождается новое пространство памяти
JVK HotSpot JDK 8 теперь использует собственную память для представления метаданных класса и называется Metaspace; похож на Oracle JRockit и IBM JVM.
Хорошая новость заключается в том, что это означает, что больше не будет
java.lang.OutOfMemoryError: PermGen
проблем с пространством и вам больше не нужно настраивать и отслеживать это пространство памяти с помощью Java_8_Download или выше.источник
1) Увеличение объема памяти PermGen
Первое, что можно сделать, - это увеличить размер кучи постоянного поколения. Это невозможно сделать с помощью обычных аргументов JVM –Xms (установить начальный размер кучи) и –Xmx (установить максимальный размер кучи), поскольку, как уже упоминалось, пространство кучи постоянного поколения полностью отделено от обычного пространства кучи Java, и эти аргументы устанавливаются пространство для этого обычного пространства кучи Java. Однако есть аналогичные аргументы, которые можно использовать (по крайней мере для jvms Sun / OpenJDK), чтобы увеличить размер кучи постоянного поколения:
По умолчанию это 64м.
2) Включить Sweeping
Еще один способ позаботиться об этом навсегда - разрешить выгрузку классов, чтобы ваш PermGen никогда не заканчивался:
Такие вещи работали для меня магией в прошлом. Одна вещь, тем не менее, есть существенный компромисс производительности при их использовании, так как развертки permgen будут делать как дополнительные 2 запроса на каждый запрос, который вы делаете, или что-то в этом роде. Вам нужно будет сбалансировать свое использование с компромиссами.
Вы можете найти детали этой ошибки.
http://faisalbhagat.blogspot.com/2014/09/java-outofmemoryerror-permgen.html
источник
Кроме того, вы можете переключиться на JRockit, который обрабатывает permgen иначе, чем Sun JVM. Как правило, он также имеет лучшую производительность.
http://www.oracle.com/technetwork/middleware/jrockit/overview/index.html
источник
java.lang.OutOfMemoryError: There is insufficient native memory
вместо этого.У меня была проблема, о которой мы здесь говорим, мой сценарий eclipse-helios + tomcat + jsf, и вы делали развертывание простого приложения для tomcat. Я показывал здесь ту же проблему, решил ее следующим образом.
В eclipse перейдите на вкладку серверов двойным щелчком мыши по зарегистрированному серверу в моем случае tomcat 7.0, он откроет для моего файлового сервера общие регистрационные данные. В разделе «Общая информация» перейдите по ссылке «Открыть конфигурацию запуска» , это откроет выполнение параметров сервера на вкладке Аргументы в аргументах виртуальной машины, добавленных в конце этих двух записей.
и готово.
источник
Самый простой ответ в наши дни - использовать Java 8.
Он больше не резервирует память исключительно для пространства PermGen, позволяя памяти PermGen смешиваться с обычным пулом памяти.
Имейте в виду, что вам придется удалить все нестандартные
-XXPermGen...=...
параметры запуска JVM, если вы не хотите, чтобы Java 8 жаловалась, что они ничего не делают.источник
В текстовой области Параметры Java добавьте эту строку:
источник
Ошибка Пермского пространства возникает из-за использования большого пространства, а не пространства, предоставленного jvm для выполнения кода.
Лучшее решение этой проблемы в операционных системах UNIX - изменить некоторые настройки в файле bash. Следующие шаги решают проблему.
Запустите команду
gedit .bashrc
на терминале.Создайте
JAVA_OTPS
переменную со следующим значением:Сохраните файл bash. Запустите команду exec bash на терминале. Перезагрузите сервер.
Я надеюсь, что этот подход будет работать на вашу проблему. Если вы используете версию Java ниже 8, эта проблема иногда возникает. Но если вы используете Java 8, проблема никогда не возникает.
источник
Увеличение размера постоянной генерации или настройка параметров GC НЕ поможет, если у вас есть реальная утечка памяти. Если ваше приложение или какая-либо сторонняя библиотека, которую оно использует, пропускает загрузчики классов, единственное реальное и постоянное решение - найти эту утечку и исправить ее. Есть ряд инструментов, которые могут вам помочь, одним из последних является Plumbr , который только что выпустил новую версию с необходимыми возможностями.
источник
Также, если вы используете log4j в своем веб-приложении, проверьте этот параграф в документации log4j .
Кажется, что, если вы используете
PropertyConfigurator.configureAndWatch("log4j.properties")
, вы вызываете утечки памяти при удалении вашего веб-приложения.источник
У меня есть комбинация Hibernate + Eclipse RCP, пробовал использовать
-XX:MaxPermSize=512m
и,-XX:PermSize=512m
кажется, это работает для меня.источник
Set
-XX:PermSize=64m -XX:MaxPermSize=128m
. Позже вы также можете попробовать увеличитьMaxPermSize
. Надеюсь, это сработает. То же самое работает для меня. Установка толькоMaxPermSize
не работала для меня.источник
Я попробовал несколько ответов, и единственной вещью, которая наконец сделала работу, была эта конфигурация для плагина компилятора в pom:
надеюсь, это поможет
источник
JRockitрешил это и для меня; Тем не менее, я заметил, что время перезапуска сервлета было намного хуже, поэтому, хотя он был лучше в производстве, это было своего рода тормозом в развитии.
источник
Конфигурация памяти зависит от характера вашего приложения.
Что делаешь?
Какое количество транзакций обработано?
Сколько данных вы загружаете?
и т.п.
и т.п.
так далее
Возможно, вы могли бы профилировать свое приложение и начать очистку некоторых модулей из вашего приложения.
Tomcat имеет горячее развертывание, но он потребляет память. Попробуйте перезапустить ваш контейнер время от времени. Кроме того, вам нужно знать объем памяти, необходимый для работы в производственном режиме, это, кажется, хорошее время для этого исследования.
источник
Они говорят, что последняя версия Tomcat (6.0.28 или 6.0.29) намного лучше справляется с задачей повторного развертывания сервлетов .
источник
Я столкнулся с точно такой же проблемой, но, к сожалению, ни одно из предложенных решений не помогло мне. Проблема не возникала во время развертывания, и я не делал ни одного горячего развертывания.
В моем случае проблема возникала каждый раз в одно и то же время во время выполнения моего веб-приложения при подключении (через спящий режим) к базе данных.
Эта ссылка (также упоминавшаяся ранее) предоставила достаточно внутренностей для решения проблемы. Перемещение jdbc- (mysql) -драйвера из WEB-INF в папку jre / lib / ext /, похоже, решило проблему. Это не идеальное решение, так как обновление до новой JRE потребует переустановки драйвера. Другим кандидатом, который может вызвать аналогичные проблемы, является log4j, так что вы можете переместить и этот.
источник
Первый шаг в таком случае - проверить, разрешено ли GC выгружать классы из PermGen. Стандартная JVM довольно консервативна в этом отношении - классы рождены, чтобы жить вечно. Поэтому после загрузки классы остаются в памяти, даже если их больше не использует ни один код. Это может стать проблемой, когда приложение создает много классов динамически, и сгенерированные классы не нужны в течение более длительных периодов времени. В таком случае может помочь JVM выгрузить определения классов. Это может быть достигнуто путем добавления только одного параметра конфигурации в ваши сценарии запуска:
По умолчанию для этого параметра установлено значение false, поэтому для его включения необходимо явно указать следующую опцию в параметрах Java. Если вы включите CMSClassUnloadingEnabled, GC также будет сканировать PermGen и удалять классы, которые больше не используются. Имейте в виду, что этот параметр будет работать только в том случае, если UseConcMarkSweepGC также включен с использованием указанного ниже параметра. Поэтому при запуске ParallelGC или, не дай Бог, Serial GC, убедитесь, что вы установили GC на CMS, указав:
источник
Назначение Tomcat дополнительной памяти НЕ является правильным решением.
Правильное решение - выполнить очистку после уничтожения и повторного создания контекста (горячее развертывание). Решение состоит в том, чтобы остановить утечки памяти.
Если ваш сервер Tomcat / Webapp сообщает вам, что не удалось отменить регистрацию драйверов (JDBC), отмените их регистрацию. Это остановит утечки памяти.
Вы можете создать ServletContextListener и настроить его в своем файле web.xml. Вот пример ServletContextListener:
И вот вы настраиваете это в своем файле web.xml:
источник
«Они» не правы, потому что я работаю 6.0.29 и у меня та же проблема, даже после установки всех параметров. Как сказал Тим Хоулэнд выше, эти варианты только откладывают неизбежное. Они позволяют мне выполнить повторное развертывание 3 раза, прежде чем совершать ошибку, а не каждый раз, когда я выполняю повторное развертывание.
источник
В случае, если вы получаете это в IDE eclipse, даже после установки параметров
--launcher.XXMaxPermSize
и-XX:MaxPermSize
т. Д., Все же, если вы получаете ту же ошибку, наиболее вероятно, что eclipse использует ошибочную версию JRE, которая была бы установлена некоторыми сторонние приложения и установить по умолчанию. Эти версии с ошибками не принимают параметры PermSize, поэтому независимо от того, что вы установили, вы все равно будете получать эти ошибки памяти. Итак, в ваш eclipse.ini добавьте следующие параметры:Также убедитесь, что вы установили JRE по умолчанию в настройках затмения на правильную версию Java.
источник
Единственный способ, который работал для меня, был с JRockit JVM. У меня есть MyEclipse 8.6.
В куче JVM хранятся все объекты, созданные с помощью работающей Java-программы. Java использует
new
оператор для создания объектов, а память для новых объектов выделяется в куче во время выполнения. Сборка мусора - это механизм автоматического освобождения памяти, содержащейся в объектах, на которые программа больше не ссылается.источник
У меня была похожая проблема. Мой JDK 7 + Maven 3.0.2 + Struts 2.0 + Google GUICE проект, основанный на внедрении зависимостей.
Всякий раз, когда я пытался запустить
mvn clean package
команду, она показала следующую ошибку, и "BUILD FAILURE" происходилоЯ испробовал все вышеперечисленные полезные советы и рекомендации, но, к сожалению, ни один из них не помог мне. То, что сработало для меня, описано шаг за шагом ниже: =>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
элемент, а затем<argLine>
вложенный элемент, в котором передайте,-Xmx512m -XX:MaxPermSize=256m
как показано ниже =><configuration> <argLine>-Xmx512m -XX:MaxPermSize=256m</argLine> </configuration>
Надеюсь, это поможет, счастливого программирования :)
источник