上一文中讲到,由于新值存在于 Store Buffer 中,从 Cache line 中取得旧值,进而引起错误的问题,让我们来进一步解决这个问题。

在 <<走进 CPU 的 Cache>> 一文中有一张现代 CPU 的结构图,部分如下:

     +--------------+             |     CPU0     |                  +--------------+                 ^         |               |         |                  |         V                     |     +--------+             |<--> | Store  |              |     | Buffer |                |     +--------+           |         |                 |         V                +--------------+         |     Cache    |     +--------------+ 

在 CPU 载入内存和 Store Buffer 之间有一个交互的过程,这就是 Store forwaring,根据上一文中讲到的, 当 CPU0 执行 b = a + 1,时,此时它要加载 a 的值,此时它发现在 store buffer 中有 a 的值,
它就会直接从 store buffer 中读取,然后进行计算,这样,最后得到的 b 的值就将得到正确的结果了。
        仿佛世界顿时美好了起来,还有没有更好的优化方法呢,仔细回想一下,Store Buffer 的空间也是有限的,如果这样的情况发生的太多,在 cache miss 的情况下会经常有,那么一旦 store buffer 满了,后
面的指令依然要像上一文中那样等待,一直到其它 CPU 回应之后,再从 Store Buffer 中应用到 Cache 中,如果其它 CPU 忙碌,或者其它 CPU 接收到 read validate 消息后,置自己的 cache line 失效也会造成大量
的时间浪费,要是收到 read validate 消息后,直接给一个回应,然后自己在合适的时机慢慢处理这些消息就好了。
        对了,我只能说设计 CPU 的那些家伙太厉害了,他们发明了另一个东西,Invalidate Queue, 这个队列会将 Invalidate 消息缓存起来,然后马上给一个 Invalidate Acknowledge 消息,在结构图中也展示了这
一个队列。那么这个问题就完美解决了。
        让我们再来看一个小例子。 a 和 b 初始化都为 0。 a 在 CPU1 的 cache 中, b 在 CPU0 的 cache 中。
        CPU 0 执行下面的代码:
        a = 1;
        b = 1;
        CPU1 执行下面的代码:
        while (b != 1);
        assert (a == 1);
        断言一定能成功吗? 让我们假设下面的情况发生:
        1. CPU0 执行 a = 1, 但是发现 a 不在 cache 中,它就发出 "read invalidate" 消息,并且把 a 的值存在 store buffer 中;然后执行 b = 1;
        2。CPU1 执行 b != 1 的比较,读取 b 的值,结果不在 cache 中,因为它不想改写,所以只发一个 "read" 消息出去;
        3. CPU0 把 1 直接写入到 b 的 cache line 中, 并收到 "read" 消息,设 cache line 为共享,并给出回应。
        4. CPU1 收到 b 的值,退出循环,执行断言,断言失败;
        5. CPU1 收到 "read invalidate" 消息,但此时已晚。
        通过上面的例子,我们可以看出,由于 CPU 间消息时序的不确定性,还有 store buffer 存储写入操作的延迟性,一起导致了这个问题,这也是一些处理器普遍会存在的问题,尤其是一些弱内存序的 CPU。
        所以 Memory barriers 呼之欲出。
        Memroy barriers ,即内存屏障,它会将 Store Buffer 中的所有项目,都标打上标记,这样,当再有 store 操作时,如果发现 store buffer 中在项被标记,即使在 cache line 中已存在,它也不会直接写
入 cahce line ,取而代之的是,该操作,这里是 b = 1,也会被存入 Store Buffer, 并且该项不作标记,一直等到 Store Buffer 中被标记的项全部被应用到 Cache line 中,这些操作才会被正常应用。看来 Memory 
barriers 真是个好东西。
        (待续)

Store Forwarding相关推荐

  1. Pentium 4处理器架构/微架构/流水线 (11) - NetBurst执行核详解 - Load/Store操作/存储转发

    Loads and Stores Pentium 4处理器采用以下技术来加速访存操作的执行: 投机执行读存操作 对于读存和写存操作,重排序读存操作 允许多个缓存未中共存的情形(即无需等待上一个缓存未中 ...

  2. # 内存屏障:骇客的硬件视角(1)

    翻译自内存屏障 那么到底是什么让CPU的设计大师们着了魔,要把内存屏障这个鬼东西强行塞给了毫不知情的多处理器系统的软件开发者? 简单点说,就是因为内存访问顺序的重排会带来更好的性能.同步原语的正确操作 ...

  3. Linux内核链表 内存屏障,为什么需要内存屏障

    Author:Echo Chen(陈斌) Email:chenb19870707@gmail.com Date:September 30th, 2014 来自一篇墙外的文章,要了解如何使用memory ...

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

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

  5. 下篇 | 说说无锁(Lock-Free)编程那些事(下)

    6 内存屏障(Memory Barriers) 6.1 What Memory Barriers? 内存屏障,也称内存栅栏,内存栅障,屏障指令等,是一类同步屏障指令,是CPU或编译器在对内存随机访问的 ...

  6. CPU缓存一致性协议MESI - 笔记

    CPU缓存一致性协议MESI CPU高速缓存(Cache Memory) CPU为何要有高速缓存 CPU在摩尔定律的指导下以每18个月翻一番的速度在发展,然而内存和硬盘的发展速度远远不及CPU.这就造 ...

  7. 深入Java内存模型

    你可以在网上找到一大堆资料让你了解JMM是什么东西,但大多在你看完后仍然会有很多疑问.happen-before是怎么工作的呢?用volatile会导致缓存的丢弃吗?为什么我们从一开始就需要内存模型? ...

  8. 多核CPU缓存一致性协议MESI

    在计算机系统中,CPU高速缓存(英语:CPU Cache)是用于减少处理器访问内存所需平均时间的部件.在金字塔式存储体系中它位于自顶向下的第二层,仅次于CPU寄存器.其容量远小于内存,但速度却可以接近 ...

  9. 数仓中长跳转问题复现及解决方案

    本文分享自华为云社区<GaussDB(DWS)中长跳转可能出现的问题>,作者: 雷电与骤雨. 问题描述,在GaussDB(DWS)编码实践中,发现在debug未进行编译器优化的版本未发生问 ...

最新文章

  1. 一台物理机上VMware虚拟机实现拨号上网同时内网通信
  2. php中ini set,php ini_set更改php.ini配置功能
  3. MySQL创建用户(CREATE USER)
  4. 集群监控系统的设计方案
  5. ASP.NET Core 3.0 使用gRPC
  6. python闭合函数_Python中函数的闭包
  7. 一张小纸条(软件工程师成长过程中的一些建议)
  8. et中计算机的快捷键,ET软件快捷键
  9. Activiti工作流画图工具介绍
  10. 计算机的用户和密码在哪里看,电脑b站(哔哩哔哩)怎么查看自己的账号和密码?登录地址在哪找到?...
  11. [分类] Jzoj P1320 拯救奶牛
  12. Rhythmbox中文乱码解决
  13. 操作系统-为什么进程之间的通信必须借助操作系统内核功能?
  14. 保护手机隐私最关键是提高全民信息安全意识
  15. 全国计算机职称考试excel2003,全国计算机职称考试excel2003题库.pdf
  16. python中的strip()方法
  17. 熵值法的信息熵值、效用值如何计算?
  18. C#—得到服务器时间和国际标准时间
  19. 交换机模拟配置软件_GNS3 for mac(网络模拟工具)
  20. v-for的四种使用方法

热门文章

  1. Echarts实现省级到市级地图下钻
  2. PS、Excel快捷键桌面壁纸
  3. 数据分析过程中,发现数值缺失,怎么办?
  4. Mysql中的七种常用查询连接详解
  5. eclipse插件说明
  6. 瑞吉外卖第五天(套餐的增删改和手机端登录功能的实现)
  7. Java字母笔顺_j的笔顺 j书写顺序是什么
  8. 漏洞复现Influxdb,H2database,couchDB,ElasticSearch
  9. R shiny echart4r 常见问题整理
  10. Uable to attach or mount volumes: unmounted volumes=[xxxx], unattached volumes=[xxxx]: timed out wa