volatile 禁止指令重排
本文介绍下volatile禁止指令重排的背景及最终效果。
volatile 可见性保证
我们都知道 volatile 会保证读写修饰的变量时会将对应变量同步给主存。
但是实际上, volatile 修饰的变量不仅保证自身,还会保证其他局部变量的可见性。
以下结合例子讲解下。
1 | java复制代码 |
Reordinrg 指令重排的挑战
指令重排前的代码
1 | ini复制代码int a = 1; |
可能的重排后代码
1 | ini复制代码// 估计是为了读写操作一起,减少内存缺页率 |
对volatile可见性保证的影响
1 | java复制代码 |
hanppens-before 发生前保证
为了保证 vaolatile 对其他变量可见性的保证 规则, volatile 的 happens-before 规定对指令重排的限制。
读写其他变量如果本身在写volatile变量之前的, 禁止重排到写volatile变量之后。
读写其他变量如果本身在读volatile变量之后的, 禁止重排到读volatile变量之前。
据说 happens-before 是 JSR-133 的规范质疑,内存屏障是 CPU 的指令。
前者是目的, 后者是实现目的的手段。
本文主要参考
tutorials.jenkov.com/java-concur…
本文转载自: 掘金