前言
今天星期二,天气还不错,心情很忐忑。
1.JMM是什么?
JMM: Java 内存模型(Java Memory Model,JMM)是线程和主内存之间的一种抽象关系,线程之间共享变量储存在主内存中,每个线程有线程私有的工作内存,该内存中存储该线程读/写共享变量的副本。JMM屏蔽了各种硬件和操作系统的访问差异,保证了 Java 程序在各种平台下对内存的访问都能保证效果一致。
作用是解决由于多线程通过共享内存进行通信时,存在的本地内存数据不一致、编译器会对代码指令重排序、处理器会对代码乱序执行等带来的问题。目的是保证并发编程场景中的原子性、可见性和有序性。
JMM8大原子操作:
Lock(锁定):作用于主内存的变量,把一个变量标记为一条线程独占状态;
Unlock(解锁):作用于主内存的变量,把一个处于锁定状态的变量释放出来,释放后的变量才可以被其他线程锁定;
Read(读取):把一个变量从主内存传输到线程的工作内存中,以便随后的load动作使用;
Load(载入):它把read操作从主内中得到的变量值放入工作内存的变量副本中;
Use(使用):把工作内存中的一个变量值传递给执行引擎;
Assign(赋值):它把一个从执行引擎接收到的值赋值给工作内存的变量;
Store(存储):把工作内存中的一个变量的值传送到主内中,以便随后的write操作;
Write(写入):把store操作从主内中的一个变量的值传送到主内存的变量中。
2.保证线程可见性的方法?
(旧CPU)总线加锁: CPU从主内存读取到缓存区中,总线会加锁锁定主存区域,来自其他CPU或者总线代理的控制请求将被阻塞,无法读写该数据,直到锁定被释放;
MESI: CPU缓存一致性协议,名字是由其描述的四个cache状态组成的,分别是Modified(修改)、Exclusive(独有)、Shared(共享)、Invalid(失效)。多CPU从主内存读取同一数据到各自缓存区中,该数据在lock前缀指令(汇编指令)执行期间已经在处理器内部的缓存中被锁定,缓存被锁定期间,其他CPU无法读写该数据,直到该缓存数据被修改同步回主内存后,其他CPU通过总线嗅探机制感知数据变化及时失效自己缓存中的数据,在下一轮指令周期从主内存重新load数据。
3.内存屏障
内存屏障分类及作用:
Load1;LoadLoad;Load2:
该屏障确保Load1数据的装载先于Load2及其后所有装载指令的的操作
Store1;StoreStore;Store2:
该屏障确保Store1立刻刷新数据到内存(使其对其他处理器可见)的操作先于Store2及其后所有存储指令的操作
Load1;LoadStore;Store2:
确保Load1的数据装载先于Store2及其后所有的存储指令刷新数据到内存的操作
Store1;StoreLoad;Load2:
该屏障确保Store1立刻刷新数据到内存的操作先于Load2及其后所有装载装载指令的操作。它会使该屏障之前的所有内存访问指令(存储指令和访问指令)完成之后,才执行该屏障之后的内存访问指令