PermGen Space error on hot deploys on Tomcat

橙三吉。 提交于 2019-12-14 02:36:05

问题


I am seeing the following messages in the logs after each redeploys.

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.

Eventually after 1-2 hot deploys the server stops responding & I get the PermGen space error

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)

How can I get more information about the source of bug?


回答1:


I'd report it to Hector guys. It's their bug that their code is not properly shutting down running threads on webapp's shutdown. In the meanwhile, you could consider to pick a better development server (favourite is Glassfish; it hotdeploys in a subsecond) or to install JRebel to transform Tomcat into a real hotdeployer instead of a hotrestarter.

As to the background information about Tomcat's memory leak protection, read the following wikis:

  • Tomcat wiki - Memory leak protection
  • Tomcat wiki - How to deal with out of memory



回答2:


Shortly I had to deal with a leaking Thread named "Mojarra-WebResourceMonitor-1-thread-1" on Apacht Tomcat 8.0.26 with Mojarra 2.2.12 in my web app using servlet sepc 3.0.

The root cause was that two instances of com.sun.faces.config.ConfigureListener had been added to the ServletContext.

First instance (A) was added by Tomcat's container SCI org.apache.jasper.servlet.JasperInitializer.onStartup(...) as it is configured in javax.faces-2.2.12.jar!/META-INF/jsf_core.tld

Second instance (B) was added by
com.sun.faces.config.FacesInitializer.onStartup(...)

Workaround was to prevent JapserInitializer from invokation by editing my web app context.xml and add the containerSciFilter attribute to the context element:

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

Both SCIs are not needed for my web app. So this work around won't help if you depend on JSP and JSF.


This is what happend wrong here:

On Servlet initialization, tomcat called

  • A.contextInitialized(...)
    • Initialize JSF
    • Start the threadPool
  • B.contextInitialized(...)
    • As JSF is running ...nothing to do

On Shutdown, tomcal calls:

  • B.contextDestroyed(...)
    • Shutdown JSF
    • Don't know of any threadPool as I haven't started one.
  • A.contextDestroyed(...)
    • As JSF is stopped, nothing to do.

Thus As' threadPool remains up and running, preventing GC on WebAppClassloader.

But whose fault is this?

  1. Did Tomcat fail to reject multiple listeners of same Class?
  2. Did JSF Mojarra fail to stop the threadPool due to its' implication of threadPool absence when there's no JSF up and running?
  3. Is it wrong that the listener is declared twice:
    • Programmaticalli thru SCI
    • Declared in core TLD taglib.

Edit: It was problematic for me to completely skip the JasperInitializer. I had to remove it from containerSciFilter and add javax.faces-*.jar to Tomcat tldSkip filter like this:

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


来源:https://stackoverflow.com/questions/9744219/permgen-space-error-on-hot-deploys-on-tomcat

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!