Ошибка PermGen Space при горячем развертывании на Tomcat - PullRequest
1 голос
/ 17 марта 2012

Я вижу следующие сообщения в журналах после каждого повторного развертывания.

INFO: Reloading Context with name [/x1Application] has started
SEVERE: The web application [/x1Application] appears to have started a thread named [Mojarra-WebResourceMonitor-1-thread-1] but has failed to stop it. This is very likely to create a memory leak.
SEVERE: The web application [/x1Application] appears to have started a thread named [Hector.me.prettyprint.cassandra.connection.CassandraHostRetryService-1] but has failed to stop it. This is very likely to create a memory leak.

В конце концов после 1-2 горячих развертываний сервер перестает отвечать, и я получаю ошибку пространства PermGen

17 Mar, 2012 1:40:01 AM org.apache.catalina.core.StandardWrapperValve invoke
SEVERE: Servlet.service() for servlet [jsp] in context with path [] threw exception [The HTTP Monitor server side component intercepted and rethrew an error while processing a JSP or servlet. Please see the stack trace under the root cause message below to identify the problem.] with root cause
java.lang.OutOfMemoryError: PermGen space
    at java.lang.ClassLoader.defineClass1(Native Method)
    at java.lang.ClassLoader.defineClassCond(ClassLoader.java:632)
    at java.lang.ClassLoader.defineClass(ClassLoader.java:616)
    at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:141)
    at java.net.URLClassLoader.defineClass(URLClassLoader.java:283)
    at java.net.URLClassLoader.access$000(URLClassLoader.java:58)
    at java.net.URLClassLoader$1.run(URLClassLoader.java:197)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:307)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:248)
    at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:382)
    at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:333)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:304)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:240)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:164)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:164)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:563)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:399)
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:317)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:204)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:182)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:311)
    at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
17 Mar, 2012 1:40:12 AM org.apache.catalina.core.StandardWrapperValve invoke
SEVERE: Servlet.service() for servlet [jsp] in context with path [] threw exception [The HTTP Monitor server side component intercepted and rethrew an error while processing a JSP or servlet. Please see the stack trace under the root cause message below to identify the problem.] with root cause
java.lang.OutOfMemoryError: PermGen space
    at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:382)
    at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:333)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:304)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:240)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:164)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:164)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:563)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:399)
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:317)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:204)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:182)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:311)
    at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
    at java.lang.Thread.run(Thread.java:662)

Как я могу получить больше информации об источнике ошибки?

Ответы [ 2 ]

2 голосов
/ 17 марта 2012

Я бы доложил об этом ребятам Гектора. Их ошибка в том, что их код неправильно закрывает запущенные потоки при завершении работы веб-приложения. В то же время, вы можете выбрать лучший сервер разработки (любимым является Glassfish ; он выполняет горячее развертывание за секунду) или установить JRebel , чтобы превратить Tomcat в настоящего горячего развертывания вместо hotrestarter.

Что касается справочной информации о защите утечки памяти Tomcat, прочитайте следующие вики:

0 голосов
/ 30 сентября 2015

Вскоре мне пришлось столкнуться с подтекающим потоком с именем " Mojarra-WebResourceMonitor-1-thread-1 " на Apacht Tomcat 8.0.26 с Mojarra 2.2.12 в моем веб-приложении с использованием сервлета sepc 3.0.

Основная причина состояла в том, что два экземпляра com.sun.faces.config. ConfigureListener были добавлены в ServletContext.

Первый экземпляр(A) был добавлен контейнером Tomcat SCI org.apache.jasper.servlet.JasperInitializer.onStartup(...), как это настроено в javax.faces-2.2.12.jar! /META-INF/jsf_core.tld

Второй экземпляр (B) был добавлен
com.sun.faces.config.FacesInitializer.onStartup(...)

Обходной путь состоял в том, чтобы предотвратить вызов JapserInitializer путем редактирования моего контекста веб-приложения context.xml и добавления атрибута containerSciFilter в элемент контекста:

<Context containerSciFilter="org.apache.jasper.servlet.JasperInitializer|org.apache.tomcat.websocket.server.WsSci">

Оба SCI не нужны для моего веб-приложения.Так что этот обходной путь не поможет, если вы зависите от JSP и JSF.


Вот что произошло здесь неправильно:

При инициализации сервлета, tomcat называется

  • A.contextInitialized(...)
    • Инициализация JSF
    • Запуск потока
  • B.contextInitialized(...)
    • Поскольку JSF работает ... нечего делать

При выключении, звонки:

  • B.contextDestroyed(...)
    • Выключение JSF
    • Не знаю ни о каком threadPool, так как я его еще не запустил.
  • A.contextDestroyed(...)
    • Поскольку JSF остановлен, ничего не делать.

Таким образом, поскольку 'threadPool остается в рабочем состоянии и предотвращает сбор GC на WebAppClassloader.

Но чья это ошибка?

  1. Не удалось ли Tomcatотклонить несколько слушателей одного и того же класса?
  2. Не удалось ли JSF Mojarra остановить threadPool из-за его отсутствия threadPool, когда JSF не запущен и не запущен?
  3. Это неправильно, что слушатель is объявляется дважды:
    • Программно через SCI
    • Объявлено в основной метке TLD.

Редактировать: Былодля меня проблематично полностью пропустить JasperInitializer.Мне пришлось удалить его из containerSciFilter и добавить javax.faces - *. Jar в фильтр Tomcat tldSkip, например:

<JarScanner>
  <JarScanFilter defaultPluggabilityScan="false"
    pluggabilityScan="${tomcat.util.scan.StandardJarScanFilter.jarsToScan}, javax.faces-*.jar"
    tldSkip="${tomcat.util.scan.StandardJarScanFilter.jarsToSkip}, , javax.faces-*.jar" />
</JarScanner>
...