Spectre Attacks: Exploiting Speculative Execution
Published2019 IEEE Symposium on Security and Privacy (SP)
It appeared in a journal, conference or book, which normally review work before accepting it. Even so, one study is never the final word.
Abstract
No abstract is available for this paper.
Research Analysis
Written by Kurz, not by the authors of the paper. The abstract above is the authors' own.
- Last revised
- Version
- 1.0
Overview
Modern processors do not wait for a slow memory read before deciding which way a branch goes. They guess, run ahead, and throw the work away if the guess was wrong. Because the architectural state (registers and memory) is restored, this was assumed to be invisible to security. The paper, by Paul Kocher and co-authors (ten on the preprint, twelve in the published version, which adds Jann Horn and Anders Fogh), shows that the assumption is wrong: the guessed work can touch data it should not touch, and what it leaves behind in the cache can be measured afterwards.
The paper was published at the IEEE Symposium on Security and Privacy in 2019. The authors had released it as a preprint on arXiv in January 2018, together with the related Meltdown attack, and this analysis follows that public text. It matters because the isolation between processes, between a browser tab and the rest of the browser, and between containers all rest on the idea that the CPU runs a program's safety checks faithfully.
Worth knowing first: what a cache is and why a cached read is faster, how branch prediction and out-of-order execution work, and what a side channel is.
Contribution
- A new class of attacks, called Spectre, in which an attacker makes a victim program speculatively run instructions that would not run in a correct execution (the paper calls them transient instructions) and leak a secret through a side channel.
- Two concrete variants. One exploits conditional branches, by training the predictor and then giving an out-of-bounds index (a bounds check bypass, CVE-2017-5753). The other exploits indirect branches, by poisoning the branch target buffer so that a chosen "gadget" in the victim runs speculatively (CVE-2017-5715).
- Working proofs of concept in native code and in JavaScript running in a browser, which cross a process boundary and a sandbox boundary.
- A discussion of other variants and of mitigation options, and a call for a clear contract between hardware and software about what a processor may leak.
Methodology
The attack has three steps. The attacker finds code in the victim that can act as the sending side of a covert channel, makes the processor execute it speculatively, and then reads the result through the cache with Flush+Reload or Evict+Reload timing.
For the conditional-branch variant, the attacker first calls the code with valid inputs so that the predictor expects the bounds check to pass, then calls it with an out-of-range index while the array size is not in the cache. The processor guesses wrongly and reads array2[array1[x] * 256], which pulls into the cache a line whose address depends on the secret byte. Repeating with different indexes reads memory one byte at a time. For the indirect variant, the attacker trains the branch target buffer from its own address space, since only the virtual address of the target matters and the match on the branch address can be partial.
The experiments are demonstrations on real machines. The authors tested Intel Ivy Bridge (i7-3630QM), Haswell (i7-4650U) and Skylake (a Xeon on Google Cloud), AMD Ryzen, and some Samsung and Qualcomm ARM processors in phones, on 32 and 64-bit Linux and Windows.
Findings
These are the authors' reported results.
- The vulnerability was observed on all the x86 processors tested, and on some ARM processors, so the problem is in the idea of speculation and not in one vendor.
- In native code, the authors read the entire address space of a victim program, including its secrets. The unoptimized code in their appendix reads about 10 KB/s on an i7 Surface Pro 3.
- A JavaScript program running in Chrome read private memory of the process that runs it. Because the browser coarsens its timer, the authors built a high-resolution clock from a Web Worker thread that decrements a shared value.
- Mistraining across hyper-threads of the same Intel core worked, Skylake showed mistraining based on branch history, and some indirect-branch tests worked on Skylake but not on Haswell. The branch target buffer indexing needed only 20 bits of the branch address in their tests.
- Meltdown, described as related, differs: it does not use branch prediction, it relies on an Intel-specific privilege issue to read kernel memory, and the KAISER patch that stops it does not stop Spectre.
- Mitigations the authors discuss are partial: serializing instructions such as
lfence(whose guarantees were not defined at the time), costly compiler-inserted barriers, disabling hyper-threading and flushing predictor state, microcode changes. They call all of these stop-gap measures.
Critical Analysis
The paper is clear and reproducible in its core, and its main value is to show a whole new category of bug. Read it with these points in mind.
- It is a set of proofs of concept, not a measurement of how much real software is exploitable. The authors say exploitability depends on the victim CPU, the compiler's choices and the attacker's access.
- The risk is concentrated. The attacker must usually run code on the same CPU as the victim. The authors consider network-based attacks conceivable but treat same-machine code as the main danger. The leak is of secrecy, not integrity.
- The mitigation section is tentative. It ends with "stop-gap measures pending further research", and the discussion of what future processors might do is speculation. In our reading, the later industry response (new instructions, changed compilers and operating systems, new hardware) confirms the direction but is outside this paper.
- Some work overlaps. The paper itself notes that it partly overlaps independent work at Google's Project Zero.
- The text we analyzed is the preprint. Details of the published proceedings version may differ.
Further Research
- Precise hardware/software contracts that say which state a processor may leak, so that software can be shown safe.
- Compiler and operating-system defenses measured for their performance cost, since the paper warns that comprehensive barriers hurt performance.
- Tools to find vulnerable code, for example with fuzzing and static analysis, as the authors suggest.
- Processor designs that do not let speculative work change shared state, and other channels than the cache (bus contention, ALU activity, the predictor itself).
Discussion ยท 0
Sign in to join the discussionNo posts yet. Be the first to start the discussion.