目录
一、认识线程
1.认识线程V1
借用大多数计算机教材的话,线程是进程的一个执行分支,线程是CPU调度的基本单位。
多进程的缺点在于,每创建一个进程,就要创建一个PCB对象,一份地址空间,一张页表,想办法把这部分消耗缩小,就只需新建一份"PCB",地址空间和页表共用一份,代码部分再均分,比如有5个进程就把所有调度函数均分为5份,如此一来,CPU并不知道自己是执行多进程,只是在调度一个又一个PCB,而用户看来,CPU却是通过“多线程的方式”提高了效率。
2.认识线程V2
既然如此,多个进程有多个线程,系统中存在大量线程,必然需要描述、组织,然而,Linux下,并没有再单独定义线程结构体,而是用进程的结构体来模拟线程。
3.认识线程V3
- 重新认识进程
以前认识进程,这个进程是单执行流,用现在的话说就是内部只有一个线程。
现在认识进程,这个进程内部有多个线程,多个执行分支。
总结的看,进程是系统分配资源的单位,而线程是系统调度的单位,因此,往后理解进程,都要站在系统分配资源的角度去看。
4.认识线程V4
-
cpu调度角度
现在来看,有的进程只有一个执行流,cpu调度可以称为调度进程,而有的进程有多个执行流,cpu调度时称为调度线程。
Linux下,为了统一这种含糊不清的概念,把cpu调度的执行流统称为轻量级进程。线程<= 执行流 <= 进程。因此,cpu不再区分自己到底是在线程调度还是进程调度,都称为执行流。
- 内核级虚拟机技术
我们现在看待进程,它是操作系统分配资源的基本单位,可以认为是一个容器,那么如果一个进程所对应的代码部分是一个操作系统,意味着这个操作系统支持内核级虚拟机技术。
5.认识线程V5
- 页表
抛出一个问题,操作系统是怎么给多线程均分代码的?
第一个结论,内存本质上是有限个4KB的内存块,定义为数组,方便增删查改。
第二个结论,页表并不是简单的K-V映射,虚拟地址是有划分的,比如32位的虚拟地址,前10位是一个整体,中间10位是一个整体,后12位一般是页内偏移地址,而页表其实是多张页目录和多张页内偏移表。
第三个结论,多线程划分代码,其实就是让每一个线程拿到自己代码所在的n张页内偏移表。