x86 - 在英特尔酷睿 i3/i7 的情况下,从缓存集驱逐后数据的去向

标签 x86 intel cpu-architecture processor cpu-cache

L1/L2 缓存在 Intel 中是包含性的,L1/L2 缓存是 8 路关联,这意味着在一个集合中有 8 个不同的缓存线存在。缓存行作为一个整体操作,这意味着如果我想从缓存行中删除几个字节,将删除整个缓存行,而不是我想要删除的唯一那些字节。我对吗 ?

现在,我的问题是每当 一个集合的缓存线被从缓存中移除/驱逐,无论是通过其他一些进程还是通过使用 clflush(缓存线/块的手动驱逐),系统是否将该缓存线的驱逐数据存储在某处(在任何缓冲区中,注册等), 以便下次它可以从该位置加载数据以减少与从主内存或更高级别缓存加载数据相比的延迟,总是简单地使 无效缓存中的数据,下次从下一个更高级别加载数据。

任何建议或文章的任何链接将不胜感激。提前致谢。

最佳答案

L1/L2 不一定包含在内,只有最后一级缓存是已知的,在 i7 上将是 L3。
您说缓存行是基本缓存元素是正确的,您必须抛出整个缓存行才能填充新的缓存行(或在使该单行无效时)。您可以在此处阅读更多相关信息 - http://www.tomshardware.com/reviews/Intel-i7-nehalem-cpu,2041-10.html

当一行被移除时,采取的行动取决于它的 MESI 状态(MESI 及其派生类是缓存一致性维护的协议(protocol))。如果该行被修改(“M”),那么数据必须“回写”到下一级缓存(如果未命中,它可能会在那里分配,或者“直写”到下一级 - 取决于缓存维护的策略)。请注意,当您到达最后一级缓存时,您必须命中,因为它包含在内。当从最后一级缓存中驱逐一行时 - 它必须被写入内存。无论哪种方式,未能写回修改后的行都将导致失去一致性,这很可能会导致不正确的执行。

如果该行未被修改(无效、独占或共享),则 CPU 可能会在不需要回写的情况下静默删除它,从而节省带宽。顺便说一下,在更复杂的缓存协议(protocol)(如 MESIF 或 MOESI)中还有其他几种状态。

您可以通过谷歌搜索“缓存一致性协议(protocol)”找到很多解释。如果你喜欢更可靠的来源,你可以引用任何 CPU 架构或缓存设计教科书,我个人推荐 Hennessy&Patterson 的“计算机架构,一种定量方法”,有一整章关于缓存性能,但这里有点偏离主题。

小更新:从 Skylake 开始,某些 CPU(服务器段)不再具有包容性 L3,而是具有非包容性(以支持增加的 L2)。这意味着当 L2 老化时,干净的行也可能被写回,因为 L3 通常不保存它们的副本。

更多详情:https://www.anandtech.com/show/11550/the-intel-skylakex-review-core-i9-7900x-i7-7820x-and-i7-7800x-tested/4

关于x86 - 在英特尔酷睿 i3/i7 的情况下,从缓存集驱逐后数据的去向,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19416964/

相关文章:

linux - 这段汇编代码对命令行参数做了什么

c++ - VC++ 2010 - 尝试 DLL 时未声明的标识符,少量代码

cpu - 如何使用(读/写)CPU 缓存 L1、L2、L3

performance - 小阵列最快的偏移读取

c - llvm:如何生成避免基于 RIP 的寻址模式的 x64 代码?

optimization - Intel Skylake 的统一调度器与 AMD Zen 的单独调度器

x86 - 监听请求是否发送到多节点设置中的所有核心?

linux - 我们可以在 OpenWrt linux 操作系统上运行 DPDK 应用程序吗?

linux - fork: retry: 资源暂时不可用

c++ - 如何确定要为体系结构启用或禁用的功能标志