使用Java创建内存泄漏

问题:

我刚刚接受了面试,我被要求使用Java创建内存泄漏。
不用说,我觉得很笨,没有什么线索,甚至开始创造一个。
一个例子是什么?

回答:

这是创建一个真正的内存泄漏(通过运行代码但仍然存储在内存中的对象无法访问)的好方法:

  1. 该应用程序创建一个长时间运行的线程(或使用线程池泄漏更快)。
  2. 线程通过(可选自定义)ClassLoader加载类。
  3. 该类分配大块内存(例如new byte[1000000]),在静态字段中存储一个强引用,然后在ThreadLocal中存储对其自身的引用。分配额外的内存是可选的(泄漏Class实例就足够了),但它会使漏洞工作更快。
  4. 线程清除对自定义类或从其加载的ClassLoader的所有引用。
  5. 重复。

这是因为ThreadLocal保留对对象的引用,该对象保留对其Class的引用,而Class会继承其对ClassLoader的引用。 ClassLoader反过来又保留对所加载的所有类的引用。
(在许多JVM实现中,尤其是在Java 7之前,这是更糟糕的,因为Classes和ClassLoaders被直接分配给permgen,并且根本不被GC’,但是无论JVM如何处理类卸载,ThreadLocal仍然会阻止从被回收的类对象。)
这种模式的变化是为什么应用程序容器(如Tomcat)可能像筛子一样泄漏内存,如果您经常以任何方式重新部署使用ThreadLocals的应用程序。 (由于应用程序容器按照所述使用Threads,每次重新部署应用程序时都会使用一个新的ClassLoader。)
 更新:由于很多人不断要求,here’s some example code that shows this behavior in action

 
 
Code问答: http://codewenda.com/topics/python/
Stackoverflow: Creating a memory leak with Java

*转载请注明本文链接以及stackoverflow的英文链接

发表评论

电子邮件地址不会被公开。 必填项已用*标注

34 − = 24