根节点枚举
以可达性分析算法中从GC Roots集合找引用链这个操作作为介绍虚拟机高效实现的第一个例子。
固定可作为GC Roots的节点主要在全局性的引用(例如常量或类静态属性)与执行上下文(例如栈帧中的本地变量表)中。目标明确,但Java应用越做越庞大,方法区的大小就常有数百上千兆,里面的类、常量等更是恒河沙数,检查以这里为起源的引用需耗费大量时间。
主流Java虚拟机使用的都是准确式垃圾收集 ,直接得到哪些地方存放着对象引用的。
HotSpot使用一组称为OopMap的数据结构来达到这个目的。类加载动作完成的时,会把对象内什么偏移量上是什么类型的数据计算出来,在即时编译过程中,在特定的位置记录下栈里和寄存器里哪些位置是引用。这样收集器在扫描时就可以直接得知这些信息了,不需要一个不漏地从方法区等GC Roots开始查找。
安全点
HotSpot 没有为每条指令都生成OopMap, 只是在“特定的位置”记录了引用信息,这些位置被称为安全点(Safepoint)。
程序执行时并非在代码指令流的任意位置都能够停顿下来开始垃圾收集,而是强制要求必须执行到达安全点后才能够暂停。
安全点的选定
- 不能太少以至于让收集器等待时间过长;
- 不能太过频繁以至于过分增大运行时的内存负荷。
如何在垃圾收集发生时让所有线程都跑到最近的安全点?
1、抢先式中断(Preemptive Suspensio