内核态与用户态

内核态与用户态

1 概念

Linux的设计哲学之一就是:对不一样的操做赋予不一样的执行等级,就是所谓特权的概念,即与系统相关的一些特别关键的操做必须由最高特权的程序来完成。
Intel的X86架构的CPU提供了0到3四个特权级,数字越小,特权越高,Linux操做系统中主要采用了0和3两个特权级,分别对应的就是内核态(Kernel Mode)用户态(User Mode)架构

  • 内核态:CPU能够访问内存全部数据,包括外围设备(硬盘、网卡),CPU也能够将本身从一个程序切换到另外一个程序;
  • 用户态:只能受限的访问内存,且不容许访问外围设备,占用CPU的能力被剥夺,CPU资源能够被其余程序获取;

Linux中任何一个用户进程被建立时都包含2个栈:内核栈,用户栈,而且是进程私有的,从用户态开始运行。内核态和用户态分别对应内核空间与用户空间,内核空间中存放的是内核代码和数据,而进程的用户空间中存放的是用户程序的代码和数据。无论是内核空间仍是用户空间,它们都处于虚拟空间中。函数

2 内核空间相关

  • 内核空间:存放的是内核代码和数据,处于虚拟空间;
  • 内核态:当进程执行系统调用而进入内核代码中执行时,称进程处于内核态,此时CPU处于特权级最高的0级内核代码中执行,当进程处于内核态时,执行的内核代码会使用当前进程的内核栈,每一个进程都有本身的内核栈;
  • CPU堆栈指针寄存器指向:内核栈地址;
  • 内核栈:进程处于内核态时使用的栈,存在于内核空间;
  • 处于内核态进程的权利:处于内核态的进程,当它占有CPU的时候,能够访问内存全部数据和全部外设,好比硬盘,网卡等等;

3 用户空间相关

  • 用户空间:存放的是用户程序的代码和数据,处于虚拟空间;
  • 用户态:当进程在执行用户本身的代码(非系统调用之类的函数)时,则称其处于用户态,CPU在特权级最低的3级用户代码中运行,当正在执行用户程序而忽然被中断程序中断时,此时用户程序也能够象征性地称为处于进程的内核态,由于中断处理程序将使用当前进程的内核栈;
  • CPU堆栈指针寄存器指向:用户堆栈地址;
  • 用户堆栈:进程处于用户态时使用的堆栈,存在于用户空间;
  • 处于用户态进程的权利:处于用户态的进程,当它占有CPU的时候,只能够访问有限的内存,并且不容许访问外设,这里说的有限的内存其实就是用户空间,使用的是用户堆栈;

4 内核态和用户态的切换

(1)系统调用

全部用户程序都是运行在用户态的,可是有时候程序确实须要作一些内核态的事情,例如从硬盘读取数据等。而惟一能够作这些事情的就是操做系统,因此此时程序就须要先操做系统请求以程序的名义来执行这些操做。这时须要一个这样的机制:用户态程序切换到内核态,可是不能控制在内核态中执行的指令。这种机制叫系统调用,在CPU中的实现称之为陷阱指令(Trap Instruction)。spa

(2)异常事件

当CPU正在执行运行在用户态的程序时,忽然发生某些预先不可知的异常事件,这个时候就会触发从当前用户态执行的进程转向内核态执行相关的异常事件,典型的如缺页异常。操作系统

(3)外围设备的中断

当外围设备完成用户的请求操做后,会像CPU发出中断信号,此时,CPU就会暂停执行下一条即将要执行的指令,转而去执行中断信号对应的处理程序,若是先前执行的指令是在用户态下,则天然就发生从用户态到内核态的转换。设计

注意:系统调用的本质其实也是中断,相对于外围设备的硬中断,这种中断称为软中断,这是操做系统为用户特别开放的一种中断,如Linux int 80h中断。因此从触发方式和效果上来看,这三种切换方式是彻底同样的,都至关因而执行了一个中断响应的过程。可是从触发的对象来看,系统调用是进程主动请求切换的,而异常和硬中断则是被动的。指针

相关文章
相关标签/搜索