Tomcat 检测内存泄漏实例详解

 更新时间:2016年12月31日 10:17:47   投稿:lqh  
这篇文章主要介绍了 Tomcat 检测内存泄漏实例详解的相关资料,需要的朋友可以参考下

 Tomcat如何检测内存泄漏

一般情况下,如果我们重启web应用是通过重启tomcat的话,则不存在内存泄漏问题。但如果不重启tomcat而对web应用进行重加载则可能会导致内存泄漏,因为重加载后有可能会导致原来的某些内存无法让GC回收,例如web应用使用了JDBC,驱动会进行注册,当web应用停止时没有反注册就会导致内存泄漏。

看看是什么原因导致tomcat内存泄漏的。这个要从热部署开始说起,因为tomcat提供了不必重启容器而只需重启web应用以达到热部署的功能,其实现是通过定义一个WebappClassLoader类加载器,当热部署时就将原来的类加载器废弃并重新实例化一个WebappClassLoader类加载器。但这种方式可能存在内存泄漏问题,因为ClassLoader是一个结构复杂的对象,导致它不能被GC回收的可能性比较多,除了对ClassLoader对象有引用可能导致其无法回收,还可能对其加载的元数据(方法、类、字段等)有引用都会导致无法被GC回收。

如上图,tomcat的资源由不同类加载器加载,这里只看BootstrapClassLoader和WebappClassLoader两个类加载器,BootstrapClassLoader负责加载rt.jar包的Java.sql.DriverManager,WebappClassLoader负责加载web应用中的MySQL驱动包,其中有一个很重要的步骤是mysql的驱动类需要注册到DriverManager中,即DriverManager.registerDriver(new Driver()),它由mysql驱动包自动完成。这样一来当web应用进行热部署操作时,没有将mysql的Driver从DriverManager中反注册掉的话,则会导致整个WebappClassLoader回收不了,造成内存泄漏。

接着看tomcat如何对此内存泄漏进行监控的,要判断WebappClassLoader会不会导致内存泄漏只需判断WebappClassLoader有没有被GC回收即可。在Java中有一种引用叫弱引用,它能很好判断WebappClassLoader有没有被GC回收,被弱引用关联的对象只能生存到下一次垃圾回收发生之前,即如果某WebappClassLoader对象只被某弱引用关联,则它会在下次垃圾回收时被回收,但如果WebappClassLoader对象除了被弱引用关联外还被其他对象强引用,那么WebappClassLoader对象是不会被回收的,根据这些条件就可以判断是否有WebappClassLoader内存泄漏了。

Tomcat的实现是通过WeakHashMap来实现弱引用的,只需将WebappClassLoader对象put到WeakHashMap中,例如weakMap.put(“a”,webappClassLoader),当webappClassLoader及其包含的元素没有被其它任何类加载器中的元素引用到时,JVM发生垃圾回收时则会把webappClassLoader对象回收。

简单的实现代码大致如下:

public class MemoryLeakTest{
private Map<ClassLoader, String> childClassLoaders = new WeakHashMap<ClassLoader, String>();
public String[] findReloadedContextMemoryLeaks() {
    System.gc();
    List<String> result = new ArrayList<String>();
    for (Map.Entry<ClassLoader, String> entry : childClassLoaders.entrySet()) {
      ClassLoader cl = entry.getKey();
      if (!((WebappClassLoader) cl).isStarted()) {
        result.add(entry.getValue());
      }
    }
    return result.toArray(new String[result.size()]);
  }
}

使用一个WeakHashMap用于跟踪WebappClassLoader,在查找内存泄漏之前会先强制调用System.gc();进行一次垃圾回收,保证没问题的WebappClassLoader都被回收掉,这时如果还有WebappClassLoader的状态是非started(正常启动的都为started,关闭了的则为非started)的,则是未被垃圾回收的WebappClassLoader,属于内存泄漏的。

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

相关文章

  • 一篇文章讲透Tomcat的类加载机制

    一篇文章讲透Tomcat的类加载机制

    Tomcat的类加载机制是违反了双亲委托原则的,对于一些未加载的非基础类,各个web应用自己的类加载器会优先加载,加载不到时再交给commonClassLoader走双亲委托,这篇文章主要给大家介绍了如何通过一篇文章讲透Tomcat的类加载机制的相关资料,需要的朋友可以参考下
    2021-11-11
  • 详解tomcat各个端口的作用

    详解tomcat各个端口的作用

    这篇文章主要介绍了详解tomcat各个端口的作用,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-10-10
  • tomcat 启动时卡住问题排查及解决方法

    tomcat 启动时卡住问题排查及解决方法

    这篇文章主要介绍了tomcat 启动时卡住问题排查,本文给大家分享完美解决方法,对tomcat 启动卡住解决方法感兴趣的朋友一起看看吧
    2023-03-03
  • 关于Tomcat 结合Atomikos 实现JTA的方法

    关于Tomcat 结合Atomikos 实现JTA的方法

    Tomcat作为一款经典的Web服务器,在开发、测试和生产环境中得到了广泛的使用。但Tomcat毕竟不是Java EE服务器,因此在EJB,JTA方面并没有提供支持。本文讲述了Tomcat使用Atomikos实现JTA的一种方法,需要的朋友可以参考下
    2021-11-11
  • 详解Tomcat多域名的配置

    详解Tomcat多域名的配置

    本篇文章主要介绍了Tomcat多域名的配置 ,几个项目需要发布在同一个tomcat服务器上,每个项目有不同的域名,有兴趣的可以了解一下
    2017-07-07
  • 一文告诉你如何解决Tomcat乱码问题(很详细!)

    一文告诉你如何解决Tomcat乱码问题(很详细!)

    这篇文章主要给大家介绍了关于如何解决Tomcat乱码问题的相关资料,还给大家介绍了tomcat窗口中文乱码的解决方法,文中通过图文介绍的非常详细,需要的朋友可以参考下
    2022-03-03
  • web安全—tomcat禁用WebDAV或者禁止不需要的 HTTP 方法

    web安全—tomcat禁用WebDAV或者禁止不需要的 HTTP 方法

    现在主流的WEB服务器一般都支持WebDAV,使用WebDAV的方便性,呵呵,就不用多说了吧,用过VS.NET开发ASP.Net应用的朋友就应该 知道,新建/修改WEB项目,其实就是通过WebDAV+FrontPage扩展做到的,下面我就较详细的介绍一下
    2017-03-03
  • Tomcat服务器 安全设置

    Tomcat服务器 安全设置

    tomcat是一个开源Web服务器,基于Tomcat的Web运行效率高,可以在一般的硬件平台上流畅运行,因此,颇受Web站长的青睐。不过,在默认配置下其存在一定的安全隐患,可被恶意攻击。
    2009-08-08
  • 详解tomcat设置默认路径致使项目url冲突解决方法

    详解tomcat设置默认路径致使项目url冲突解决方法

    这篇文章主要介绍了详解tomcat设置默认路径致使项目url冲突解决方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2019-01-01
  • Tomcat安全设置 win2003 下tomcat权限限制

    Tomcat安全设置 win2003 下tomcat权限限制

    Tomcat安全设置 win2003 下tomcat权限限制,需要的朋友可以参考下。
    2011-03-03

最新评论