Ring0-Ring3层到底是个什么东西

10,497 阅读5分钟

Intel的CPU将特权级别分为4个级别:RING0,RING1,RING2,RING3。

Windows只使用其中的两个级别RING0和RING3,RING0只给操作系统用,RING3谁都能用。

如果普通应用程序企图执行RING0指令,则Windows会显示“非法指令”错误信息。

尽管有CPU的特权级别作保护,遗憾的是WINDOW98本身漏洞很多,使用Windows 98的系统一天死机n回也是正常的。

分级保护域示例图

Windows只使用其中的两个级别RING0和RING3。

RING0层拥有最高的权限,RING3层拥有最低的权限。

按照Intel原有的构想,应用程序工作在RING3层,只能访问RING3层的数据,操作系统工作在RING0层,可以访问所有层的数据,而其他驱动程序位于RING1、RING2层,每一层只能访问本层以及权限更低层的数据。

如果普通应用程序企图执行RING0指令,则Windows会显示“非法指令”错误信息。

诚然,RING设计的初衷是将系统权限与程序分离出来,使之能够让OS更好的管理当前系统资源,也使得系统更加稳定。

举个RING权限的最简单的例子:一个停止响应的应用程式,它运行在比RING0更低的指令环上,你不必大费周章的想着如何使系统回复运作,这期间,只需要启动任务管理器便能轻松终止它,因为它运行在比程式更低的RING0指令环中,拥有更高的权限,可以直接影响到RING0以上运行的程序,当然有利就有弊,RING保证了系统稳定运行的同时,也产生了一些十分麻烦的问题。

比如一些OS虚拟化技术,在处理RING指令环时便遇到了麻烦,系统是运行在RING0指令环上的,但是虚拟的OS毕竟也是一个系统,也需要与系统相匹配的权限。

而RING0不允许出现多个OS同时运行在上面,最早的解决办法便是使用虚拟机,把OS当成一个程序来运行。

后来才有了更新的技术解决了此问题。

现在探讨内核程序和应用程序之间的本质区别。

除了能用WDK编写内核程序和阅读一部分Windows的内核代码之外,我们还需要了解它们的本质是什么,它们和我们熟悉的应用程序有什么区别。

Intel的x86处理器是通过Ring级别来进行访问控制的,级别共分4层,从Ring0到Ring3(后面简称R0、R1、R2、R3)。

R0层拥有最高的权限,R3层拥有最低的权限。

按照Intel原有的构想,应用程序工作在R3层,只能访问R3层的数据;操作系统工作在R0层,可以访问所有层的数据;而其他驱动程序位于R1、R2层,每一层只能访问本层以及权限更低层的数据。

这应该是很好的设计,这样操作系统工作在最核心层,没有其他代码可以修改它;其他驱动程序工作在R1、R2层,有要求则向R0层调用,这样可以有效保障操作系统的安全性。

但现在的OS,包括Windows和Linux都没有采用4层权限,而只是使用2层——R0层和R3层,分别来存放操作系统数据和应用程序数据,从而导致一旦驱动加载了,就运行在R0层,就拥有了和操作系统同样的权限,可以做任何事情,而所谓的rootkit也就随之而生了。

rootkit在字面上来理解,是拥有“根权限”的工具。

实际上,所有的内核代码都拥有根权限,当然,并不一定它们都叫做rootkit,这要看你用它来做什么。

用rootkit技术开发的木马和病毒正在迅速发展,它们往往极难清除,以往杀毒软件可以轻松清除掉系统中病毒的时代似乎已经一去不复返了。

大多数指令可以同时使用于R0层和R3层,但有些和系统设置相关的指令却只能在R0层被使用,或者在R3层的使用受到限制,主要有下面这些:

  • lgdt:加载GDT寄存器

  • lldt:加载LDT寄存器

  • ltr:加载任务寄存器

  • lidt:加载IDT寄存器

  • mov:加载和存储控制寄存器、调试寄存器时受限

  • lmsw:加载机器状态字

  • clts:清除cr0中的任务切换标记

  • invd:缓冲无效,并不写回

  • wbinvd:缓冲无效,并写回

  • invlpg:无效TLB入口

  • hlt:停止处理器

  • rdmsr:读模式指定寄存器

  • wrmsr:写模式指定寄存器

  • rdpmc:读取性能监控计数器

  • rdtsc:读取时间戳计数器

最后2条指令rdpmc和rdtsc,在cr4的位4(PCE)和位2(TSD)被设置的情况下可以同时被R0层和R3层调用。

任何违反上面规定的操作,在Windows下都可能会产生通用保护故障的异常。

另外,还有些所谓的IO敏感指令,包括:

  • cli:关闭中断

  • sti:开启中断

  • in:从硬件端口读

  • out:往硬件端口写

这些指令在R0层可以直接被使用,在R3层被使用的时候还要检查IO许可位图,综合判断是否允许调用。

当然,前面已经声明我们写的和研究的代码都是内核代码,也就是说,上面这些指令都是可以用的。

当然,相应的rootkit技术的病毒和木马的作者显然也会明白这一点,所以这并不是让人很有安全感的一个现状。

更重要的保护机制是如何保证系统内存空间的读/写、可执行属性,对于病毒和木马来说,使用硬件机制来实现破坏虽然并非不可能,但是远不如直接修改内存中的操作系统内核和其他软件的代码来得简洁方便,那是破坏与安全对抗的主战场。