用户态与内核态
用户态与内核态的概念
用户态
用户态:也叫用户空间,是用户进程/线程所在的区域。主要用于执行用户程序。
用户态就是提供应用程序运行的空间,为了使应用程序访问到内核管理的资源例如CPU,内存,I/O。内核必须提供一组通用的访问接口,这些接口就叫系统调用。
系统调用是操作系统的最小功能单位。根据不同的应用场景,不同的Linux发行版本提供的系统调用数量也不尽相同,大致在240-350之间。这些系统调用组成了用户态跟内核态交互的基本接口。
内核态
内核态:也叫内核空间,是内核进程/线程所在的区域。主要负责运行系统、硬件交互。
内核态其实从本质上说就是内核,它是一种特殊的软件程序,控制计算机的硬件资源,例如协调,CPU资源,分配内存资源,并且提供稳定的环境供应用程序运行。
为什么要区分内核态和用户态
实现保护机制。防止用户进程误操作或者是恶意破坏系统。
内核态类似于C++的私有成员,只能在类内访问,用户态类似于公有成员,可以随意访问。
所以说操作系统在执行用户程序时,主要工作在用户态,只有在其执行没有权限完成的任务时才会切换到内核态。
用户态与内核态的区别
内核态:运行的代码不受任何限制,CPU可以执行任何指令。
用户态:运行的代码需要受到CPU的很多检查,不能直接访问内核数据和程序,也就是说不可以像内核态线程一样访问任何有效地址。
用户态切换到内核态的方式
1、系统调用(主动)
由于用户态无法完成某些任务,用户态会请求切换到内核态,内核态通过为用户专门开放的中断完成切换。
系统调用本身就是中断,但是是软件中断,跟硬中断不同
2、异常(被动)
在执行用户程序时出现某些不可知的异常,会从用户程序切换到内核中处理该异常的程序,也就是切换到了内核态。例如:缺页异常。
3、外围设备中断(被动)
外围设备发出中断信号,当中断发生后,当前运行的进程暂停运行,并由操作系统内核对中断进程处理,如果中断之前CPU执行的是用户态程序,就相当于从用户态向内核态的切换。
用户态与内核态空间分配
对 32 位操作系统而言,它的寻址空间(虚拟地址空间,或叫线性地址空间)为 4G(2的32次方)。也就是说一个进程的最大地址空间为 4G。操作系统的核心是内核(kernel),它独立于普通的应用程序,可以访问受保护的内存空间,也有访问底层硬件设备的所有权限。为了保证内核的安全,现在的操作系统一般都强制用户进程不能直接操作内核。具体的实现方式基本都是由操作系统将虚拟地址空间划分为两部分,一部分为内核空间,另一部分为用户空间。针对 Linux 操作系统而言,最高的 1G 字节点(从虚拟地址 0xC0000000 到 0xFFFFFFFF)由内核使用,称为内核空间。而较低的 3G 字节点(从虚拟地址 0x00000000 到 0xBFFFFFFF)由各个进程使用,称为用户空间。
对上面这段内容我们可以这样理解:
每个进程的 4G 地址空间中,最高 1G 都是一样的,即内核空间。只有剩余的 3G 才归进程自己使用。换句话说就是, 最高 1G 的内核空间是被所有进程共享的!
现代的操作系统大都通过内核空间和用户空间的设计来保护操作系统自身的安全性和稳定性。
所以说啊,这篇里的概念原理其实都是一种思想,每个操作系统都不一样,一般就是拿Linux说。