目录
概念
操作系统的概念
操作系统是最接近硬件的软件。
最直观的管理就是可以通过任务管理器查看:
以运行一个程序来看:
底层的硬件交互接口不友好,通过操作系统可以让程序有个友好的交互接口
这其实就是一种封装思想:
接口分为两种,一种是用户直接使用,一种是软件/程序员使用。
操作系统的特征
- 并发
(并行才是真正的同行进行)
- 共享
而并发和共享这两个特性是一个共存的关系。一般来说,两个程序并发的进行,那他们就会共享一部分系统资源。
- 虚拟
空分复用技术
时分复用技术
- 异步
分时操作系统:
- 内核态和用户态
中断和异常
没有中断机制就不会有并发
中断分为内中断和外中断:
如果执行了非法的指令,cpu会夺回控制权。
陷入指令也可以产生内中断:
外中断的例子,通过时钟定时进行中断实现并发功能。
或者比如还有设备型的IO中断服务:
一般内中断叫异常,外中断叫中断。
系统调用
系统调用就是操作系统给用户一些接口,用户可以通过这些接口来操作硬件部分。
系统调用的作用:
第二章 进程管理
进程的概念、组成、特征
程序和进程的区别:
QQ是一个程序,但是打开三次QQ就会产生3个进程:
调度就是指让哪个进程进入cpu执行。
进程的特征
进程的状态与转换
当如果出现某个指令需要申请设备资源但是却无法申请到时:
此时让改进程进入阻塞态,并且选取其他就绪态的进程进入cpu
如果此时设备可以给它用了,则让它再次回到就绪态:
当此时cpu上的进程运行结束时,会让它进入终止态,并且回收资源、PCB等
进程状态的转换
进程的组织方式 (*非重点)
链接方式和索引方式
进程控制
为什么不能中断?因为这个操作可能有几步,如果被中断了那么其中进程的转换可能就会出错。
进程的创建:
进程的终止:
进程的阻塞和唤醒
进程的切换
程序是如何运行的?
cpu中会设置寄存器来存放程序运行过程中所需的数据
重点是这个:
运行环境就是指程序运行过程中的进程上下文
进程通信(重点)
线程概念
什么是线程,为什么要引入线程?
一个QQ进程可以做很多事,发文字、语音、视频…
引入线程后,每个进程可以有多个线程
此时进程不再是系统调度的基本单位,线程才是
而设备资源是分配给进程的,而不是线程。
进程是资源分配的基本单位,线程是调度的基本单位
线程的属性总结:
重点的几条:线程是处理机调度的单位
线程几乎不用友系统资源
同一进程的不同线程间共享进程的资源
多线程模型
(暂时跳过)
处理机调度概念、层次
调度的基本概念
调度有三个层次
- 高级调度
- 低级调度
- 中级调度
内存不够时,会将一些进程的数据调出外村,空闲时再调入,这种状态被称为挂起状态。
从五状态模型到七状态模型
三种调度的对比:
进程调度的时机、切换调度的过程,方式
对于进程的调度方式有两种,主动和被动
进程同步和互斥
什么是进程同步
进程同步与进程互斥
进程具有异步性,具有先后不确定性,然而现实情况需要我们有时候让进程按照一定的顺序执行,协调这种次序产生的制约关系称作是同步。
进程互斥指有一些临界资源比如打印机,同一时刻只能有一个进程在使用。我们得保证进程对这些临界资源的访问必须是互斥的进行。
信号量机制
信号量机制用来实现进程的互斥和同步
上图2号发生时,此时它进入阻塞队列,而3号同理进入阻塞队列。
当上图中的4号位置的打印机用完时,使用singal原语,此时value值++后,仍然小于0,则其将阻塞队列中的2号位置的打印机唤醒,让其从阻塞队列进入就绪队列,当cpu分配给他时即可变成运行态。
对记录型信号量进行总结:
用信号量实现进程互斥、同步、前驱
- 信号量机制实现进程互斥
互斥是保证同一临界资源在一个时刻只有一个进程访问,(例如洞口一个时间段只能有一个棒进去,但是谁先谁后没有关系)
进洞前需要告诉上锁,这样别人就不能进来了,出洞后就解开锁,这样别人就可以进去了。
信号量初始值为1,代表的是初始的时候就有一个洞口可以进入。与下面的同步不同,下面的洞口,一开始洞口就被某个人填满了,所以初始信号量是0。
- 信号量机制实现进程同步
为了保证代码12在代码4之前执行,加入下面的操作:
前V后P,让后需要执行的进程在使用资源前需要先申请(也就是P操作),而需要先执行的进程执行完毕后释放资源(也就是V操作),这样就能保证先后顺序了。
换句话说就是想用资源得申请,并且等到别人释放了你才能用,这样就保证了先后。
- 用信号量实现进程前驱关系
读者写者问题
实现如下:
但是如果是这样,则无法实现多个读者可以同时访问
这样就实现了只有第一个读者会进行读的操作,后面来的读者都不需要进行P操作,也就是不需要执行wait原语。
但是如果两个读者刚开始几乎同时访问,那么当一个读者执行了P操作之后,还没执行count前,即执行到箭头所示的地方时,此时第二个读者的count还是0,那么会执行wait操作,导致无法进入。
解决方法如下:
这样即可解决问题。
不过也有一个小问题,就是:
为了防止有读者源源不断的出现时,写者一直被阻塞着,我们要实现一个机制,一旦出现了写者,那么当前在读的读者依然可以读,但是后面进来的读者不能再继续读了,必须要停下来。
当读者2到来时,会被Pw阻塞住,如下图所示。
读者2直到写者1写完才能继续。而写者什么时候能写?等读者1读完才能开始写。所以就实现了读者1,写者1,读者2这样的顺序。
如果是这样的顺序:
那么读者1也必须
读写锁和互斥锁
互斥锁: 对共享数据进行锁定,保证同一时刻只能有一个线程去操作。
2. 互斥锁的特点:
多个线程访问共享数据的时候是串行的
读写锁
互斥锁把试图进入临界区的所有其它线程都阻塞注。然而有时候我们希望在读某个数据与修改某个数据之间作区分。读写锁就是在用于读与写之间作区分。读写锁的分配规则如下:
互斥锁 - 读写串行
读写锁:读:并行 写:串行
哲学家进餐问题
如何防止死锁的发生,有这三种思路:
下面实现第三种情况这样的情况:
上述两种情况表明,不能实现只有两边的筷子都可用时才允许哲学家拿起筷子。
但是,它却可以实现,当一个哲学家拿筷子拿到一半时,一定会执行Pmutex,那么,保证其他哲学家此时不会再拿筷子! 于是只要等当前正在吃饭的哲学家放下筷子后,被阻塞的哲学家就可以获得等待的筷子了。 于是最终不会产生死锁。
死锁的概念
什么是死锁?
- 死锁、饥饿、死循环
- 死锁产生的必要条件
互斥条件:首先肯定这个东西大家都抢着想要筷子
不剥夺:并且其中一个人有了部分东西,他说我还没用完呢:有一个筷子,所以拿着不放,
请求和保持:我只有一个筷子,我还需要一个筷子,快给我上(请求和保持条件)
循环等待:我在等你手中的筷子,你也在等我手中的筷子
- 什么时候会发生死锁?具体什么情况?
上面是发生死锁的细节,现在来从一个宏观的层面去看,什么时候会有这种情况呢?
1.大家都在竞争筷子(对系统资源的竞争)
2.大家拿筷子的顺序不对(进程推进顺序非法)
3.拿筷子后,没有通知别人拿筷子(信号量的使用不当)
- 死锁的处理策略
四种方法类似一些疾病,首先打预防针,并且生活中也得做出避免的措施,
感觉有点异常了就去医院看病,即检测,发生生病了则解决病,所以就是解除
知识回顾和重要考点
预防死锁
- 破坏互斥条件
- 破坏不剥夺条件
- 破坏请求和保持条件
- 破坏循环等待条件
避免死锁
假如答应了B的请求,则表格如下所示: 则此时BAT再向你借钱时,就可能无法满足了
但是如果是A向你借20亿,
上面那种方法可行,也可以换种顺序:
对上面的情况进行总结:
所以办法就是在资源分配之前预先判断 这次分配是否会导致进入不安全状态,以此决定是否答应资源分配请求。这也是银行家算法的核心思想。
- 银行家算法
银行家有(10,5,7),已经分配了(7,2,5),还剩下(3,3,2)
接下来判断上面那种情况接下来会不会是安全情况:
首先对于P0来说不行
虽然不能分配给P0,但是发现可以分配给P1,当P1结束时资源会变得多
接下来继续往下遍历发现p2没有足够多的资源分配,但是p3可以
更快的一个方法是:
- 银行家算法具体实现代码思想
死锁的检测和解除
就这样循环直到消除全部边
如果不能消除全部边,则:
- 死锁解除
如何决定对谁动手?
第三章 内存管理
内存的基础知识
Cache的基本概念
如果是1KB为一个块,则1K=2的10次方
Cache中存放着主存里的各个块,如下所示:
但是Cache还有几个问题,见下面
Cache和主存的映射方式
还得增加一个有效位:
- 全相联映射
用主存大小除以块大小即可得到有多少个块,当块放入Cache中时,将有效位置为1
例如接下来我们要访问某个主存地址:那么接下来步骤是:
- 直接映射
通过取余的方式
注意到在cache中存放了一个标记位,这个标记位包含0~22位,但是我们注意到,如果cache有8块,则这三位是重复了的:
则可以将其省略掉。
但是会出现0和8放在同一个地方,此时就会发生重复, 就会覆盖。
这样就会出现虽然有空闲,但是就用不上了。于是下面介绍一下组相联映射:
- 组相联映射
Cache替换算法
- 随机算法
随机选择一块进行替换
- FIFO先进先出算法(First in first out)
- LRU最近最少使用算法(Least Recently Used)
注意上面有一点是只有让比其低的计数器菜++。因为比它高的计数器,此时以及无需++,因为此时已经是最高的了,因此不用再提高。并且还可以让这个数字只使用nBite表示
- LFU最不经常使用算法(Least Frequently Used)
如果出现次数相同的,则使用FIFO或者
总结:
Cache写策略
写命中
- 写回法
用一个脏位表示是否被修改过,未被修改的块不必写回
- 写缓冲
写不命中
- 写分配法
- 非写分配法
总结: