JAVA并发编程--JAVA内存模型以及CPU缓存知识

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/LuuvyJune/article/details/86540623

阅读《Java高并发编程详解》后的笔记。

CPU cache模型

CPU的处理速度和内存的访问速度差距太大,于是在CPU和主存之间增加了缓存。

CPU cache模型如图:

Cache的出现解决直接访问内存效率低下。程序运行时,Cache会将运算所需要的数据从主存复制一份到CPU cache中,这样CPU进行计算时就可以直接对CPU Cache中的数据进行读取和写入,运算结束后,再将CPU cache中的最新数据刷入主存中。

CPU和主存之间交互的架构如图:

CPU缓存一致性问题

缓存的出现极大提高了CPU的吞吐能力,但会引入缓存不一致的问题。

如 i++,根据上面CPU和主存交互的过程,步骤如下:

  • 读取主存的i到CPU Cache中
  • 对i进行+1
  • 将结果写回到CPU Cache中
  • 将数据刷新到主存中

这个过程对于单线程来讲不会出现问题,但是多线程下会出现缓存不一致的问题。每个线程都会有一个自己的工作内存(本地内存--CPU Cache),i在多线程的本地内存中都会有一个副本。假设2个线程执行i++操作,i的初始值设为0,每个线程都从主存中获取i的值存入CPU Cache中,然后经过计算再写入主内存中,很可能i在进过两次自增之后的结果还是1。

解决缓存不一致的方法:

  • 总线加锁,悲观,效率低下,会阻塞其他CPU对其他组件的访问
  • 缓存一致性协议

Intel的MESI缓存一致性协议:

大致思想:CPU在操作Cache中的数据时,如果发现该类变量是一个共享变量,也就是说在其他CPU Cache中也存在一个副本,那么:

(1)读取操作,不做任何处理,只将Cache中的数据读取到寄存器

(2)写入操作,发出信号通知其他CPU将该变量的Cache Line设置为无效状态,其他CPU在进行该变量读取的时候必须到主存中再次获取。

JAVA内存模型

JAVA的内存模型(Java Memory Mode)制定了Java虚拟机如何与计算机的主存(RAM)进行工作。

Java内存模型如图:

 JAVA内存模型与CPU硬件架构交互图:

当同一个数据被分别存储在计算机的各个内存区域时,会导致多个线程在各自的工作区域中看到的数据有可能是不一样的。volatile保证不同线程对某个共享变量的可见性。

猜你喜欢

转载自blog.csdn.net/LuuvyJune/article/details/86540623