Page 5 of 10
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 9:30 am
by bluemoon
Sik wrote:OK the more stuff gets disclosed the more things seem to change so huuuuh screw it. How do Meltdown and Spectre actually work?
Google Project Zero has the descriptions.
Basically, It's the nature of speculative execution creating observable effects on the cache. Think about the following code
Code: Select all
// flush caches
if index1 < array1.length {
value1 = array1[index1] // index1 is bogus, pointing to kernel address
index2 = (value1 & 1) * 0x100 + 0x200 // index2 := 0x100 or 0x300
if index2 < array2.length {
value2 = array2[index2] // legal access
}
}
In theory, the entire if-block should not be executed, but with speculative execution (and if array1.length is not in cache), the branch is executed anyway and results will be discarded later, "supposedly creating no side effect" to the program's logic. However, running the inside block in "speculative execution" will bypass any permission checking and either array2[0x100] or array2[0x300] will be fetched to cache.
Now by re-reading array2[0x200] and array2[0x300] and check the timing, you can deduce the lower bit of value1, which is the content of kernel memory. Repeat all these and you have a full memory dump.
For meltdown its similar:
Code: Select all
mov rax, [kernel_address] // trigger exception, which can be handled gracefully and return rax = 0
and rax, 1
mov rbx, [user_address + rax* 0x100]
if [user_address + 0x100] is in the cache, the bit is 1.
These problems cannot be easily fixed without architectural changes, thus the workaround is simply unmap (most) kernel address from user context.
NOTE: credits to project zero.
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 10:17 am
by Korona
Yes, Meltdown attacks kernel memory with the cache-based speculative execution attack that bluemoon described. It can only be mitigated by hiding the kernel (which is what the patches do) or by mapping the whole kernel as uncached (which is not acceptable for performance reasons).
Spectre is more complex. It attacks user-space memory. It does not necessarily depend on the cache. One of the Spectre attacks trains the branch predictor to speculatively execute an instruction series after an indirect branch (i.e. this instruction series is not committed to the real register/memory state and its effects are not visible from an architectural PoV) and then uses timing measurements to extract information from that.
Note that, contrary what ~ believes, neither Spectre nor Meltdown depend on sensitive data being in the cache. The attacks only use the cache to measure timings, they do not access, read, or extract the contents of the cache. In particular, the attacks only access cached auxiliary buffers (containing random data) and not the cache lines that contain real data.
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 10:35 am
by bluemoon
Korona wrote:Note that, contrary what ~ believes, neither Spectre nor Meltdown depend on sensitive data being in the cache. The attacks only use the cache to measure timings, they do not access, read, or extract the contents of the cache. In particular, the attacks only access cached auxiliary buffers (containing random data) and not the cache lines that contain real data.
Indeed. No memory from kernel is directly accessed, they get discarded and not visible to you. The sensitive information don't even need to be in cache. What you need to do is measure the side effect left on your own legally accessible buffer and indirectly deduce the sensitive information.
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 5:54 pm
by Sik
OK, from what I'm understand (now that I see that code snippet):
- Trick the CPU into reading the byte you want to snoop into the cache
- Mask (AND) the value with the bit you want to get
- Use said bit as part of an offset for an address
- Try to read from the address that would be used if the bit was 1
The timing of the last access would tell you whether the bit you tried was a 0 (cache miss, long delay) or 1 (cache hit, short delay).
The difference between Meltdown and Spectre is that the former can go across privilege boundaries (hence being able to read kernel memory) while the latter can't (hence only giving access to data the process already had access to), if I'm understanding it correctly.
The way this works makes me doubtful that Spectre is useful at all. To pull it off you'd likely need to get your own code running on the machine (anything else is very unlikely to work), and if you can do that you may as well just read the data you want directly. Meltdown at least would be more useful in that it allows something that normally shouldn't be allowed.
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 6:21 pm
by Korona
The are Spectre proof-of-concepts that read your Chrome passwords from JavaScript (even though Chrome already randomizes its timing functions). Spectre is definitely useful.
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 7:41 pm
by Sik
Ugh, right, external scripts run in the same context. Though it makes me wonder how you can get javascript to read a specific address so reliably (you'd think that being a script already mangles any low-level access too much to make it work).
We need better sandboxing and not just for scripts. Take a media player: why should the codec have direct access to the file it's taking, rather than just being given a stream? Or why should the GUI have direct access to that when it just needs to send commands and query the current state? Etc. Right now we rely on boundaries imposed by programming languages but those don't matter for somebody looking to exploit a system. But if performance is already a huge issue when going from userland to kernel, imagine if the user process itself was also split into many contexts =/
Re: CPU bug makes virtually all chips vulnerable
Posted: Fri Jan 05, 2018 8:06 pm
by Korona
The trick is that you don't actually need to read arbitrary addresses. Remember that the read is only executed speculatively. You "just" need to train the branch predictor to speculatively jump to a certain instruction sequence. That instruction sequence itself is part of the normal .text segment, similar to a return-oriented programming attack. The cache timing side-channel can then be abused on a JavaScript UInt8Array or similar data structure.
Actually, browsers already isolate some components into own processes (e.g. Flash and other plugins). However, JavaScript needs to be able to access the DOM, so it cannot be separated from the rendering.
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 12:47 am
by bluemoon
Sik wrote:We need better sandboxing and not just for scripts. Take a media player: why should the codec have direct access to the file it's taking, rather than just being given a stream? Or why should the GUI have direct access to that when it just needs to send commands and query the current state? Etc.
Call it micro-app
(vs micro-kernel).
But in reality, it create a lot of trouble maintaining the sandbox parameters per each module. At the end, users don't care and just treat the whole media player plus the codec as a whole, the sensible difference is the way they linked together (static linking, dynamic linking, COM mechanic, pipe, etc), people would just sandbox the whole app instead.
If you are providing the codec in a OS-level service, it might make sense to give enough isolation, but then the OS provided codec would "just be trusted".
Korona wrote:The are Spectre proof-of-concepts that read your Chrome passwords from JavaScript (even though Chrome already randomizes its timing functions). Spectre is definitely useful.
There are multiple ways to implement high resolution timer without RTC. The easiest way is do a polyfill over array and use that time as a "standard unit" of time, and the branch with more "unit of time" denote a cache miss.
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 1:08 am
by Sik
Well, the idea would be more to isolate the individual parts making an application so an exploit in one would make it much harder to exploit the others, not necessarily for the application to be visibly split apart. Basically take the kind of encapsulation we've come to see in modern languages and have it enforced at the hardware level.
The problem is that this requires CPU support and unless somebody can find a really clever way to implement it with the current hardware, we're stuck with waiting for ISAs to be changed to allow that. Not to mention first figuring out how such a thing would work.
Korona wrote:Actually, browsers already isolate some components into own processes (e.g. Flash and other plugins). However, JavaScript needs to be able to access the DOM, so it cannot be separated from the rendering.
Technically it could (through IPC)... it would just be horribly slow, which is kind of the point I was making (that we need some way to sandbox better without that massive performance loss).
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 8:47 am
by mariuszp
Could they perhaps fix both Spectre and Meltdown in hardware by simply deleting the results of speculative mis-execution from the cache, just like they are deleted from registers?
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 9:16 am
by Korona
Meltdown can be fixed in hardware by only speculating executing code from the same privilege level. Spectre is harder to fix as it does not violate hardware privilege levels and only attacks software isolation.
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 9:29 am
by mariuszp
Korona wrote:Meltdown can be fixed in hardware by only speculating executing code from the same privilege level. Spectre is harder to fix as it does not violate hardware privilege levels and only attacks software isolation.
Yes, but Spectre depends on using bits from the speculatively-read value (whether userspace or not) being used to index into an array, and checking the effect on the cache. If the cache effects are reversed (just as register effects are reversed) after mis-speculation, it would not be possible to exploit anymore, right?
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 1:58 pm
by Sik
Yeah (or just marking the relevant cache row as invalid, don't even bother flushing it), though that may be harder to implement than it sounds since a mispeculated access may share a row with an access that was intended (which wouldn't be the case in Spectre, but more likely to be the case with normal code, and as such needs to be handled). May be doable though, albeit only in new CPUs of course.
It does leave us wondering if there are other cache-induced potential exploits though. In fact, mispeculation causing data loading into cache already has another side effect, which is to needlessly hamper performance of the program (as it's inevitably evicting other cached data), but getting rid of speculation will harm the performance of CPUs overall. Of course this would be much less dangerous than exposing data it shouldn't =P
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 2:50 pm
by mariuszp
Sik wrote:Yeah (or just marking the relevant cache row as invalid, don't even bother flushing it), though that may be harder to implement than it sounds since a mispeculated access may share a row with an access that was intended (which wouldn't be the case in Spectre, but more likely to be the case with normal code, and as such needs to be handled). May be doable though, albeit only in new CPUs of course.
It does leave us wondering if there are other cache-induced potential exploits though. In fact, mispeculation causing data loading into cache already has another side effect, which is to needlessly hamper performance of the program (as it's inevitably evicting other cached data), but getting rid of speculation will harm the performance of CPUs overall. Of course this would be much less dangerous than exposing data it shouldn't =P
Just invalidate the cache line in the case where previously it was already invalid. If there was something already in that cache line then Spectre woudl not have worked anyway, so that case can be ignored.
Re: CPU bug makes virtually all chips vulnerable
Posted: Sat Jan 06, 2018 5:22 pm
by Korona
That justs introduces a races condition between the timing measurement and the invalidation. It makes the attack harder but not impossible.