问题描述
我有这个代码动态生成类并加载它
I have this code to generate class dynamically and load it
import javassist.CannotCompileException;
import javassist.ClassPool;
public class PermGenLeak {
private static final String PACKAGE_NAME = "com.jigarjoshi.permgenleak.";
public static void main(String[] args) throws CannotCompileException, InterruptedException {
for (int i = 0; i < Integer.MAX_VALUE; i++) {
ClassPool pool = ClassPool.getDefault();
pool.makeClass(PACKAGE_NAME + i).toClass();
Thread.sleep(3);
}
}
}
我推出这个类对Java 7(jdk1.7.0_60)和预期它填满了PermGenSpace并且堆仍未使用
I launched this class against Java 7 (jdk1.7.0_60) and as expected it filled up PermGenSpace and heap remained unused
现在相同的代码针对Java 8运行(jdk1 .8.0_40-ea)并且正如预期的那样它不断扩大本机内存(Metaspace)但令人惊讶的是,1g Metaspace在OldGen中消耗了3g Heap(随着时间的推移几乎是Metaspace的3倍)
Now the same code ran against Java 8 (jdk1.8.0_40-ea) and as expected it kept expanding native memory (Metaspace) but surprisingly for 1g of Metaspace it consumed 3g of Heap in OldGen (almost 3x of Metaspace maintained over time)
和说
在将多个类加载到Metaspace中时,堆的增加究竟是什么?
what exactly makes this increase in heap as it loads more classes into Metaspace ?
推荐答案
运行 jmap -histo PID
以查看哪些对象占用堆空间。
当我运行你的例子时,我看到堆满了Javassist辅助对象:
Run jmap -histo PID
to see which objects consume the Heap Space.
When I ran your example I saw the heap full of Javassist auxiliary objects:
num #instances #bytes class name
----------------------------------------------
1: 592309 312739152 [Ljavassist.bytecode.ConstInfo;
2: 6515673 208501536 java.util.HashMap$Node
3: 2964403 169188824 [C
4: 1777622 102165184 [Ljava.lang.Object;
5: 4146200 99508800 javassist.bytecode.Utf8Info
6: 3553889 85293336 java.util.ArrayList
7: 2964371 71144904 java.lang.String
8: 593075 56944008 java.lang.Class
9: 592332 47388032 [Ljava.util.HashMap$Node;
10: 592309 37907776 javassist.bytecode.ClassFile
11: 592308 37907712 javassist.CtNewClass
12: 1185118 28555808 [B
13: 592342 28432416 java.util.HashMap
14: 1184624 28430976 javassist.bytecode.ClassInfo
15: 592309 28430832 [[Ljavassist.bytecode.ConstInfo;
16: 592322 23692880 javassist.bytecode.MethodInfo
17: 592315 23692600 javassist.bytecode.CodeAttribute
18: 592434 18957888 java.util.Hashtable$Entry
19: 592309 18953888 javassist.bytecode.ConstPool
20: 592308 18953856 java.lang.ref.WeakReference
21: 592318 14215632 javassist.bytecode.MethodrefInfo
22: 592318 14215632 javassist.bytecode.NameAndTypeInfo
23: 592315 14215560 javassist.bytecode.ExceptionTable
24: 592309 14215416 javassist.bytecode.LongVector
25: 592309 14215416 javassist.bytecode.SourceFileAttribute
26: 592507 9487584 [I
27: 8 6292528 [Ljava.util.Hashtable$Entry;
28: 212 18656 java.lang.reflect.Method
29: 407 13024 java.util.concurrent.ConcurrentHashMap$Node
30: 124 8928 java.lang.reflect.Field
这篇关于Java8 metaspace&堆使用情况的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!