一探究竟 -- 操作系统

39 阅读17分钟

一、操作系统结构

1、中断和异常

(1)内核

    内核是计算机配置的底层软件,是操作系统最基本、最核心的部分、实现操作系统内核功能的程序就是内核程序。包括
时钟管理、中断处理、原语等。

(2)用户态&核心态

针对权限的控制,操作系统把内存分为两部分:

  • 用户态:此时CPU只能执行非特权指令。

  • 核心态:特权指令、非特权指令。

(3)中断

    中断:需要操作系统介入,开展管理工作。中断可以使CPU从用户态转为核心态,使操作系统获取计算机的控制权。
  1. 当中断发生时,CPU立即进入核心态。
  2. 发生中断时,当前运行的进程暂停运行,并由操作系统对中断进行处理。
  3. 对于不同中断信号,进行不同处理。

中断分类:

image.png

问题一:用户态、核心态的转换?

答:用户态到核心态是通过中断实现的,并且中断是唯一的途径。当应用程序使用系统调用时,会产生一个中断。中断产生,CPU会中断当前进程,开始处理中断。处理完成后,主动触发中断,将CPU交回给用户程序,回到用户态继续工作。核心态到用户态时通过执行一个特权指令,将程序状态字(PSW)标志位置为用户态。

2、系统调用

系统调用:通过应用程序进行调用的特殊函数,应用程序可以发出系统调用请求来获得操作系统的服务。

二、进程

1、进程

(1)定义

  1. 进程就是程序的一次执行过程。

  2. 进行是一个程序及其数据在处理机上顺序执行所发生的活动。

  3. 进程由程序段、数据段、PCB三部分组成。

(2)状态和转换

  • 运行态:占有CPU资源,在CPU上运行。

  • 就绪态:具备运行条件,但是没有空闲的CPU,暂时不能运行。

  • 阻塞态:因为等待某个时间而暂停不能运行。

  • 创建态:进程正在被创建,操作系统为进程跟配资源,初始化PCB。

  • 终止态:进程从系统中撤销,操作系统回收资源。

进程状态的转换:

image.png

(3)进程通信

    进程通信是指进程之间的信息交换。各进程拥有独立的内存地址空间。为了保证安全,一个进程不能直接访问另一个进程的
地址空间。但是进程间的信息交换又是必须的,因此通过以下方法实现。
  1. 共享存储

     通过共享空间连接两个进程,两个进程对共享空间的访问必须是互斥的。一种基于数据结构的共享,限制存储数据的结构,
     限制多,速度慢;另一种基于存储区共享,有进程控制数据的格式,速度快。
    
  2. 消息传递

     进程间以格式化的消息通信。
    
  3. 管道通信

     管道:指连接读写进程的一个共享文件,又名pipe文件。其实就是在内存中开辟一个大小固定的缓冲区。
    

image.png

  • 管道只能采用半双工通信,即某一时间段内只能实现单向的传输。如果想实现双向同时通信,则需要两个管道。

  • 各进程要互斥的访问管道。

  • 数据以字符流的形式写入管道,当管道写满时,写进程的write()系统调用会被阻塞,等待读进程取走数据。当读进程将数据全部取走后,管道变空,读进程的read()系统调用将被阻塞。

  • 如果没写满,不允许读;如果没读空,则不允许写。

  • 一旦数据被读出,就会从管道中被抛弃,意味着读进程只能有一个。

2、线程

(1)定义

  1. 线程是一个基本的cpu执行单元,也是程序执行流的最小单元。

  2. 引入线程后,不仅进程间可以并发,线程间也可以并发。

  3. 引入线程后,进程只作为除CPU之外的系统资源的分配单元。

image.png

3、进程调度

(1)进程切换

  1. 进程切换需要对原来运行进程各种数据保存。

  2. 对新的进程各种数据的恢复。

(2)调度算法

饥饿:进程长时间等不到CPU的调度。

饿死:进程一直获取不到CPU的调度。

1、先来先服务(FCFS)

算法规则:按照进程到达的先后顺序进行调度,非抢占式算法。

优缺点:公平、算法实现简单。但是排在长作业后的短作业等待时间过长。

2、短作业优先(SJF)

算法规则:最短的作业/进程优先的到服务,非抢占式算法。最短剩余时间优先是抢占式的。

优缺点:对短作业有利,对长作业不利。可能产生饥饿现象。

3、高响应比优先(HRRN)

算法规则:每次调度时先计算各个作业的响应比,选择响应比最高的作业。响应比等于等待时间+要求服务时间/要求服务时间。非抢占式的算法,只有当前运行的作业主动放弃CPU时(正常/异常完成,或主动阻塞),才会使用该算法。

优缺点:折中算法,等待时间相同时,要求服务时间短的优先(SJF的优点);要求服务时间相同,等待时间长的优先(FCFS的优点),对于长作业,随着等待时间越长,响应比越大,避免长作业饥饿。

4、时间片轮转(RR)

算法规则:按照各进程达到就绪队列的顺序,轮流让各个进程执行一个时间片(如100ms)。若进程未在一个时间片内执行完,则剥夺CPU,将进程重新放到就绪队列末尾重新排队。抢占式算法,由时钟装置发出时钟中断通知CPU时间片已到。

优缺点:如果时间片太大,每个进程都能在一个时间片内完成作业,就会退化成先来先服务算法,增大进程响应时间。如果时间片太小,进程间切换过于频繁,系统消耗大。

5、优先级调度

算法规则:每个进程都有各自的优先级,调度时选择优先级最高的进程。非抢占式的只有当前进程主动放弃CPU后,其他进程才能使用该算法。抢占式的,每次调度时选择当前已到达且优先级最高的进程,当前进程主动放弃。

优缺点:区分紧急程度,灵活调整对各个进程的偏好程度。可能导致饥饿。

6、多级反馈队列

算法规则:设置多级就绪队列,各级队列优先级从高到低,时间片从小到大。新进程优先进入第一级队列,按先进先服务原则等待分配时间片,若用完时间片进程还未结束,则进入下一级队列队尾。如果已经在最下级队列,重新放回该队列队尾。只有上一级队列为空,才会为下下一级队列队头分配时间片。抢占式的。

优缺点:可以灵活调整对各类进程的偏好程度。

3、进程同步、进程互斥

进程同步

  1. 多个进程相互协调的完成工作。

进程互斥

  1. 互斥共享方式:一个时间段内只允许一个进程访问该资源。
  2. 同时共享方式:允许一个时间段内,多个进程访问该资源。

三、死锁

1、死锁

(1)定义

  1. 死锁:两个或两个以上的进程相互等待对象的资源,从而导致的死锁的现象。发生死锁的进程一定处于阻塞状态。

  2. 饥饿:可能只有一个进程发生饥饿,既可能处于阻塞态(长期得不到需要的IO设备)也可能处于就绪态(长期获取不到处理机资源)。

(2)死锁的产生条件

  • 互斥条件:进程必须互斥抢夺资源。

  • 不剥夺条件:进程所获得的资源在未使用完之前,不能由其他进程强行夺走,只能主动释放。

  • 请求和保持条件:进程已经获得一个资源,仍然去获取新的资源。

  • 循环等待:相互等待。

2、死锁的处理策略

(1)预防死锁

通过破坏死锁的产生条件预防产生死锁。
  • 破坏互斥条件:将独占资源改造为共享资源;可行性不高。

  • 破坏不剥夺条件:申请不到资源时,立即释放拥有的资源;复杂度高,可能导致工作失效。

  • 破坏请求和保持条件:运行前分配好资源,之后一直保持;资源利用率低,可能导致饥饿。

  • 破坏循环等待条件:给资源编号,必须按编号从小到大顺序申请资源;导致资源浪费,麻烦。

四、内存

1、内存

内存由程序段、数据段、PCB构成。虚拟内存是操作系统提供的⼀种机制,将不同进程的虚拟地址和不同内存的物理地址映射起来。

(1)逻辑地址

    程序所使用的地址。

(2)物理地址

    硬件存在的真实地址。

2、内存管理

(1)内存基本理论

1、内存保护

通过重定位寄存器存放进程的起始物理地址,界寄存器存放进程最大的逻辑物理地址。CPU发生调度时,会优先跟界寄存器中的地址比较进程的逻辑地址是否越界,没越界,则加上重定位寄存器的地址就可以访问该物理地址上的存储单元。

2、内存覆盖

早期的计算机通常内存过小,人们引入覆盖技术,解决程序大小超过物理内存总和的问题。

思想:将程序分为多个段。常用的段常驻内存,不常用的段需要时调入内存。内存分为一个固定区和若干个覆盖区。需要常驻内存的段放在固定区,调入后不再调出,除非运行结束。不常用的段放在覆盖区,需要时调入内存,用不到时调出内存。

由于覆盖技术必须由程序员生命覆盖结构,对用户不透明,增加编程负担,早期使用。

3、内存交换

内存紧张时,将内存中某些进程暂时换出外存,具备运行条件时换入内存。暂时换出内存等待的进程状态为挂起状态。则塞挂起进程调出内存。

(2)内存空间的分配

1、内存分配

  • 内部碎片:分配给某个进程的内存区域中,如果有些部分没有使用。

  • 外部碎片:指内存中的某些空闲分区由于太小无法使用。

  1. 单一连续分配:内存分为系统区和用户区。内存区只能有一个用户程序,实现简单。有内部碎片。

  2. 固定分区分配:将用户区分割为多个固定大小的区域,每个区域一个作业。内部碎片。

  3. 动态分区分配:不会预先划分内存,进程装入内存时,根据进程大小动态建立分区。没有内部碎片,有外部碎片。

2、动态内存分配算法

image.png

3、分页存储管理

将内存空间分为一个个大小相等的分区,称为页框。将用户进程的地址空间分为与页框大小相等的区域,称为页。

通过逻辑地址对应的页号和页面在内存中的起始地址,以及逻辑地址在页面中的偏移量,物理地址等于页面地址加偏移量。

页号=逻辑地址/页面长度页号 = 逻辑地址 / 页面长度
页内偏移量=逻辑地址页内偏移量 = 逻辑地址 % 页面长度
  1. 基本地址变换机构

    通过页表寄存器(PTR),存放页表在内存中的起始地址和页表长度。进程未执行存放在PCB中,调度时放在页表寄存器中。

  2. 快表(高速缓冲存储器)

    基本地址变换机构,每次访问一个逻辑地址,都需要查询内存中的页表。可能连续查到的都是同一个页表项。 快表,又称联想寄存器(TLB)。用于存放当前访问的若干页表项,以加速地址变换过程。类似于我们使用缓存。

  3. 两级页表

4、分段存储管理

将进程的地址空间按照程序自身的逻辑关系划分为若干个段,每个段都有一个段名,每段从0开始编址。为每个进程建立一张段映射表,称为段表。段表记录记录该段在内存中的起始位置和段的长度。各个段表项的长度是相同的。

分段和分页管理对比

  1. 页是信息的物理单位。分页的目的是实现离散分配,提升内存利用率。对用户是不可见的。

  2. 段是信息的逻辑单位,分段是为了满足用户需求。一个段通常包含一个逻辑模块的信息。对用户课件。

虚拟内存

操作系统虚拟性的体现,实际的物理内存大小没变化,只是逻辑上进行扩充。

(3)页面置换算法

当内存空间不足时,操作系统负责将内存中暂时不使用的信息换出到外存,用页面置换算法决定选择哪些页面。由于页面的换入、换出需要磁盘I/O,会有较大开销,因此页面置换算法应该追求更少的缺页率。

1、最佳置换算法(OPT)

每次选择淘汰永不使用的页面,或者在最长时间内不再访问的页面,保证最低的缺页率。理想算法,只有进程执行的过程中才能知道接下来会访问的页面,无法提前预判页面的访问顺序,无法实现。

2、先进先出置换算法(FIFO)

每次选择淘汰最早进入内存的页面。性能差。

3、最近最久未使用置换算法(LRU)

每次淘汰最近最久未使用的页面。用访问字段记录该页面上次被访问以来所经历的时间。实现需要专门的硬件支持,算法开销大。

3、时钟置换算法(CLOCK)

简单CLOCK算法:为每个页面设置一个访问位,再将内存中的页面通过指针链接成一个循环队列。访问位为1表示最近访问过,访问位为0表示最近没访问过。当某页被访问时,设置为1。需要淘汰时,检查访问位,如果是0,换出页面,如果是1,置位0。最多经过两轮扫描。

改进:简单CLOCK算法仅考虑页面是否被访问过。页面只有在被修改过后,才需要写回外存。因此增加修改位,减少IO操作。

五、文件

1、文件基本操作

  1. 创建文件(create):进行create系统调用,在外存中找到文件所需的空间,然后创建文件对应的目录项。

  2. 读文件(read):应用程序通过操作系统提供的读文件功能,即read系统调用,将文件数据从外存中读入内存中。

  3. 写文件(write):应用程序通过操作系统提供的写文件功能,即write系统调用,将文件数据从内存写回外存。

2、文件共享

(1)基于索引节点的共享方式(硬链接)

索引节点:是一种文件目录瘦身策略。检索文件时需要用到文件名,因此将文件名之外的信息放在索引节点中,这样目录项旧只包含文件名、索引结点指针。索引结点上的变量count,表示链接到本索引结点上的用户目录项数。

image.png

(2)基于符号链的共享方式(软链接)

创建一个link类型的文件,记录文件1的存放路径,类似于win操作系统的快捷方式,当user3访问文件ccc时,操作系统判断其属于link文件,会根据其记录的路径查找目录,最终找到目录表中的aaa的表项,于是就找到其索引结点。

六、磁盘

1、基本概念

  • 磁盘:由磁性物质组成的盘。

  • 磁道:磁盘的盘面被划分为一个个磁道。

  • 扇区:一个磁道会被分为一个个扇区,每个扇区就是一个磁盘块。各个扇区存放的数据量相同。最内侧磁道上的扇区面积最小,因此数据密度最大。

  • 盘面:磁盘的表面。

  • 柱面:每个盘面对应一个磁头,所有磁头链接一个磁臂,所有盘面中相对位置相同的磁道组成柱面。

(1). 从磁盘中读/写数据

需要把磁头移动到想要读/写的扇区所在的磁道。磁盘会转起来,让目标扇区从磁头下面划过,完成对扇区的读/写操作。

(2). 磁盘的物理地址

可用柱面号、盘面号、扇区号来定义任意一个磁盘块。文件数据存放在外存中的磁盘块中。

(3). 一次磁盘读/写操作需要的时间

  1. 寻道时间:将磁头移动到指定磁道所花的时间,启动磁头臂的时间和移动磁头的时间。

  2. 延迟时间:通过旋转磁盘,使磁头定位到目标扇区所需要的时间。

  3. 传输时间:从磁盘读出或写入数据所经历的时间。

(4). 如何减少延迟时间

磁头读取一个扇区的内容后,需要一小段时间处理,而盘面是不停地旋转,因此如果相邻的扇区,无法连续读入,因为磁头读取一个扇区的数据后也需要一小段的时间处理。因此逻辑上相邻的扇区在物理上也相邻,则读入几个连续的逻辑扇区,可能需要很长的延迟时间。

  1. 采用交替编号策略,让逻辑上相邻的扇区在物理上有一定的间隔。

  2. 错位命名:不同盘面扇区对应的编号上下不一致。

2、磁盘调度算法

  1. 先来先服务算法(FCFS)

根据进程请求访问磁盘的先后顺序进行调度。如果大量进程使用磁盘,请求访问的磁道很分散,则FCFS算法性能很差,寻道时间长。

  1. 最短寻找时间优先(SSTF)

优先处理与当前磁头最近的磁道,但是未必总体寻道时间最短。可能产生饥饿现象,磁头在一个小的区域内来回移动。

  1. 扫描算法(SCAN)

只有磁头移动到最外侧磁道时才能往内移动,移动到最内侧磁道的时候才能往外移动。会移动过多的磁头,并且各个位置磁道的响应频率不平均。

  1. look算法

如果磁头移动方向上已经没有别的请求,就立即改变磁头移动方向。

5.循环扫描算法(C-SCAN)

规定只有磁头朝某个特定方向移动时才处理磁道访问请求,返回时直接快速移动至起始端不处理任何请求,会移动过多的磁头。

6.C-LOOK算法

在c-scan算法的基础上,磁头返回时只需要返回到有磁道访问请求的位置即可。