R大在在介绍CMS时提到了write barrier写屏蔽的概念,是来干什么的?

http://hllvm.group.iteye.com/group/topic/38223#post-248757 我是用手机看的,不知道复制的对不…
关注者
76
被浏览
8,285
登录后你可以
不限量看优质回答私信答主深度交流精彩内容一键收藏

由于并发 mark-and-sweep 中 mark 阶段和 mutator 是并发的,以并发三色 mark 为例,有可能一块已经被 mark 成黑色的内存中的引用又被 mutator 修改指向了一块白色内存,write barrier 的功能就是处理类似这种情况,将新指向的白色内存 mark 为灰色。如果没有 write barrier,那块新指向的白色的内存就被视为垃圾了(如果没有其他指向它的引用)。

但是即使具备了 write barrier,mark 阶段仍然需要 stop-the-world 两次,第一次是 mark 初始化阶段,需要 stop-the-world 来将 root set 入队以及开启 write barrier,第二次是 mark termination 阶段,因为如果让 mutator 一直运行可能 mark 阶段永远无法结束(一直产生新的灰色内存导致需要一直去 mark)。

read barrier 解决的问题跟 write barrier 不一样,在 mark-and-sweep 中是不需要 read barrier 的,因为 GC 本身不会去移动内存。但是对于 mark-compact 或者 copying,因为 GC 要移动内存、修改引用,如果不用 read barrier 去跟踪读的情况,就需要等 GC 完全移动结束之后才能允许 mutator 去读,否则可能读到错误的(未移动完成的)引用。如果有了 read barrier,只要保证在 read barrier 时将要读的内存的引用移动完成即可,无需等待其他内存引用移动完成,等于是把内存引用移动这个过程平摊开了。

只熟悉 Go 的 GC,Go 的 GC 里没 read barrier,有可能理解有误,请 @RednaxelaFX 指正。