浅谈CPU漏洞


发布人:Zer0 Sec_lionhoo分类:网络安全浏览量:1101发布时间:2018-01-20

(借阅各技术论坛以及技术博客总结)

近日,CPU芯片漏洞事件持续发酵,继Meltown(熔断)和Spectre(幽灵)两大漏洞之后,英特尔再曝新漏洞。至此,“芯片漏洞门”事件已经波及了全球几乎所有的手机、电脑、云计算产品。
区别于以往的操作系统或软件漏洞,此次CPU安全漏洞是波及到整个处理器芯片底层设计的行业性问题,包括桌面处理器、移动处理器和Windows之外的系统,以及ARM处理器,Linux系统,还有苹果的MacOS系统等在内都受到了影响,黑客可越级访问到个人电脑内核的内存数据,其中包括用户账号密码、应用程序文件,文件缓存等,从而造成敏感信息泄露。

Web成CPU漏洞最重要的攻击途径

据了解,Web网页是此次漏洞危机最重要的攻击手段,攻击者可能在浏览器中借助JS脚本的某些特性来实现类似的攻击方式,用户如果使用浏览器访问了带有漏洞利用代码的网页,将会导致敏感信息(账号密码等)泄露。而在企业环境中,被泄露的就不只是用户自己的个人隐私了,很可能还包含了企业中的机密数据

谈谈幽灵和熔断两兄弟

 

先来补补基础知识(参考维基百科)。

 

概念:

 

 

0x00 乱序执行

 

在计算机工程领域,乱序执行(错序执行,英语:out-of-order execution,简称OoOE或OOE)是一种应用在高性能微处理器中来利用指令周期以避免特定类型的延迟消耗的范式。在这种范式中,处理器在一个由输入数据可用性所决定的顺序中执行指令,而不是由程序的原始数据所决定。在这种方式下,可以避免因为获取下一条程序指令所引起的处理器等待,取而代之的处理下一条可以立即执行的指令。

 

 

0x01 分支预测

 

分支预测器(英语:Branch predictor)是一种数字电路,在分支指令执行结束之前猜测哪一路分支将会被运行,以提高处理器的指令流水线的性能。使用分支预测器的目的,在于改善指令管线化的流程。现代使用指令管线化处理器的性能能够提高,分支预测器对于现今的指令流水线微处理器获得高性能是非常关键的技术。

 

 

0x02 数据缓存

 

CPU高速缓存(英语:CPU Cache,在本文中简称缓存)是用于减少处理器访问内存所需平均时间的部件。在金字塔式存储体系中它位于自顶向下的第二层,仅次于CPU寄存器。其容量远小于内存,但速度却可以接近处理器的频率。当处理器发出内存访问请求时,会先查看缓存内是否有请求数据。如果存在(命中),则不经访问内存直接返回该数据;如果不存在(失效),则要先把内存中的相应数据载入缓存,再将其返回处理器。

 

 

幽灵(spectre)

 

 

上边提到cpu在执行指令的时候会进行分支预测,简单来说,就是cpu在执行一个逻辑判断的时候会进行提前预测改走哪个逻辑,然后选择其中它正确的逻辑,并将其所需要的数据加入缓存中。

这样,我们看一个例子。

一般来说,如果data[untrusted_opffset_from_caller]越界,程序就会失败。但是cpu有一个预测执行的特性,如果arr1->length不在缓存之中,并且之前这个逻辑多次进入的情况下,cpu就判断if语句是真的,然后先将下一步指令所需要的内存存储到缓存之中(此时不对访问数据是否允许进行判断)。假如发现预测错误,然后回滚指令就可以了。但是这时,cpu缓存并没有清空,而spectre正是利用了这一点来获取非法内存的内容的。

 

1)spectre构造一个训练集,使cpu不断地进入以下的逻辑。此时这是一个很正常的逻辑,x为一个小于array1_size的值。多次训练之后,cpu自作聪明的认为,哦,这就是一个正常的逻辑,那我为了加快执行速度就在判断的时候我将下条指令的所需的内存填入缓存吧。但是,此时CPU不对这个内存的地址是否合法进行判断!只有在执行到它的时候才判断对错,并且,上层预测执行如果预测失败,cpu会回滚指令,但是不去清除这里的缓存。

if (x < array1_size)

{

temp &= array2[array1[x] * 512];

}

 

2)突然,攻击者传入了一个非法的x值,x值是目标地址相当于array1的偏移(注意,在这之前攻击者已经清除掉array1_size的缓存,cpu并不知道array1_size的大小)。

 

但是cpu还是傻傻的认为我可以进入if逻辑,那我就先将大菜准备好,等待客人到来吧。此时,cpu不知道自己已经陷入了攻击者的陷阱了(这时看来,spectre是精心构造了一个结构,其中,array1是一个普通的数组,而array2就比较神奇了,array2[256 * 512]是一个256 * 512的二维数组。为什么是256 * 512呢?这是因为单个字节最大为255。

 

我们来看spectre构造的这个结构,x为目标地址到array1的偏移,这样当这条指令被cpu解析装入缓存之后,array1[x]处便是我们要访问的地址内容,因为是一个字节,肯定小于256。这样array2[array1[x]*512]就是一个正常的数组)。

 

欸,cpu忽然发现这个时候x不再小于array1_size了,那我就不用等客人了,先跑去其他地方玩了,但是,它却忘了将准备好的菜倒掉(嘻嘻,这个cpu和大部分人一样懒呢,都不知道马上洗盘子洗碗)。

 

3)重头戏来了,我这时就要偷偷的从盘子中取菜了。这时,array2[目标内容*512]已经在缓存之中。因为读取缓存和读取内存所需的时间是不相同的,我们只需要去循环读取array2的内容,判断读取的时间就可以推测出目标内存的内容。

 

/* Time reads. Order is lightly mixed up to prevent stride prediction */

for (i = 0; i < 256; i++)

{

mix_i = ((i * 167) + 13) & 255;

 

addr = &array2[mix_i * 512];

 

time1 = __rdtscp(&junk); /* READ TIMER */

 

junk = *addr; /* MEMORY ACCESS TO TIME */

 

time2 = __rdtscp(&junk) – time1; /* READ TIMER & COMPUTE ELAPSED TIME */

 

if (time2 <= CACHE_HIT_THRESHOLD && mix_i != array1[tries % array1_size])

 

results[mix_i]++; /* cache hit – add +1 to score for this value */

}

 

熔断(meltdown)

 

 

Meltdown利用的原理和spectre相似,只不过实现方式不同。

 

来看一个简化版的meltdown

 

mov rax byte[x]            // x为目标地址,非法操作

 

shl rax 0xC                // rax * 4096, page alignment

 

mov rbx qword [rbx + rax]  // [rbx] 为用户空间的一个array,合法操作

 

本身,cpu看到第一条指令非法之后,会将rax的值清零。一般cpu为了更好的性能,会将2,3条指令部分执行,直到rax,rbx被清零。但是关键在于第三条指令,如果rbx+rax不在缓存中,则会首先将目标内存加载到缓存之中。这时就和spectre的处理方式相似了,不断地访问用户空间的数组,通过访问时间来推出目标内容。

 

通俗的举个栗子

 

技术分析想必大家已经看了不少,我来借助大神给的一个最简单好理解的例子:

 

生活实例:新生入学报道

 

(为简化问题,假设今天只有你一个人去学校报道,并且学校工作人员都是250)

 

开学去学校报道,三个步骤(三条CPU指令):

1)凭借录取通知书去领学号

2)凭借领取到的学号去领寝室号

3)凭借领取到的寝室号去领寝室钥匙

 

开学了,你捡到一张录取通知书,通知书编号是1001,然后去拿着它去学校报道,报道工作处有三个工作人员甲乙丙。甲负责直接和你交互,甲拿到你的入学通知书后开始查找你的学号,然后填写表格,然后把学号给你。

与此同时,工作人员乙拿到甲查到的学号后,去表格中查你对应的寝室号,等甲办完以后直接交给你。

 

还是与此同时,工作人员丙拿到乙查到的寝室号后开始去库房的钥匙柜架取出你的钥匙放在办公桌(同时,为了避免等会又跑一趟,它把这栋楼这一层的钥匙盒直接拿到办公室了,等会就不用再去库房奔波了),等乙办完以后就交给你。

但是,这个时候,甲发现你身份有问题,这不是你的录取通知书,不能给你办理入学手续,不能把学号给你。于是你被打回。

可是:乙已经提前帮你把对应学号的寝室号取到了(只是还没给你),丙也已经提前帮你把对应寝室的钥匙给你拿到了(只是还没给你)

好,你被拒绝办理入学了,因为你是假冒的。

实际上,你已经是在校生了,不是大一新生,刚才你是故意去假冒大一新生去报道。

这个时候,你去丙的办公室借钥匙。往常丙都是说你等一下,我去给你拿,然后会等差不多五分钟,丙给你拿来钥匙。但今天不同的是,今天没有等那么久,而是直接就把钥匙取出来了给你,全程不超过10秒钟。

于是,你明白了,一定是我刚才假冒去甲办理入学的时候,丙把钥匙盒取过来的,于是你意识到:我开始捡到的1001号的录取通知书新生住在我们这栋楼这一层。

于是,你如法炮制,伪造1002,1003,1999···号录取通知书去报道,然后知道了他们每个人住在哪一栋那一层。

被黑站点统计 - 文章版权1、本主题所有言论和图片纯属会员个人意见,与本文章立场无关
2、本站所有主题由该文章作者发表,该文章作者与被黑站点统计享有文章相关版权
3、其他单位或个人使用、转载或引用本文时必须同时征得该文章作者和被黑站点统计的同意
4、文章作者须承担一切因本文发表而直接或间接导致的民事或刑事法律责任
5、本帖部分内容转载自其它媒体,但并不代表本站赞同其观点和对其真实性负责
6、如本帖侵犯到任何版权问题,请立即告知本站,本站将及时予与删除并致以最深的歉意
7、被黑站点统计管理员有权不事先通知发贴者而删除本文

免责声明

本站主要通过网络搜集国内被黑网站信息,统计分析数据,为部署安全型网络提供强有力的依据.本站所有工作人员均不参与黑站,挂马或赢利性行为,所有数据均为网民提供,提交者不一定是黑站人,所有提交采取不记名,先提交先审核的方式,如有任何疑问请及时与我们联系.

Zer0 Sec_lionhoo  的文章

  • 浅谈CPU漏洞

    简单来说,就是cpu在执行一个逻辑判断的时候会进行提前预测改

    发布人:Zer0 Sec_l


微信公众号

微信公众号


Copyright © 2012-2022被黑网站统计系统All Rights Reserved
页面总访问量:21229205(PV) 页面执行时间:89.354(MS)
  • xml
  • 网站地图