LeakType

内存泄漏实质

内存泄漏实质上是GC时候,被GC Root引用或间接引用着的对象无法被回收,而可以作为GC Root的对象在java中有几种:

  1. 虚拟机栈或叫JVM栈(栈帧中的本地变量表)中引用的对象; (线程泄露)

    虚拟机栈是线程私有的,每个java方法被执行的时候都会同时创建一个栈帧(Stack Frame)用于存储局部变量表、操作栈、动态链接、方法出口等信息。每一个方法被调用直至执行完成的过程,就对应着一个栈帧在虚拟机栈中从入栈到出栈的过程。

  2. 方法区中的类静态属性引用的对象; (static变量)

    方法区存储类信息、常量、静态变量等数据,是线程共享的区域

  3. 本地方法栈中JNI(即一般说的Native方法)中引用的对象 (Jni持有的对象)

    对应虚拟机栈为虚拟机执行java方法服务,而本地方法栈为虚拟机使用到的Native方法服务

  4. 方法区中常量引用的对象; (final修饰的int/float/long等基本数据类型和String) 不常见

Read more

JvmMemoryStructure

image-20240425141403378

程序计数器不会OOM和StackOverflow

有栈的结构(栈 java stack、navtive stack)可能发生 StackOverflowError(栈过深) 和 OOM

StackOverFlowError ︰若Java 虚拟机栈的内存大小不允许动态扩展,那么当线程请求栈的深度超过当前Java 虚拟机栈的最大深度的时候,就抛出StackOverFlowError错误。
OutOfMemoryError :如果虚拟机栈可以动态扩展(当前大部分的 Java 虚拟机都可动态扩展,只不过 Java 虚拟机规范中也允许固定长度的虚拟机栈),当扩展时无法申请到足够的内存时会抛出 OutOfMemoryError 异常。

没栈的结构(堆heap、方法区Method Area)只可能发生 OOM

Read more

Gc

现代VM:”引用计数法,不行。可达性分析法,行!”
JVM:”可达分析法,很行”

Read more