操作系统-------信号量和死锁

1.信号量

1.1信号量机制

信号量:其实就是一个变量(可以是一个整数,也可以是更复杂的记录型变量),可以用一个信号量来表示系统中某种资源的数量。比如:系统中的一台打印机,就可以设置一个初值为1的信号量。

用一对原语来对信号量进行操作:wait(S)原语和signal(S)原语,简称为P、V操作-------P(S)、V(S)

 

  • 整型信号量

    • 用一个整数型的变量作为信号量,来表示系统中某种资源的数量
    • 不满足让权等待,会发生忙等,一直占用CPU进行循环
    • 操作系统-------信号量和死锁_第1张图片
  • 记录型信号量

    • 用记录型数据结构表示
    • 遵循了让权等待
    • 操作系统-------信号量和死锁_第2张图片

 

1.2信号量机制实现互斥、同步

信号量机制实现进程互斥:在缓冲区前后分别执行P、V

  • 划分临界区,设置互斥信号量mutex,初值为1
  • 对不同的临界资源要设置不同的互斥信号量mutex1、mutex2……

信号量机制实现进程同步:前V后P

  • 同步就是要保证一前一后执行两个操作

  • 设置同步信号量S,初值为0

  • 在前操作之后执行V(S),在后操作之前执行P(S)操作系统-------信号量和死锁_第3张图片

信号量机制实现前驱关系

  • 每一对前驱关系都是一个进程同步问题,因此为每一对前驱关系设置一个同步信号量

 
 

2.用信号量机制解决问题

2.1生产者消费者问题

  • 生产者和消费者共享一个初始为空、大小为n的缓冲区

    • 二者必须互斥的访问缓冲区(互斥)

    • 只有缓冲区没满的时候,生产者才能把产品放入缓冲区,否则必须等待(同步)

    • 只有缓冲区不空时,消费这才能从中取走产品,否则等待(同步)

 
操作系统-------信号量和死锁_第4张图片

  • 实现互斥的P操作一定要在实现同步的P操作之后,否则死锁
  • V操作不会导致进程阻塞,可以交换
  • 生产产品,使用产品最好不要放到缓冲区去执行,压力会很大

 

2.2多生产者消费者问题

操作系统-------信号量和死锁_第5张图片
操作系统-------信号量和死锁_第6张图片
操作系统-------信号量和死锁_第7张图片

当缓冲区为1时,此问题可以不写互斥的P、V

分析这类问题要从事件的角度出发:盘子变空-------->放入水果

 

2.3吸烟者问题(单生产者)

操作系统-------信号量和死锁_第8张图片

 

2.4读写者问题

在这里插入图片描述
操作系统-------信号量和死锁_第9张图片
 
操作系统-------信号量和死锁_第10张图片
 
在这里插入图片描述

 

2.5哲学家进餐问题

  • 每个进程都需要持有两个临界资源,容易死锁

    操作系统-------信号量和死锁_第11张图片
    操作系统-------信号量和死锁_第12张图片

 
 

3.管程

  • 管程也是用来实现进程的互斥和同步,管程就是解决了信号量机制麻烦,易错问题。封装思想
  • 管程相当于类,组成部分:
    • 共享数据结构(类)
    • 对数据结构操作的一组过程(函数)
    • 共享数据设置初始值
    • 通过函数才能访问共享数据
    • 管程有一个名字
  • 互斥特性由编译器执行,我们不需要关心
  • 每次仅允许一个进程在管程内执行函数
  • 可在管程中设置条件变量、等待、唤醒操作解决同步问题

 
 

4.死锁

4.1概述

死锁:各进程互相等待对方手里的资源,导致各进程都阻塞,无法推进

  • 至少两个进程或者两个进程进程以上才会死锁
  • 必为阻塞态,缺少资源

饥饿:长期得不到想要的资源,如短进程优先,某个长进程就会饥饿

  • 一个进程饥饿
  • 就绪态(缺CPU)、阻塞态(缺I/O设备)

死循环:某个进程执行一直挑不出某个循环,逻辑bug

  • 只有一个进程死循环

  • 死循环可以处于运行态,是管理者的问题,不是操作系统的问题

 

死锁产生的4个必要条件:

  • 互斥条件:对必须互斥使用资源的争抢
  • 不剥夺条件:未使用完之前,不能由其他进程强行夺走
  • 请求和保持条件:已经有了至少一个资源,但又提出了新的资源请求
  • 循环等待条件:存在资源的循环等待链

存在循环等待的时候未必死锁,如果同类资源大于1,就不会死锁。

对不可剥夺资源的不合理分配就会发生死锁(互斥信号量在同步信号量之前会死锁)

 

死锁处理策略:

操作系统-------信号量和死锁_第13张图片

 

4.2预防死锁

破坏死锁产生条件之一

破坏互斥条件:

  • 将互斥资源变为共享资源,就不会争抢了
  • 缺点:很多时候互斥资源不可以改为共享的,为了系统的安全,很多时候无法破坏互斥性操作系统-------信号量和死锁_第14张图片

 

破坏不剥夺条件:

  • 方案一:当某个进程请求新的资源得不到满足,就立即释放现有资源,需要的时候再申请
  • 方案二:某个进程所需资源被其它进程占用,可以由操作系统协助,将想要的资源强行抢过来,这种方式考虑的是优先级
  • 缺点:
    • 实现起来相对复杂
    • 释放已有资源可能造成前面工作失效,因此只适合易于保存和恢复的资源,如CPU
    • 仿佛申请释放资源会增加系统开销,降低系统吞吐量
    • 采用方案一可能会饥饿

 
破坏请求保持条件:

  • 采用静态分配法,一次申请完他所需要的全部资源
  • 缺点:资源利用率低,可能饥饿
     

破坏循环等待条件:

  • 采用顺序资源分配法,给资源编号,按照从小到大申请
  • 缺点:不方便增加新设备,要重新编号
  • 实际使用资源顺序和编号不一致,造成资源浪费
  • 必须按顺序申请,编程麻烦

 

4.3避免死锁

安全序列:系统按照某种序列分配资源,每个进程都能顺利完成,即处于安全状态。

安全序列可以有多个。

系统处于不安全状态可能会死锁,死锁一定是处于不安全状态

银行家算法核心思想:进程提出申请资源,先预测一下是哦福会导致进入不安全状态,如果会,不答应这次请求,先让进程阻塞等待。

 

4.4死锁的检测和解除

死锁的检测:

数据结构:来保存资源的请求和分配信息

操作系统-------信号量和死锁_第15张图片

上述请求让p1先执行,p1执行完成后,释放资源和请求,p2就可以执行了。这是一种安全状态,最终能消除所有边,一定不会发生死锁。

死锁定理:如果某时刻系统的资源分配图时不可完全简化的,就发生了死锁。

最终害连这边的进程就是处于死锁状态的进程。

 

死锁解除方法:
操作系统-------信号量和死锁_第16张图片

我们可以选择下面这些进程用来牺牲,以解除死锁:

  • 优先级低的
  • 已经执行的时间较短
  • 还要很长时间才能完成的
  • 进程已经使用的资源多的
  • 进程是批处理式,而非交互式

你可能感兴趣的:(操作系统,windows)