聊聊Linux中CPU上下文切换( 二 )


聊聊Linux中CPU上下文切换

文章插图
进程上下文切换内核空间和用户空间我们知道为了限制不同的指令的访问能力,提升安全,Linux 按照特权等级,把进程的运行空间分为内核空间用户空间。进程既可以在用户空间运行,又可以在内核空间中运行 。进程在用户空间运行时,被称为进程的用户态,而陷入内核空间的时候,被称为进程的内核态
  1. 内核空间(Ring 0):具有最高权限,可以直接访问所有资源(读取文件)
常见的内核操作:分配内存、IO操作、创建子进程……
  1. 用户空间(Ring 3):只能访问受限资源,不能直接访问内存等硬件设备,必须通过系统调用进入到内核中,才能访问这些特权资源
常见的用户态空间程序:数据库、web服务器、shell脚本、Java程序或者其他常见语言的程序……
我们一起看下Linux整体架构图:
聊聊Linux中CPU上下文切换

文章插图
top命令查看CPU资源在linux系统使用top命令查看cpu时,能看到用户态和内核态占用的cpu资源
聊聊Linux中CPU上下文切换

文章插图
其中各项数据表示内容:
us用户空间占用CPU百分比sy内核空间占用CPU百分比ni用户进程空间内改变过优先级的进程占用CPU百分比id空闲CPU百分比wa等待输入输出的CPU时间百分比hi硬件中断si软件中断st实时系统调用对于一个进程来说,比如web服务的进程,一般是运行在用户态的,但是当需要访问内存、磁盘等硬件设备的时候需要先进入到内核态中,也就是从用户态到内核态的转变,而这种转变需要借助系统调用来实现 。系统调用是内核向用户进程提供服务的唯一方法 。比如查看文件时,需要执行多次系统调用:open()打开文件,read()读取文件内容,write()将文件内容输出到控制台,最后close()关闭文件等 。系统调用的过程如下:
  1. 把 CPU 寄存器里原来用户态的指令位置保存起来;
  2. 为了执行内核代码,CPU 寄存器需要更新为内核态指令的新位置,最后跳转到内核态运行内核任务;
  3. 系统调用结束后,CPU 寄存器需要恢复原来保存的用户态,然后再切换到用户空间,继续运行进程;
我们可以发现一次系统调用的过程,其实是发生了两次 CPU 上下文切换(用户态-内核态-用户态) 。需要注意的是:系统调用过程中,不涉及虚拟内存等进程用户态的资源,也不会切换进程,也就是系统调用过程中一直是同一个进程在运行 。系统调用过程也通常称为特权模式切换 。
进程上下文切换 和 系统调用的区别?
  1. 进程上下文切换是指,从一个进程切换到另一个进程;系统调用过程一直是同一个进程在运行,属于进程之内的上下文切换
需要注意的是:进程是由内核来管理和调度的,进程的切换只能发生在内核态,保存上下文和恢复上下文的过程并不免费,需要消耗一定资源

聊聊Linux中CPU上下文切换

文章插图
  1. 进程的上下文不仅包括了虚拟内存、栈、全局变量等用户空间的资源,还包括了内核堆栈、寄存器等内核空间的状态 。而系统调用这里没有涉及到虚拟内存等这些进程用户态的资源
  2. 经验总结扩展阅读