MESI一致性协议

小陈:老王,上一章你让我看看MESI一致性协议,我大概了解了一下。

老王:哦,来说说你对MESI一致性协议的理解

小陈:MESI协议也叫做缓存一致性协议,主要是用来进行协调多核CPU的高级缓存的数据一致的。第一章的时候讲过,CPU多级缓存架构,存在多个高速缓存之间数据一致性的问题。

老王:哦,第一章讲的多核CPU高速缓存之间的数据一致性问题,你还记得啊,哈哈,那你来说说。

小陈:当然,当时我可以记在小本本里面的,就等着你来讲这事的呢,沿用第一篇的那个图来讲一下:

(1)看下面的图,假如两个CPU0、CPU1同时将 i = 0 读取进入自己的高速缓存

(2)然后CPU0执行得比较快,执行完 i++操作之后将 i=1 的结果刷回主存了

(3)但是CPU1并不知道数据已经变更了,还是使用 i = 0 的结果去进行 i++ 操作

(4)本来正确的结果应该是 i = 2的,结果执行了两次i++,结果却是1

老王:没错,当时讨论多核CPU的高速缓存的时候,留了这个问题;看来你还记得这个问题,很好很好,掌声鼓励一下!

小陈:嘿嘿,突然的夸我,怪不好意思的......

小陈:造成上面数据不一致的原因主要是因为,CPU0修改了数据之后没有机制能够通知到CPU1,让CPU1它高速缓存上这个变量的数据失效掉,导致CPU1计算的时候还是使用旧的值

所以要解决多核CPU的高速缓存数据一致性的问题,必须有个机制能够某个CPU0修改了数据之后,立即通知的CPU1,让CPU1的高速缓存上的这个变量数据失效掉;然后CPU1用到的时候重新重主内存读取最新的值,这样就能得到最新的结果了。

小陈:MESI实现的缓存一致性协议,正是CPU0修改了数据,通知到CPU1的那套通知机制的一种规范,计算机厂商根据这套规范实现了这种通知机制,但是不同的厂商之间实现方式可能稍微不同。

老王:哎呀呀,不错啊。看来两天不见,你竟然把问题研究得这么深入了。

小陈:那是,问了看懂这个MESI协议,我可是连续肝了两天晚上,点了无数根华子...

老王:孺子可教也,那你继续来说说MESI的缓存一致性的内容

小陈:MESI一致性协议定义了高速缓存中数据的4中状态,分别是:

M(Modified): 修改过的,只有一个CPU能独占这个修改状态,独占的意思是当有一个CPU的高速缓存数据处于这个状态的时候,其它CPU的高速缓存对这个共享的数据均不能操作;高速缓存中的数据发生了更新,需要被刷入主内存中。

E(Exclusive): 独占状态,只有一个CPU独占这个状态,同样当某个CPU的高速缓存的数据处于这个状态的时候,其它CPU的均不能操作这个共享数据

S(Share):共享的状态,当CPU的高速缓存中的数据这个状态的时候,各个CPU可以并发的对这个数据进行读取

I(Invalid):无效的,意思是当前高速缓存的这个数据已经是无效了或者过期了,不能使用。

老王:那你继续来说说,MESI这四种状态是怎么来解决多核CPU高速缓存数据一直的?

小陈:好,下面我画几张图来i讲一下:

(1)首先像下面的图一样,CPU0CPU1将共享变量 i = 0 读取,进入自己高速缓存的时候;缓存的状态是S,也就是共享的

(2)然后CPU0要对 i = 0 的变量进行修改操作,在MESI一致性里面大概会经过这些步骤:

1. CPU0发送消息给总线,说我要修改数据了,帮我通知一下其它的CPU

2. 其它的CPU收到总线通知消息,将自己高速缓存上 i = 0 的数据状态变为Invalid过期

3. 其它CPU返回给总线说我们都过期了

4. 总线收到其它CPU返回过期OK了

5. 总线返回给CPU0说,好了,其它CPU都通知到位了,它们高速缓存上的 i = 0的数据都是过期状态了

6. CPU0收到了过期确认,都过期了,那我就可以独占这份数据了,嘿嘿,准备可以修改数据了

(3)CPU0修改数据,刷新回主内存,还会经过这些步骤:

7. CPU0执行 i++ 操作,将 i = 1 的最新结果刷入到高速缓存中,同时将高速缓存的数据状态设为M(修改过的)

8. 然后将高速缓存中 i = 1 的最新结果又刷入主内存

(4)CPU1读取数据操作,发现高速缓存上数据过期了,回经过下面步骤:

9. CPU1发现自己高速缓存上 i = 0 的数据是 Invalid 过期状态,于是从主存重新读取

10. 然后CPU1从主内存读取到 i = 1的最新的数据,将自己状态设置成S

小陈:上面就是我理解的MESI一致性协议在多核CPU之间进行协调的原理

老王:牛啊,小陈;短短两天时间你理解到这个程度,这理解能力很不错了,颇有我当年的风范啊.....

小陈:......

老王:就MESI一致性协议来说,你理解到这个程度已经可以了;再往下层次就是各个计算机厂商在硬件层面实现的差异了,这个我也不懂了,理解到这里已经非常不错了...

小陈:老王,我记得你跟我说JAVA内存模型的时候,每个线程在JMM中都有自己的工作内存。每个线程的工作内存都有共享变量的一个副本,这多个工作内存的变量副本之间也可能存在数据不一致的情况。

老王:嗯嗯怎了了?

小陈:我回顾了之前JMM的图,是这样子的:

小陈:多个工作内存之间共享变量x的副本,可能数据不一致,这个数据不一致的可见性问题在JMM层次是怎么解决的?

老王:你想想,Java内存模型建立在多核CPU高速缓存之上对不对?

小陈:是的

老王:那JAVA内存模型对应到底层肯定也是操作主内存、操作高速缓存来操作数据的,既然多核CPU的缓存一致性又是通过MESI协议来达到一致性的。所以啊,JAVA内存模型底层其实也还是通过MESI一致性来使得一个线程修改了数据,把别的线程的工作内存副本数据弄失效的。

小陈:哦哦,原来JAVA内存模型底层也是通过MESI来使得别的线程的工作内存变量副本失效的啊。

老王:嗯嗯,没错的。

小陈:底层的原理我知道了,那在JAVA编程的层次又是怎么来做的?

老王:那就是下面要讲的文章了,前面的几篇文章和这一篇我们都是讨论在底层原理层次。真正在使用层次来说,volatile、synchronized、cas、锁等都用到了这些底层原理

老王:下面我们就先来讨论volatile这个关键字,看看它是怎么来保证可见性的?

小陈:好啊,我期待一波......

关注小陈,公众号上更多更全的文章

JAVA并发文章目录(公众号)

JAVA并发专题 《筑基篇》

1.什么是CPU多级缓存模型?

2.什么是JAVA内存模型?

3.线程安全之可见性、有序性、原子性是什么?

4.什么是MESI缓存一致性协议?怎么解决并发的可见性问题?

JAVA并发专题《练气篇》

5.volatile怎么保证可见性?

6.什么是内存屏障?具有什么作用?

7.volatile怎么通过内存屏障保证可见性和有序性?

8.volatile为啥不能保证原子性?

9.synchronized是个啥东西?应该怎么使用?

10.synchronized底层之monitor、对象头、Mark Word?

11.synchronized底层是怎么通过monitor进行加锁的?

12.synchronized的锁重入、锁消除、锁升级原理?无锁、偏向锁、轻量级锁、自旋、重量级锁

13.synchronized怎么保证可见性、有序性、原子性?

JAVA并发专题《结丹篇》

14. JDK底层Unsafe类是个啥东西?

15.unsafe类的CAS是怎么保证原子性的?

16.Atomic原子类体系讲解

17.AtomicInteger、AtomicBoolean的底层原理

18.AtomicReference、AtomicStampReference底层原理

19.Atomic中的LongAdder底层原理之分段锁机制

20.Atmoic系列Strimped64分段锁底层实现源码剖析

JAVA并发专题《金丹篇》

21.AQS是个啥?为啥说它是JAVA并发工具基础框架?

22.基于AQS的互斥锁底层源码深度剖析

23.基于AQS的共享锁底层源码深度剖析

24.ReentrantLock是怎么基于AQS实现独占锁的?

25.ReentrantLock的Condition机制底层源码剖析

26.CountDownLatch 门栓底层源码和实现机制深度剖析

27.CyclicBarrier 栅栏底层源码和实现机制深度剖析

28.Semaphore 信号量底层源码和实现机深度剖析

29.ReentrantReadWriteLock 读写锁怎么表示?

30. ReentrantReadWriteLock 读写锁底层源码和机制深度剖析

JAVA并发专题《元神篇》并发数据结构篇

31.CopyOnAarrayList 底层分析,怎么通过写时复制副本,提升并发性能?

32.ConcurrentLinkedQueue 底层分析,CAS 无锁化操作提升并发性能?

33.ConcurrentHashMap详解,底层怎么通过分段锁提升并发性能?

34.LinkedBlockedQueue 阻塞队列怎么通过ReentrantLock和Condition实现?

35.ArrayBlockedQueued 阻塞队列实现思路竟然和LinkedBlockedQueue一样?

36.DelayQueue 底层源码剖析,延时队列怎么实现?

37.SynchronousQueue底层原理解析

JAVA并发专题《飞升篇》线程池底层深度剖析

38. 什么是线程池?看看JDK提供了哪些默认的线程池?底层竟然都是基于ThreadPoolExecutor的?

39.ThreadPoolExecutor 构造函数有哪些参数?这些参数分别表示什么意思?

40.内部有哪些变量,怎么表示线程池状态和线程数,看看道格.李大神是怎么设计的?

41. ThreadPoolExecutor execute执行流程?怎么进行任务提交的?addWorker方法干了啥?什么是workder?

42. ThreadPoolExecutor execute执行流程?何时将任务提交到阻塞队列? 阻塞队列满会发生什么?

43. ThreadPoolExecutor 中的Worker是如何执行提交到线程池的任务的?多余Worker怎么在超出空闲时间后被干掉的?

44. ThreadPoolExecutor shutdown、shutdownNow内部核心流程

45. 再回头看看为啥不推荐Executors提供几种线程池?

46. ThreadPoolExecutor线程池篇总结

4.什么是MESI缓存一致性协议?怎么解决并发的可见性问题?相关推荐

  1. MESI 缓存一致性协议

    本文目录 场景再现 1.总线锁 2.MESI 缓存一致性协议 1.MESI 协议概念 2.通过例子来介绍 MESI 协议 1.MESI 场景 2.MESI 协议下,执行步骤 3.MESI协议失效问题 ...

  2. MESI缓存一致性协议详解

    MESI缓存一致性协议详解 1.CPU为何要有高速缓存 CPU中内置了少量的高速缓存以解决I\O速度和CPU运算速度之间的不匹配问题. 带有高速缓存的CPU执行计算的流程 程序以及数据被加载到主内存 ...

  3. 并发编程实战-MESI缓存一致性协议

    大家好,最近呢我对并发编程展现出了兴趣(没办法,别人都会你不会说不过去啊),然后我就要奋发图强学好并发编程,那么接下来让我们一起进入学习吧.我们在学习并发编程实战之前,应该先要了解一下我们的cpu缓存 ...

  4. 聊聊高并发(五)理解缓存一致性协议以及对并发编程的影响

    Java作为一个跨平台的语言,它的实现要面对不同的底层硬件系统,设计一个中间层模型来屏蔽底层的硬件差异,给上层的开发者一个一致的使用接口.Java内存模型就是这样一个中间层的模型,它为程序员屏蔽了底层 ...

  5. MESI缓存一致性协议

    每个处理器,在自己的高速缓存中都有变量副本,这就有了缓存不一致问题,因此有了MESI协议. MESI协议将缓存行状态flag分为4种: invalid:无效的,标记为I,当前cache entry无效 ...

  6. 简述Intel的MESI缓存一致性协议

    ①M:modified--与主存的内容相比,有改动就标记为M.我改过,那么对于别人来说就是i了. ②E:exclusive--内容为我锁独占,标记为E. ③S:shared--与此同时别人也在读,标记 ...

  7. 两个例子详解并发编程的可见性问题和有序性问题,通过volatile保证可见性和有序性以及volatile的底层原理——缓存一致性协议MESI和内存屏障禁止指令重排

    1. 并发编程的可见性问题 2. 并发编程的有序性问题 3. 使用volatile关键字解决可见性问题 4. 可见性问题的本质--缓存不一致 因为cpu执行速度很快,但是内存执行速度相对于CPU很慢, ...

  8. “了解高并发底层原理”,面试官:讲一下MESI(缓存一致性协议)吧

    目录 前言: 1.什么是(Who): 2.为何来(How): 2.1缓存不一致带来的后果 2.2解决方法: 3.是什么(What) 3.1数据在缓存中的四种状态: 3.2MESI的六种消息(请求消息和 ...

  9. 同时存多个变量缓存 微信小程序_CPU缓存一致性协议MESI,memory barrier和java volatile...

    MESI协议 MESI协议是一个被广泛使用的CPU缓存一致性协议.我们都知道在CPU中存在着多级缓存,缓存级别越低,容量就越小,速度也越快.有了缓存,CPU就不需要每次都向主存读写数据,这提高了CPU ...

最新文章

  1. Windows 2003 + ISA 2006+单网卡×××配置(4)
  2. Error:Unable to tunnel through proxy. Proxy returns HTTP/1.1 400 Bad Request
  3. Idea左侧显示目录结构和.java文件的解决办法
  4. c++中scanf和printf
  5. SVM与SoftMax分类器
  6. 20145315 《信息安全系统设计基础》第14周学习总结
  7. c++ primer 第六版 pdf_A3N630 塑壳断路器如何更换.pdf
  8. 解决ie8及低版本浏览器不支持html5标签属性
  9. 使用静态内置类实现线程安全的单例设计模式
  10. flink离线mysql_Flink 流模式跑离线任务
  11. 小程序入门学习10--云开发03
  12. 【渝粤教育】电大中专门店销售与服务技巧 (2)作业 题库
  13. 下一代操作系统与软件
  14. 用SQL Server(T-SQL)获取连接字符串
  15. 第三章 DirectX 图形绘制(上)
  16. 抗衡微软,三款国产软件接力金山WPS,身体力行,不愧是国产之光
  17. java开发必备基础
  18. 【绝对好用】java poi 导入、导出excel(支持xsl、xslx)
  19. 全球与中国PH传感器盒市场深度研究分析报告
  20. 0711 练习 百分制成绩记入与十分制成绩记入方式转换

热门文章

  1. ESP8266+水墨屏
  2. Docker之旅(1)-Docker基础
  3. 利用Cadence Allegro强大的功能节省您调丝印的时间
  4. 分享Canvas简笔画小程序源码
  5. C语言编程输出象棋棋盘
  6. java 多线程 售票_Java 多线程 之 火车站售票实例
  7. 整理的开学需要准备的物品清单,删了怪可惜,做个备份吧
  8. 欧几里得距离转换(EDT)算法
  9. linux操作系统实验教程费翔林,实验一操作系统接口实验.doc
  10. 【零基础】MT4/MT5一条语句让EA发微信消息推送