CVE-2018-12126已分配给MSBDS(微体系结构StoreBuffer数据采样),这是英特尔处理器的漏洞,属于新创建的MDS (Microarchitectural Data Sampling)类。

我正在尝试获取这些漏洞背后的微体系结构详细信息。我从MSBDS开始,也称为Fallout(cfr Meltdown),它允许攻击者泄漏存储缓冲区的内容。

出于某种原因,讨论微体系结构细节的网络安全论文通常不准确。
幸运的是,MSBDS论文引用了patent US 2008/0082765 A1(用于拍摄图片)。

对于我所收集的信息,似乎在MSBDS的情况下,该漏洞存在于内存消歧算法如何处理具有无效物理地址的负载。

这是用于检查存储缓冲区中的负载是否匹配的算法:

security - MSBDS(Fallout)背后的微体系结构细节是什么?-LMLPHP

302 检查加载所引用的页面的偏移量是否与存储缓冲区中任何先前存储所引用的页面的偏移量匹配。
如果此检查失败,则装载与任何存储都不匹配,可以在 304 处执行(已分派(dispatch))。
如果 302 检查,则将负载的虚拟地址的上部与商店的虚拟地址进行检查1。
如果找到匹配项,则加载匹配,并且在 308 处进行匹配,如果无法转发(例如从狭窄的存储到较宽的加载),则转发所需的数据或阻止加载本身​​(直到匹配存储提交)。
请注意,可以将同一虚拟地址映射到两个不同的物理地址(在不同的时间,但在商店转发窗口内)。通过此算法,而不是通过消耗存储缓冲区(例如,使用正在序列化的mov cr3, X)2,可以防止错误转发。
如果加载的虚拟地址与商店的任何虚拟地址都不匹配,则在 310 处检查物理地址。
这对于处理不同的虚拟地址映射到同一物理地址的情况很有必要。

段[0026] 添加:



这意味着,如果物理地址不可用,CPU将仅考虑地址的低(12)位3。
考虑到下面几行内容将解决TLB丢失的情况,因此仅留下不存在所访问页面的情况。

研究人员确实是这样提出攻击的:

char * victim_page = mmap (... , PAGE_SIZE , ...) ;
char * attacker_page = mmap (... , PAGE_SIZE, ...) ;

mprotect ( attacker_page , PAGE_SIZE , PROT_NONE ) ;

offset = 7;
victim_page [ offset ] = 42;

//Why people hate specpolines??
if ( tsx_begin () == 0) {
  //Read the stale value and exfiltrate it with a spectre gadget
  memory_access ( lut + 4096 * attacker_page [ offset ]) ;
  tsx_end () ;
}

//Reload phase of FLUSH+RELOAD
for ( i = 0; i < 256; i ++) {
  if ( flush_reload ( lut + i * 4096) ) {
     report ( i ) ;
  }
}

我不确定还会导致无效的物理地址(访问特权页面返回正确的物理地址)。

真的是因为对无效物理地址的处理才触发MSBDS漏洞?

1 SBA(存储缓冲区地址)组件既包含存储的虚拟地址又包含物理地址,可能仅包含物理地址的一部分(其余部分位于专用阵列中,可能称为物理地址缓冲区)。
2我尚不清楚是否真的有可能通过将页表条目更改为指向其他地方然后发出invlpg来触发错误转发。
3我的基本原理是,由于我们不是处于可恢复的情况下,因此负载是有缺陷的,因此,在性能不佳的情况下跳过另一次检查,以免出现转发错误的风险是值得的,因为这将使负载提前退休(并导致故障)。

最佳答案

内存一致性要求加载uop获得最近存储到目标内存位置的值。因此,内存顺序缓冲区(MOB)必须确定负载是否与程序顺序中的任何早期存储uop重叠。加载缓冲区和存储缓冲区都是循环的,每个加载都以程序顺序用加载之前的最年轻存储的ID进行标记(分配器在必须分配加载时知道它已分配的最后一个存储的ID )。这使MOB能够正确确定哪些存储在哪些加载之前。

从英特尔酷睿微体系结构和戈德蒙特微体系结构开始,调度程序包括一个推测性内存歧义消除(SMD)逻辑,该逻辑使用负载的IP来决定是否允许相对于STA指令无序地分派(dispatch)负载。所有较早的商店。这类似于分支预测如何使用获取的当前16字节块的IP来预测控制流,除了在这种情况下,IP用于内存消除歧义。如果RS中没有等待的STA,或者可以在与加载uop相同的周期中调度所有STA,则将忽略SMD结果并分派(dispatch)负载。否则,如果SMD决定阻止负载,则调度程序仅在所有较早的STA已被分派(dispatch)或将在与负载相同的周期中分派(dispatch)时才分派(dispatch)负载。对于某些负载,SMD始终会阻塞RS中的负载。

当将负载uop分派(dispatch)到负载AGU端口之一时,将使用指定的段基数,基址寄存器操作数,索引寄存器操作数,标度和位移来计算负载的有效地址(即线性地址)。同时,存储缓冲区中可以有存储。将负载的线性地址与执行了STA指令的所有较早存储的线性地址进行比较(即,该存储的线性地址可用)。可能还需要比较物理地址,但是此时负载的物理地址仍然不可用(此情况在专利中称为无效物理地址)。为了最大程度地减少负载的可观察到的延迟,MOB仅使用负载的线性地址的最低有效12位以及每个较早的存储执行快速比较。有关此比较的更多信息,请引用L1 memory bandwidth: 50% drop in efficiency using addresses which differ by 4096+64 bytes(但此处未讨论带掩码的uops)。这种逻辑称为松散网络,它构成了推测内存消除歧义机制的另一部分。自Pentium Pro以来,所有Intel微体系结构都支持松散网络(包括按顺序排列的Bonnell),但是确切的实现方式已更改,因为单个加载或存储uop可以操作的数据大小增加了,并且引入了从Pentium II开始的掩盖内存。与松散网络操作并行,将负载的线性地址发送到TLB以获取相应的物理地址并执行必要的页面属性检查,并执行段检查。

如果加载不与根据松散净结果调度加载时地址已知的任何较早存储重叠,则将加载请求发送到L1D。从RIDL漏洞我们已经知道,即使没有来自TLB的有效物理地址,也可能将某些数据转发到MOB,但前提是负载导致故障或协助。在第一级TLB未命中时,负载在负载缓冲区中被阻止,因此它尚无法继续其L1D访问。稍后,当请求的页面条目到达第一级TLB时,MOB会获知该虚拟页面的地址,该虚拟页面依次检查该页面上被阻塞的所有负载和存储,并通过按以下方式重播uops来解除阻塞TLB端口的可用性。

我认为,松散网络只需一个周期即可将给定负载的地址与存储缓冲区中任意数量的存储进行比较,并确定比该负载早的最年轻的重叠存储(如果有的话)。查找第一级TLB并在命中时向L1D提供物理地址的过程只需一个周期。这样便可以达到4个周期的最佳负载使用延迟(这还要求(1)正确推测物理页面地址,(2)基本+分配寻址模式,不带索引或零(3)段基址为零,否则至少要有一个周期的损失。有关更多信息,请参见评论中的讨论。

注意,如果未在松散网络中丢失了负载uop,则可以得出结论,该负载不与任何先前的存储区重叠,而是仅在分配负载uop时已执行所有较早uoop的STA的情况下。最低有效12位不同的两个线性地址不可能重叠。

如果松散的净结果表明负载与早期存储重叠,则MOB并行执行两项操作。其中之一是,存储器清除过程将继续使用精细网络(即完全线性地址比较)。如果在精细网络中错过了负载,则在可用时比较物理地址。否则,如果负载击中细网,则负载和存储重叠。请注意,对分页结构进行更改后,x86 ISA要求使用完全序列化指令。因此,在精细网络命中情况下,无需比较物理地址。除此之外,每当分派(dispatch)新的STA uop时,都会重复此整个过程,但是这次是将所有负载加载到负载缓冲区中。所有这些比较的结果将合并在一起,并且已针对所有较早的存储检查了负载后,最终结果将确定如何正确执行负载uop。

同时,MOB推测在负载中撞到松散网中的存储具有应转发给负载的值。如果加载和存储到同一虚拟页面,则推测是正确的。如果加载和存储到不同的虚拟页面,但虚拟页面映射到同一物理页面,则推测也是正确的。否则,如果加载和存储到不同的物理页面,则MOB会困惑,从而导致一种称为4K别名的情况。但是,等等,让我们回退一点。

可能无法将存储数据转发到负载。例如,如果负载没有完全包含在存储中,那么它必须等待直到提交存储,然后才允许负载继续进行并从缓存中获取数据。另外,如果尚未执行商店的STD uop(例如,取决于长等待时间的uop)怎么办?通常,仅在满足商店转发要求时才从存储缓冲区转发数据。但是,MSBDS漏洞表明并非总是如此。特别是,当负载导致故障或辅助时,存储缓冲区可以将数据转发到负载,而无需执行任何存储转发检查。从有关MDS的英特尔文章中:



显然,即使尚未执行STD uop,也可以转发数据。但是数据将从何而来?好了,解除分配后不会清除存储缓冲区条目的数据字段。数据字段的大小等于存储uop的宽度,可以通过测量执行最宽的可用存储指令(例如,来自XMM,YMM或ZMM寄存器)所需的存储uop数量来确定。在Haswell上似乎是32字节,在Skyake-SP上是64字节。存储缓冲区条目的每个数据字段都很大。由于永远不会清除它,因此它可能会保留来自存储的某些随机数据组合,而这些存储恰好是在该存储缓冲区条目中分配的。当负载碰到松散的网并造成故障/辅助时,负载指定宽度的数据将从存储缓冲区转发到负载,甚至不检查STD的执行或存储宽度。这样一来,加载就可以从一个或多个存储中获取数据,这些存储甚至可能已经被提交了十亿条指令。与MLBDS相似,转发的某些数据部分或整个数据可能是陈旧的(即,不属于占据条目的商店)。

这些详细信息实际上仅由英特尔提供,而并非由辐射白皮书提供。在本文中,作者在禁用了KPTI的系统上进行了实验(第4节)(我将解释原因),但是他们没有利用Meltdown漏洞。实验是这样进行的:

  • 攻击者执行一系列存储,所有存储在高速缓存层次结构中丢失。存储的数量至少与存储缓冲区条目的数量一样大。
  • 调用一个内核模块,该模块执行一系列存储,每个存储在不同内核页面中的不同偏移量。存储的值是已知的。存储的数量在1至50之间变化,如图5所示。然后,内核模块返回给攻击者。
  • 攻击者将一系列加载到用户页面(与内核页面不同)的偏移量相同。每个用户页面仅在虚拟地址空间中分配,并且已撤消访问权限(通过调用mprotect(...,PROT_NONE),将其标记为User and Not Present)。表1显示不存在的Supervisor页面不起作用。加载数量与内核模块执行的存储数量相同。然后使用传统的FLUSH + RELOAD攻击来泄漏已加载的值。

  • 第一步尝试使存储缓冲区尽可能多地被占用,以延迟从内核模块提交存储。请记住,错误的存储转发仅适用于占用的存储缓冲区条目。第一步有效,因为商店必须按顺序提交。第三步,重要的是获得宽松的网络点击。请注意,在此实验中,作者没有想到要泄漏任何过时的数据,他们只是想从内核存储中获取希望仍在存储缓冲区中的数据。更改当前特权级别时,在执行新特权级别中的任何指令之前,所有指令都将退出。即使在RFO请求完成之前,存储也可以快速退休,但是它们仍然必须在存储缓冲区中等待顺序提交。认为以这种方式在存储缓冲区中具有来自不同特权级别的存储不是问题。但是,当攻击者开始执行加载时,如果与当前正在分派(dispatch)的负载具有相同偏移量的存储仍在存储缓冲区中,则在推测性转发(不陈旧)数据时,会发生松散的网络命中。你知道其余的。

    启用KPTI后,大多数内核页面与用户页面位于不同的虚拟地址空间中。因此,当从内核模块返回时,内核必须通过将值写入CR3寄存器来切换地址空间。但这是一个序列化操作,这意味着它将暂停管道,直到所有(内核)存储都被提交为止。这就是为什么作者需要禁用KPTI才能使其实验正常工作(即,存储缓冲区为空)。不幸的是,由于Coffee Lake R具有缓解Meltdown的硬件功能,因此Linux内核默认情况下会禁用此处理器上的KPTI。这就是为什么作者说硬件缓解措施使处理器更加脆弱。

    英特尔文章(而不是本文)中描述的内容表明,MSBDS的危害远不止于此:故障/辅助负载还可能从存储缓冲区泄漏过时的数据。英特尔的文章还表明,MSBDS可在兄弟逻辑内核之间工作:当逻辑内核进入休眠状态时,为其静态分配的存储缓冲区条目可能会被另一个逻辑内核使用。稍后,如果逻辑内核再次变为 Activity 状态,则会对存储缓冲区进行静态分区,这可能使该内核能够从其他内核写入的条目中泄漏过时的数据。

    所有这些表明,启用KPTI不足以减轻MSBDS。同样,第6节中的论文中建议的缓解措施(越过安全边界使用MFENCE刷新存储缓冲区)也是不够的。适当的MDS缓解措施here进行了讨论。

    我不知道第3.2节中的作者如何从英特尔专利的以下引言中得出结论:



    以下:



    整个专利没有提到比较12位,也没有说负载必须出错才能发生错误的存储转发。另外,结论本身是不正确的,因为12个最低有效位不必完全匹配,并且负载也不必出错(但是攻击只有在出错时才起作用)。

    MSBDS与Meltdown的不同之处在于,攻击者从位于单独虚拟地址空间中的内核页面泄漏数据。 MSBDS与SSB的不同之处在于,攻击者对SMD进行了错误的训练,因此它会在分派(dispatch)负载之前的所有STA之前分派(dispatch)负载。这样,负载不会被打到松散的网络中的机会就更少了,这使MOB可以将负载发布到L1D高速缓存,并根据程序顺序获得可能不是最新值的值。可以通过将IA32_SPEC_CTRL[2]设置为1来禁用SMD。禁用SMD后,调度程序将像在Pentium Pro中一样处理负载。

    值得一提的是,有一些加载和存储操作与我上面描述的不同。示例包括来自MFENCESFENCECLFLUSH的内存操作。但是它们在这里不相关。

    08-16 10:51