-
-
[翻译]计时瞬态执行:针对英特尔处理器的新型侧信道攻击
-
发表于: 2023-4-28 10:38 11363
-
瞬态执行攻击(Transient Execution Attack)是一种利用现代 CPU 优化技术漏洞的攻击。 侧信道(Side-channel)是瞬态执行攻击泄漏数据的关键部分。 在这项工作中发现了一个漏洞,即瞬态执行中 EFLAGS 寄存器的更改可能会对英特尔处理器中条件代码跳转指令(Jcc,Jump on condition code)产生附加影响。本研究基于此发现提出了一种新的侧信道攻击,它利用瞬态执行和 Jcc 指令的时间来传递数据。 这种攻击将秘密数据编码到寄存器的变化中,这使得上下文的执行时间稍微变慢,攻击者可以通过测量来解码数据。 这种攻击不依赖缓存系统,也不需要手动将 EFLAGS 寄存器重置为攻击前的初始状态,这可能会使其更难检测或缓解。 在配备了 Intel Core i7-6700、i7-7700 和 i9-10980XE CPU 的机器上实现了这个侧信道。 在前两个处理器中结合其作为Meltdown攻击的侧信道,可以达到100%的泄漏成功率。
现代 CPU 的复杂性和积极优化及其许多微体系结构特性提高了性能,但它们也产生了一系列安全漏洞 。 这种复杂性和优化是许多安全问题的根源,包括侧信道攻击、Meltdown攻击、Spectre攻击、微架构数据采样(MDS)攻击、故障注入攻击等。 现代 CPU 的复杂性和动态性使其成为安全研究人员和开发人员发现和缓解的具有挑战性的目标,并成为用户持续关注的问题。 随着计算机安全领域的不断发展,将需要新的技术和对策来跟上不断变化的威胁形势。
许多微架构侧信道攻击都是基于缓存系统的附带作用和状态。 有很多方法可以通过缓存系统泄露信息。 在2005年第一个缓存计时攻击(Cache-timing Attack)被发现之后,出现了多种变体:如 evict+time (2006) 、flush+reload(2014) 、prime+probe(2015) 、flush+flush(2016) 。 新的缓存侧信道攻击仍在不断被发现,例如缓存替换策略(2020)、streamline(2021)、使用缓存脏状态(2022)、缓存一致性(2022)。此外,一些攻击并不直接依赖于缓存系统,例如 PortSmash、PlatyPus、PMU-Spill。
瞬态执行攻击,包括 Meltdown、Spectre 和 MDS 攻击都利用了现代 CPU复杂和积极的优化,从而通过瞬态泄漏敏感信息。 瞬态执行攻击包括五个阶段:(1) 微架构准备,(2) 触发故障,(3) 将秘密数据编码到隐蔽通道,(4) 刷新瞬态指令,以及 (5) 解码秘密数据。 阶段 3 和 4 的成功取决于侧信道,这需要信道状态被初始化或设置为特定状态。 例如在 flush+reload 攻击中,攻击者需要在阶段 1 中从缓存中刷新被监控的内存行,并在阶段 4 中通过将内存行的一个索引加载到缓存中来对秘密数据进行编码。这允许攻击者测量在阶段 5 中被监控的内存行被加载到缓存中以解码数据的时间。
逆向工程试图揭示有关处理器微体系结构行为的信息,尽管缺乏公开可用的实现细节。 英特尔的软件开发人员手册提供了对指令性能特征的更多见解,强调某些指令可能由于其功能要求而导致流水线停顿或其他影响。 例如,MFENCE 指令在流水线中引入了一个停顿,直到所有先前的内存操作都已完成。了解这些细微差别对于优化代码以最大限度地提高特定处理器架构的性能并识别潜在的安全漏洞至关重要。
本工作对瞬态执行攻击的行为和附带作用进行了深入研究,并发现了因特尔处理器中实施的漏洞。 具体来说,EFLAGS 寄存器在瞬态执行中的变化可能会影响其后的 Jcc 指令。 基于此发现,本文引入了一种新颖的侧信道攻击,它利用 Jcc 指令的瞬态执行时间。 瞬态执行中 EFLAGS 的变化可能会使一些 Jcc 指令在它之后稍微变慢。 如下图所示,通过将秘密数据编码到 EFLAGS 寄存器,可以测量 Jcc 指令上下文的执行时间来解码数据,而无需在瞬态攻击的第 1 阶段将 EFLAGS 寄存器重置为其初始状态。
这种攻击不依赖于缓存系统,与之前的侧信道攻击相比,这可能使其更难检测。在使用 Intel Core i7-6700 和 i7-7700 以及 i9-10980XE CPU 的真机中实现了这个侧信道。 使用侧信道攻击构建 Meltdown 攻击,并在 i7-6700 和 i7-7700 上对其进行评估。 在实践中,侧信道可以达到 100% 的成功率。 为了减轻这种攻击,根据评估提出了几种实用的缓解方法。
CPU的每个内核的微体系结构由几个组件组成,例如缓存系统,包括分支预测器的前端单元(Frontend),乱序执行单元等。CPU内核是处理器的核心,负责指令的执行。 缓存系统用于存储经常访问的数据和指令,前端单元负责指令获取和解码,乱序执行单元负责指令的乱序执行。 由于现代 CPU 是一个微体系结构复杂的系统,大多数商业 CPU的微体系结构是一个黑盒,许多研究试图在其中进行逆向工程。
微体系结构中的侧信道攻击是一类利用程序的附带作用来泄露有关程序执行的信息的攻击。 侧信道可以是缓存系统、分支预测器、电流等。例如,缓存系统可以用于泄漏有关程序内存访问模式的信息,分支预测器可用于泄露有关程序控制流的信息。 微架构中大多数侧信道攻击的根本原因是共享资源,这是CPU性能优化的关键之一。
自发现Meltdown和 Spectre攻击以来,瞬态执行攻击一直是安全社区的热门话题,其发展如下图所示。 瞬态执行可能是由故障、分支预测错误、缓存未命中等引起的。 英特尔和 AMD 等 IP 供应商已经发布了微码更新,以减轻瞬时执行攻击。
假设:可以通过瞬态执行攻击访问秘密数据。 瞬态执行攻击有很多,例如 Meltdown、Spectre、Foreshadow、ZombieLoad等。尽管大多数现有攻击都已得到缓解,但它们可能在 CPU 和设备中存在未公开的瞬态执行漏洞 已在未来被利用。
威胁模型:攻击者在非特权模式下运行。 还有另一个受害进程在同一台机器上运行。 本研究的威胁模型定义为:攻击者利用瞬态执行时序来恢复瞬态执行攻击中获取的秘密数据。
将攻击实施为 Meltdown 攻击的侧信道,如前图所示。攻击由两个阶段组成:在第一阶段,触发瞬态执行并通过 EFLAGS 寄存器对秘密数据进行编码。 在第二阶段测量 Jcc 指令上下文的执行时间以解码数据。 要通过二进制标志对秘密进行编码,需要使用迭代 test_num 来设置标志。 如果 test_num 等于 secret,则标志将被设置并且 secret 将被成功编码。
将 secret_addr 标记为秘密数据的地址。 而offset就是secret_addr的偏移量。 EFLAGS 指令是可以改变EFLAGS 寄存器的指令。 Jcc 指令是可以受 EFLAGS 寄存器影响的指令。 可用的指令集在下表中列出。使用 x86intrin.h 中的 __rdtsc 来获取 CPU 的时间戳计数器。
secret_addr 是内核空间中的地址。 并且攻击者以非特权模式运行,无法访问 secret_addr。 偏移量是 secret_addr 的偏移量。 在 TSX 交易中,攻击者会尝试通过 sub 指令访问 secret_addr。 故障会导致瞬时执行。 在瞬态执行期间,如果 *(secret_addr+offest) 中的秘密数据等于 i,则 ZF 可以设置为 1。 瞬态执行后ZF会恢复为0。 ZF 会被JZ 指令用来判断是跳转到相等标号还是不等标号。 在实验中,如果*(secret_addr+offest)中的秘密数据等于i,上下文的执行时间会比*(secret_addr+offest)中的秘密数据不等于的上下文执行时间慢 我。 max_time 是上下文的最大执行时间。 argmax 是秘密数据,如下图中的分布所示。max_time 和 argmax 可用于解码秘密数据。
研究者在 Intel i7-6700、i7-7700 和 i9-10980XE CPU 中实施了攻击。 该实验在内核版本为 4.15.0(i7-6700、i7-7700)的 Ubuntu 16.04 xenial 和内核版本为 5.15.0(i9-10980XE)的 Ubuntu 22.04 jammy 中运行。 使用侧信道构建 Meltdown 攻击,从用户空间读取内核内存,并在前两个处理器中实现 100% 的泄漏成功率。
在实验中,发现 EFLAGS 寄存器对 Jcc 指令执行时间的影响并不像缓存状态那样持久。 在瞬态执行后大约 6-9 个周期,Jcc 执行时间将不会构建侧信道。
根据经验,攻击需要重复数千次才能获得更高的准确性。 对于上图的代码,使用事务内存实现 Intel TSX 来完全抑制异常。 还使用系统中断处理程序来抑制异常并达到相同的效果。 TSX 比瞬态执行攻击的系统中断处理程序更有效。
虽然时序argmax的统计分布可以用来解码秘密数据。 由于噪声,平均时钟的分布不能用作侧信道,如上图所示。受害者代码如下所示,与 Meltdown中的 POC 相同。 实验在与攻击者在同一个物理内核但不同的逻辑内核中并行运行它以获得更高的读取率。 受害者将尝试将秘密字符串缓存在缓存行中。
为了减轻瞬态执行时序攻击,可以使用延迟 Jcc 指令或在瞬态执行后重写 EFLAGS 寄存器。
Jcc 指令的实现在不同条件下不应有时序或其他附带作用,以避免对抗性执行测量。
如果在更改 EFLAGS 寄存器后不立即执行 Jcc 指令,则可以减少 EFLAGS 寄存器的影响。 10 个周期足以减少 EFLAGS 寄存器的影响。 .rept count 重复 .rept 指令和下一个 .endr 指令之间的行序列 count 次。 通过NOP指令延迟Jcc指令,可以减少EFLAGS寄存器对执行时间的影响。 延迟的方法有很多种,这里只举一个例子。
赞赏
- [翻译]针对Model X无钥匙系统的远程攻击 23104
- [翻译]计时瞬态执行:针对英特尔处理器的新型侧信道攻击 11364
- [翻译]大疆无人机安全与DroneID漏洞 27911
- [翻译]基于充电桩的电动汽车勒索攻击 12489
- [翻译]基于DVFS的GPU电磁侧信道窃听攻击 22942