我想知道为什么CMS需要两个阶段(以及两个暂停)的标记:即初始标记和备注。我们可以简单地做一个标记然后执行扫描吗?我想这可能是一个更快的停顿。有人可以帮助解释第二个标记的主要目的是什么以及我们为什么需要它?谢谢!
答案 0 :(得分:5)
HotSpot内存管理白皮书中非常好地解释了这一点:
CMS收集器的收集周期以称为初始标记的短暂停顿开始,该停顿标识可直接从应用程序代码访问的初始活动对象集。然后,在并发标记阶段,收集器标记从该集合可传递地到达的所有活动对象。由于应用程序正在运行并在标记阶段发生时更新引用字段,因此并非所有活动对象都保证在并发标记阶段结束时进行标记。为了处理这个问题,应用程序再次停止第二次暂停,称为remark,它通过重新访问在并发标记阶段期间修改的任何对象来完成标记。由于备注暂停比初始标记更重要,因此多个线程并行运行以提高其效率。 在备注阶段结束时,保证堆中的所有活动对象都已被标记,因此后续并发扫描阶段将回收已识别的所有垃圾。