cpu-architecture - MESI-读取当前正在修改的数据时会发生什么?

标签 cpu-architecture mesi

如果我有一个缓存行数据并且第一个字节正在被原子修改,我仍然可以同时从该缓存行读取不同字节的数据吗?或者我会尝试阅读了解正在发生的原子更新并等待它吗?

我试图理解上述场景对性能的影响。

最佳答案

缓存一致性是按行粒度维护的,目前大多数 CPU 中通常为 64B。 进行修改的核心将首先请求整条线的所有权,这意味着所有其他核心必须使它们的副本无效(如果它们有这样的副本)。尝试读取的任何其他核心都必须请求该行,这将导致窥探被发送到修改核心。从那里你有两个选择:

  1. 修改核心完成了读取-修改-写入序列,并且该行与最新修改的数据一起位于其缓存中 - 在这种情况下,监听将启动 WB 序列,更新后的行将可供所有,第二个核心可以从中读取任何字节。

  2. 修改核心通过加载获取了该行,但其存储仍未进行更改(这是可能的,因为存储通常在管道中稍后执行,而加载通常是推测性完成的)。在这种情况下,核心必须保护线路不被窥探,通常是通过为此类操作实现内部锁定。请注意,例如在 x86 上,大多数原子读取-修改-写入操作需要锁定前缀。另请注意,正常的读+写(非原子)序列只会在该点丢失该行,并稍后再次获取该行以进行存储,从而失去一致性。

编辑:按照 Paul 的评论,确实可以设计一个允许子行粒度跟踪的缓存系统。这基本上意味着将 MESI 协议(protocol)的基本 block 与用于缓存的基本 block 大小解耦,您需要为每个子集添加状态位(但仍然可以对所有子集使用单个标签),仅使本地子集无效,并最终执行以某种方式合并以重新获得完整的线路。然而,开销会使其非常罕见,而且我不熟悉商用 CPU 这样做只是为了避免错误共享。不管怎样,由于这样的子 block 可能不是字节大小的,所以最初的问题仍然适用于同一 block 内的字节。

关于cpu-architecture - MESI-读取当前正在修改的数据时会发生什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32424817/

相关文章:

cpu - 存储缓冲区是否发送读取无效消息或使请求消息无效?

x86 - 驱动程序将如何使用MONITOR指令(_mm_monitor内部函数)?

operating-system - "Protection rings"和 "CPU modes"是一回事吗?

memory - 共享内存和分布式内存的主要区别

assembly - PIC 是否处理不可屏蔽中断?

c - 如何从命令行使所有(数据)缓存失效?

x86 - 现代 x86 CPU 使用什么缓存一致性解决方案?

cpu - 如果在独占缓存访问期间发生写操作,为什么会出现数据竞争?