操作系统的知识点汇总

操作系统具有以下几个主要特征:

1. 并发性:指两个或多个事件在同一时间间隔内发生。在操作系统中,多个程序可以同时运行,宏观上看是并发的,但微观上某一时刻只有一个程序在执行。

2. 共享性:指系统中的资源可供内存中多个并发执行的进程共同使用。资源共享可以分为互斥共享和同时共享两种方式。

3. 虚拟性:通过某种技术把一个物理实体变为若干个逻辑上的对应物。例如虚拟内存技术,将物理内存虚拟化为比实际内存更大的逻辑内存。

4. 异步性:进程以不可预知的速度向前推进。每个进程何时执行、何时暂停以及以怎样的速度向前推进都是不可预知的。

这些特征相互依存、相互影响,共同构成了操作系统的复杂功能和高效运行机制。

计算机系统资源的管理者在计算机系统中,操作系统扮演着系统资源管理者的关键角色。系统资源包括处理器(CPU)、内存、存储设备、输入/输出设备等。

用户与计算机系统之间的接口

命令接口是用户通过输入命令来控制计算机系统的一种方式。这种接口通常适用于有一定技术背景的用户,他们能够熟练使用特定的命令来完成各种操作。例如,在 Windows 系统中的命令提示符(CMD)中,用户可以输入“dir”命令来查看当前目录下的文件和文件夹列表;在 Linux 系统中,“sudo apt-get install”命令用于安装软件包。

程序接口则是为程序员提供的,允许他们通过编写程序来访问系统的功能和资源。例如,各种编程语言都提供了系统调用的接口,以便程序能够进行文件操作、网络通信等。

GUI(图形用户界面)是一种直观、易于使用的接口,通过图形元素如窗口、图标、菜单等,让用户可以通过鼠标和键盘的简单操作与计算机进行交互。例如,Windows 操作系统的桌面环境,用户可以通过点击图标来启动程序,通过菜单选择执行各种操作。

扩充机器:

没有任何软件支持的计算机称为裸机,而覆盖了软件的机器称为扩充机器或虚拟机。

操作系统实现了对硬件机器的扩展。硬件如同工具和材料,而操作系统则像优秀的工匠,通过操作系统,简单的硬件原料可以组成各种具有丰富功能的“物品”,供人们便捷地使用。

例如,操作系统提供了虚拟内存功能,使得计算机可以运行比物理内存更大的程序;设备驱动程序将复杂的硬件设备操作封装起来,为用户提供了方便的使用接口;文件系统帮助用户更方便地组织、存储和管理数据;图形用户界面(GUI)则提供了直观、可视化的操作界面等。这些都是操作系统对硬件机器进行扩充的具体表现。

从用户的角度来看,有了操作系统,计算机的功能变得更强大、使用更方便,就好像计算机本身具备了这些扩展后的功能一样。这种扩充使得用户无需直接了解和处理复杂的硬件细节,能够更加高效、便捷地使用计算机完成各种任务

批处理操作系统(Batch Operating System)

特点:用户将作业成批提交给计算机,由操作系统自动地、顺序地执行作业,减少了人工干预和作业准备时间。

优点:系统资源利用率高,系统吞吐量较大。

缺点:无交互性,用户一旦提交作业就失去了对其运行的控制;作业平均周转时间较长。

分时操作系统(Time Sharing Operating System)

特点:多个用户通过终端同时与计算机交互,系统将 CPU 时间划分成很短的时间片,轮流分配给各个终端用户使用。

优点:具有交互性,用户可以及时响应和控制自己的作业;多用户同时使用,提高了资源利用率。

缺点:响应时间有时较长,不能满足对响应时间要求苛刻的任务。

实时操作系统(Real Time Operating System)

特点:系统能够及时响应外部事件,并在规定的时间内完成对事件的处理。根据对响应时间的严格程度,分为硬实时操作系统和软实时操作系统。

优点:能够保证关键任务的实时性和可靠性。

缺点:系统设计较为复杂,资源开销较大。

网络操作系统(Network Operating System)

特点:基于计算机网络环境,在各种计算机操作系统上按网络体系结构协议标准开发的软件,包括网络管理、通信、资源共享、系统安全和多种网络应用服务等。

优点:实现了网络中计算机之间的资源共享和协同工作。

缺点:对网络带宽和稳定性有一定依赖。

分布式操作系统(Distributed Operating System)

特点:通过网络将多个分散的计算机连接起来,实现资源共享、协同工作和分布式处理。系统中的多个处理机无主次之分,系统具有高度的内聚性和透明性。

优点:具有更高的可靠性、可用性和扩展性,能够处理大规模的计算任务。

缺点:系统设计和实现难度较大,需要解决分布式一致性等复杂问题。

中断是指由外部设备或事件引起的 CPU 暂停当前程序的执行,转而处理外部事件的机制。常见的中断类型包括:

硬件中断:由外部硬件设备产生,例如 I/O 设备完成数据传输、时钟定时到达等。

软件中断:由程序中的特定指令产生,通常用于实现系统调用或特定的功能切换。

中断的作用包括:

实现 I/O 设备与 CPU 的并行工作,提高系统效率。

实时处理外部事件,增强系统的响应能力。

异常则是由 CPU 内部事件或执行指令引起的程序执行的非正常情况。常见的异常类型有:

程序性异常:如算术运算溢出、除数为零、非法指令等。

访存异常:访问非法的内存地址。

异常的处理过程通常包括:

保存当前程序的状态信息,如程序计数器、寄存器的值等。

确定异常的类型和原因。

根据异常类型进行相应的处理,可能包括终止程序、进行错误恢复或调用特定的异常处理程序。

中断和异常都能导致 CPU 从当前正在执行的程序切换到相应的中断或异常处理程序,处理完成后再返回原来的程序继续执行。

系统调用是操作系统提供给应用程序的接口,应用程序通过系统调用请求操作系统的服务。

系统调用的主要作用包括:

实现资源访问控制:操作系统通过系统调用对系统资源(如内存、文件、设备等)的访问进行严格控制,确保应用程序只能在允许的范围内使用资源,保障系统的安全性和稳定性。

提供统一的服务接口:使得不同的应用程序能够以相同的方式请求操作系统的服务,增强了程序的可移植性。

系统调用的执行过程通常如下:

应用程序执行到系统调用指令,产生一个中断或异常。

CPU 从用户态切换到内核态,这通常通过执行特定的指令(如陷入指令)来实现。

操作系统内核根据系统调用号,查找相应的服务例程。

内核执行服务例程,完成所需的操作。

操作完成后,内核将结果返回给应用程序,并将 CPU 状态从内核态切换回用户态,应用程序继续执行。

常见的系统调用类型包括:

文件操作:如打开、关闭、读写文件等。

进程管理:创建、终止进程,获取进程信息等。

内存管理:分配、释放内存。

设备管理:控制设备的输入输出。

进程是操作系统中一个重要的概念。

进程是指在系统中正在运行的一个程序的实例,它包含了程序执行所需的各种资源,如内存空间、CPU 时间、打开的文件、I/O 设备等。进程具有动态性、独立性和并发性等特征。程序则是一组指令的有序集合,是一个静态的概念,它描述了为完成特定任务所需的操作步骤和逻辑。

进程和程序的主要区别在于:

1. 进程是动态的,程序是静态的。进程是程序的执行过程,会随着时间的推进而产生状态变化;而程序只是一组指令的集合,不具有执行的动态特征。

2. 进程具有并发性,而程序不具有。多个进程可以在同一时间内并发执行;而程序本身无法并发执行。

3. 进程是暂时的,程序是永久的。进程会随着其任务的完成而终止;而程序只要不被删除,就会一直存在。

4. 进程具有独立性,每个进程都有自己独立的资源和状态;而程序通常不具备这种独立性。

总之,程序是进程的基础,进程是程序的执行。

进程具有以下特征:

1. 动态性:进程是程序的一次执行过程,具有创建、活动、暂停、终止等生命周期中的各种状态变化。

2. 并发性:多个进程可以在同一时间段内同时执行,宏观上并行,微观上串行。

3. 独立性:进程是系统进行资源分配和调度的基本单位,每个进程都拥有独立的资源,如内存空间、文件描述符等。

4. 异步性:由于进程的执行速度不可预知,每个进程都以不可预知的速度向前推进。

5. 结构性:进程通常由程序段、数据段和进程控制块(PCB)三部分组成。

这些特征使得进程在操作系统中能够有效地进行资源分配和任务执行。

进程在其生命周期中会处于不同的状态,常见的进程状态包括:

就绪态(Ready):进程已经准备好,等待被分配 CPU 资源来执行。此时,进程除了 CPU 之外,其他所需的资源都已具备。

运行态(Running):进程正在 CPU 上执行。在单 CPU 系统中,同一时刻只能有一个进程处于运行态。

阻塞态(Blocked 或 Waiting):进程由于等待某个事件的发生(如等待 I/O 操作完成、等待资源分配等)而暂时无法继续执行,处于阻塞状态。

此外,还有一些细化的状态,例如:

新建态(New):进程刚刚被创建,但还没有被放入就绪队列,操作系统还没有完成对其资源的分配和初始化工作。

终止态(Terminated):进程已完成执行或因某种原因被终止,操作系统将回收其占用的资源。

进程状态的转换通常由以下情况引起:

就绪态 -> 运行态:当操作系统选择一个就绪进程,并为其分配 CPU 资源时,该进程从就绪态转换为运行态。

运行态 -> 就绪态:当正在运行的进程时间片用完,或者出现更高优先级的就绪进程时,当前运行进程会被剥夺 CPU 资源,回到就绪态。

运行态 -> 阻塞态:如果进程在运行过程中需要等待某个事件发生,如等待输入、等待资源等,它会从运行态转换为阻塞态。

阻塞态 -> 就绪态:当进程等待的事件完成,它会从阻塞态转换为就绪态,等待再次被分配 CPU 资源执行。

这些状态和状态转换的管理是操作系统进行进程调度和资源分配的重要依据,以确保系统的高效运行和资源的合理利用。

进程控制是操作系统内核的重要功能之一,它负责对进程的创建、终止、状态转换等进行管理和控制。

进程控制的主要功能包括:

进程创建

为新进程分配唯一的进程标识符(PID)。

为进程分配内存空间,包括程序代码、数据和堆栈等。

初始化进程控制块(PCB),设置进程的初始状态、优先级等信息。

将新进程插入到就绪队列中等待调度执行。

进程终止

回收进程所占用的资源,包括内存、文件描述符、设备等。

从系统中的各种队列(如就绪队列、阻塞队列)中删除该进程的 PCB。

通知父进程或其他相关进程该进程的终止情况。

进程阻塞

当进程需要等待某个事件发生时,将其状态从运行态或就绪态转换为阻塞态。

将进程的 PCB 从相应的队列中移除,并插入到等待该事件的阻塞队列中。

进程唤醒

当进程等待的事件发生时,将其从阻塞队列中移出。

将进程的状态从阻塞态转换为就绪态,并将其 PCB 插入到就绪队列中。

进程切换

保存当前运行进程的上下文,包括 CPU 寄存器的值、程序计数器、堆栈指针等。

选择一个新的就绪进程。

恢复新进程的上下文,使其开始执行。

进程控制通常通过原语来实现,原语是一种不可分割的、具有原子性的操作。常见的进程控制原语包括创建原语、终止原语、阻塞原语和唤醒原语等。

在实现进程控制时,操作系统需要考虑以下几个方面:

同步与互斥:在对进程状态和资源进行操作时,要确保操作的原子性和正确性,避免出现竞争条件和不一致的情况。

资源管理:合理分配和回收进程所需的各种资源,以提高系统的资源利用率和性能。

调度策略:进程的状态转换和切换需要与系统的调度策略相结合,以保证系统的公平性和效率。

错误处理:对进程控制过程中可能出现的各种错误情况进行有效的处理和恢复。

总之,进程控制是操作系统中确保进程正确、高效运行的关键机制,它对于系统的稳定性、性能和用户体验都有着重要的影响。

进程的组织是指操作系统对多个进程进行有效管理和调度的方式。常见的进程组织方式有链接方式和索引方式:

链接方式:使用队列来组织进程的 PCB(进程控制块)。系统按照进程状态将 PCB 分为多个队列,如就绪队列、阻塞队列等。每个队列可以看作是一个链表,通过指针将具有相同状态的 PCB 链接在一起。例如,就绪队列指针指向当前处于就绪态的进程,阻塞队列指针指向当前处于阻塞态的进程。在单 CPU 计算机中,同一时刻只会有一个进程处于运行态,其执行指针会指向该进程的 PCB。这种方式适用于进程数量较少的情况。

索引方式:根据进程状态的不同,建立多张索引表。每个索引表指向具有相同状态的一组 PCB。例如,有就绪索引表、阻塞索引表等。操作系统持有各个索引表的指针,通过索引表可以快速找到特定状态的进程 PCB。这种方式在进程数量较多时可以提高查找效率。

通过这些组织方式,操作系统能够方便地对进程进行管理、调度和切换,以实现多进程的并发执行,充分利用系统资源,提高计算机的性能和效率。

另外,在一些操作系统中,还会使用哈希表等数据结构来快速查找目标进程的 PCB。同时,为了表示进程之间的关系,

进程组织的目的是为了更好地管理和协调多个进程的运行,使它们能够合理地分配资源、进行切换和通信等操作,从而保证系统的稳定性和高效性。不同的操作系统可能会根据自身的特点和需求,采用不同的进程组织方式或对这些方式进行一定的改进和优化。

进程通信是指进程之间交换数据和信息的机制。常见的进程通信方式主要有以下几种:

共享存储

基于共享数据结构的通信:这种方式通常速度较慢,并且需要程序员自行解决同步互斥问题。例如多个进程共同访问一个共享的缓冲区,需要注意读写的顺序和并发控制。

基于共享存储区的通信:在内存中划出一块共享存储区域,多个进程可以直接读写该区域。为了保证数据的一致性,通常需要使用同步机制,如信号量。

消息传递

直接通信方式:发送进程直接把消息发送给接收进程,并指明接收进程的名字。接收进程也可以直接从发送进程接收消息。

间接通信方式:通过信箱来进行通信。发送进程把消息发送到信箱,接收进程从信箱中获取消息。信箱可以看作是一个中间存储区域。

管道通信

所谓管道,是指用于连接一个读进程和一个写进程以实现它们之间通信的一个共享文件,又名pipe文件。向管道(共享文件)提供输入的发送进程(即写进程),以字符流形式将大量的数据送入管道;而接收进程可从管道中接收数据。

信号量机制

这是一种低级的进程通信方式,主要用于实现进程之间的同步与互斥。信号量实际上是一个整型变量,通过对其进行操作(P 操作和 V 操作)来实现进程间的协调。

线程是进程中的一个执行单元,是进程内的一条执行路径。

线程和进程的区别主要体现在以下几个方面:

资源拥有:进程拥有独立的地址空间和资源,如内存、文件等;而线程共享所属进程的资源,除了线程自身的少量栈空间和寄存器等。

调度:进程是资源分配的基本单位,线程是调度的基本单位。线程切换的开销通常比进程切换小。

并发性:进程之间并发程度较低,线程之间并发程度较高,可以更高效地利用多核处理器。

系统开销:创建或撤销进程时系统开销较大,而创建或撤销线程的开销较小。

线程的属性包括:

线程标识符:用于唯一标识线程。

线程状态:如就绪、运行、阻塞等。

线程优先级:决定线程获得 CPU 资源的优先级。

线程上下文:包括线程的栈、寄存器等。

线程专属数据:某些数据仅属于特定线程。

线程的实现方式主要有以下两种:

用户级线程(User-Level Thread,ULT)

线程的管理工作由应用程序完成,内核并不知道线程的存在。

优点:切换速度快,因为不需要陷入内核;调度算法可以由应用程序定制,更加灵活。

缺点:当一个线程被阻塞时,整个进程都会被阻塞;不能利用多核处理器的优势,因为内核一次只能调度一个进程。

内核级线程(Kernel-Level Thread,KLT)

线程的管理工作由内核完成。

优点:一个线程阻塞时,其他线程可以继续运行;可以充分利用多核处理器,实现真正的并行。

缺点:线程切换需要陷入内核,切换开销较大。

还有一种结合了用户级线程和内核级线程优点的实现方式,称为组合方式:

将多个用户级线程映射到少数几个内核级线程上。这样既可以有用户级线程切换的高效性,又能在一定程度上发挥多核处理器的优势。

处理机调度是操作系统的重要功能之一,它的主要任务是从就绪队列中按照一定的算法选择一个进程或线程,并将处理机分配给它,以实现进程或线程的并发执行。

三级调度分别是:

高级调度(作业调度):从外存的后备队列中选择一批作业调入内存,为它们创建进程并分配必要的资源。高级调度的频率相对较低,通常几分钟一次。

中级调度(内存调度):将暂时不能运行的进程调至外存等待,等其具备运行条件且内存有足够空间时,再重新调入内存。中级调度的目的是提高内存利用率和系统吞吐量。

低级调度(进程调度):从就绪队列中选取一个进程,并将处理机分配给它。进程调度是最基本的调度,其频率很高,通常几十毫秒一次。

这三级调度相互配合,共同完成处理机的分配和管理工作,以提高系统的性能和资源利用率。

处理机调度的调度方式主要有两种:抢占式调度和非抢占式调度。

非抢占式调度:一旦某个进程或线程开始运行,就会一直运行下去,直到它完成任务、主动放弃处理机或者因某种原因被阻塞,才会将处理机让给其他进程或线程。

抢占式调度:允许正在运行的进程或线程被中断,将处理机分配给更重要或更紧急的进程或线程。抢占的原则通常基于优先级、时间片用完等因素。

例如,基于优先级的抢占式调度中,如果一个更高优先级的进程就绪,系统会立即暂停当前运行的低优先级进程,将处理机分配给高优先级进程。在基于时间片的调度中,当一个进程的时间片用完,就会被抢占,处理机分配给下一个就绪进程。

非抢占式调度实现简单,但可能导致某些紧急任务得不到及时处理;抢占式调度能更好地响应紧急任务,但系统开销相对较大。

调度准则是用于评估和比较不同调度算法优劣的标准,常见的调度准则包括以下几个方面:

周转时间:从作业提交到完成的时间间隔。对于进程,周转时间是从进程创建到结束的时间。周转时间越短,系统的性能通常越好。

响应时间:从用户提交请求到系统首次产生响应的时间。在交互式系统中,响应时间是一个重要的指标,越短越好,能提供更好的用户体验。

截止时间:任务必须完成的时间。对于有严格时间限制的任务,满足截止时间是关键。

吞吐量:单位时间内完成的作业数量或进程数量。在批处理系统中,吞吐量是一个重要的考量因素。

处理机利用率:处理机处于忙碌状态的时间比例。但过高追求处理机利用率可能会导致其他指标的下降。

公平性:确保每个进程或作业都能获得合理的处理机时间,避免某些进程长期得不到调度。

等待时间:进程在就绪队列中等待的时间。等待时间越短,系统的平均响应性能越好。

不同的系统和应用场景可能会侧重不同的调度准则。例如,实时系统更关注截止时间和响应时间,而批处理系统可能更注重吞吐量和周转时间。

几种常见的处理机调度算法:

先来先服务(First Come First Served,FCFS)调度算法:按照作业或进程到达的先后顺序进行调度。优点是实现简单、公平;缺点是对短作业不利,可能导致平均等待时间较长。

短作业优先(Shortest Job First,SJF)调度算法:优先调度运行时间短的作业或进程。优点是平均周转时间短;缺点是可能导致长作业长时间得不到调度,且需要预知作业的运行时间。

优先级调度算法:为每个作业或进程赋予一个优先级,调度时优先选择优先级高的。可以分为静态优先级和动态优先级,静态优先级在创建时确定,不再改变;动态优先级会根据进程的运行情况动态调整。

高响应比优先调度算法:综合考虑作业的等待时间和要求服务的时间,响应比 = (等待时间 + 要求服务时间)/ 要求服务时间。响应比高的作业优先调度,在一定程度上克服了短作业优先和先来先服务算法的缺点。

时间片轮转调度算法:将处理机的时间分成固定大小的时间片,每个进程轮流获得一个时间片运行。如果时间片用完进程还未完成,则将其放入就绪队列末尾等待下一轮调度。这种算法主要用于分时系统。

多级反馈队列调度算法:设置多个就绪队列,每个队列具有不同的优先级和时间片大小。新进程首先进入最高优先级队列,按时间片轮转调度;如果未完成则降到下一级队列;优先级越低,时间片越大。这种算法能较好地满足不同类型进程的需求。

不同的调度算法在不同的场景下有不同的性能表现,操作系统会根据具体情况选择合适的调度算法或进行组合使用。

进程同步是指多个进程在执行过程中相互协作、协调工作,按照一定的顺序或规则来访问和操作共享资源,以避免出现错误或不一致的情况。在多进程环境中,由于进程的异步性和并发执行,可能会导致对共享资源的访问冲突。例如,两个进程同时对一个数据进行修改,可能会使数据处于混乱状态。进程同步的主要任务是确保多个进程在执行关键操作时能够有序、正确地进行,从而保证系统的正确性和稳定性。常见的进程同步机制包括信号量、管程、互斥锁等。

信号量(Semaphore)

分为整型和记录型信号量

如前面给您讲解的,信号量是一个整型变量,配合 P 操作和 V 操作来实现进程同步。可以用于控制多个进程对共享资源的访问,确保同一时刻只有符合条件的进程能够进入临界区操作共享资源。

例如,有多个进程要打印文档,打印机数量有限,就可以用信号量来控制,只有获取到信号量许可的进程才能使用打印机进行打印。

管程(Monitor)

管程是将共享资源以及对共享资源的操作集中起来,形成一个相对独立的模块。多个进程只能通过管程定义的特定入口来访问共享资源。

打个比方,管程就像一个有管理员的仓库,要存取货物(共享资源),都得通过管理员按照规定的流程来操作,进程们不能随意自行存取。

消息传递(Message Passing)

进程之间通过发送和接收消息来进行同步和通信。

比如进程 A 完成了一部分任务后,给进程 B 发送一个“任务完成”的消息,进程 B 收到这个消息后才开始自己的相关任务操作。

共享内存(Shared Memory)

多个进程可以访问同一块物理内存区域。

想象一下有一块公共的白板(共享内存),不同的人(进程)都可以在上面写字、读取内容,但是为了避免冲突,需要有一些同步机制(如信号量)来协调谁在什么时候可以进行操作。

这些方法各有特点和适用场景,在实际应用中需要根据具体的需求和系统环境来选择合适的进程同步方法

生产者 - 消费者问题

这是一个经典的并发同步问题。生产者负责生产产品并将其放入缓冲区,消费者从缓冲区取出产品进行消费。

读者 - 写者问题

存在读者(只读数据)和写者(读写数据)对共享数据的访问。读者可以同时读取数据,但写者在写数据时需要独占访问权。比如在一个图书馆中,多个读者可以同时阅读同一本书,但在有人修改这本书的内容(写者)时,其他人不能同时进行操作。

哲学家进餐问题

若干哲学家围绕一张圆桌而坐,桌上有筷子。哲学家在思考和进餐之间交替,进餐时需要拿起左右两边的筷子。可能会出现死锁等并发问题,需要合理的算法来解决。这类似于资源竞争的情况,例如多个进程竞争有限的资源。

吸烟者问题

有三个抽烟者和一个供应者。抽烟者需要烟草、纸和火柴才能抽烟,供应者随机提供两种材料,缺少的材料由抽烟者自己提供。

死锁是指在多进程或多线程系统中,两个或多个进程(线程)因竞争资源而造成的一种互相等待的僵持状态,如果没有外力作用,它们都无法推进。

打个比方,就像两个人过独木桥,一个人从桥的这头走向那头,另一个人从桥的那头走向这头,两人在桥中间相遇,谁也不愿意后退让对方先过,于是就僵持在那里,这就是一种死锁的状态

原因及其条件

互斥条件:系统中的资源不能被多个进程(线程)同时使用,在一段时间内只能被一个进程(线程)使用。比如打印机,同一时刻只能被一个进程使用来打印文件

请求和保持条件:进程(线程)在持有一部分资源的情况下,又去请求其他资源,但是对已持有的资源又不释放。例如,一个进程已经占用了打印机资源,在使用打印机的过程中,又去申请使用扫描仪资源,并且还不释放打印机资源

不可剥夺条件:进程(线程)已获得的资源,在未使用完之前,不能被其他进程强行夺走,只能由该进程自行释放。比如一个进程正在使用内存空间存放数据,其他进程不能强行将这块内存分配给别的用途

循环等待条件:存在一种进程资源的循环等待链,链中的每一个进程已获得的资源同时被下一个进程所请求。比如进程 P1 等待进程 P2 占用的资源,P2 等待 P3 占用的资源,P3 又等待 P1 占用的资源

预防死锁(Deadlock Prevention)

破坏“互斥条件”:如果允许系统资源都能共享使用,那么死锁就不会发生。但有些资源本身的特性决定了无法共享,如打印机等,所以这种方法通常较难实现。

破坏“请求和保持条件”:可以要求进程在运行前一次性申请它所需要的全部资源,如果系统不能满足全部资源请求,那么该进程就不投入运行。但这种方法降低了资源利用率和进程的并发程度。

破坏“不可剥夺条件”:当一个进程请求新的资源得不到满足时,它必须释放已占有的资源,这可能导致进程前功尽弃和反复申请释放资源的额外开销。

破坏“循环等待条件”:可以采用资源有序分配法,将系统中的资源进行编号,规定进程必须按照资源编号递增(或递减)的顺序申请资源,这样就不会形成循环等待链。

避免死锁(Deadlock Avoidance)

系统在进行资源分配之前,先计算此次资源分配的安全性。例如银行家算法,通过判断系统是否处于安全状态来决定是否分配资源,在分配资源时保证系统始终处于安全状态,从而避免死锁的发生。

检测和解除死锁(Deadlock Detection and Recovery)

死锁检测:通过某种算法(如资源分配图算法)检测系统中是否存在死锁。

死锁解除:一旦检测到死锁,就需要采取措施解除死锁。常见的方法有:资源剥夺法,即从一些进程那里强行剥夺足够数量的资源分配给死锁进程,以解除死锁;撤销进程法,即强制撤销部分甚至全部死锁进程,并剥夺这些进程的资源,以解除死锁;进程回退法,让一(或多)个进程回退到足以解除死锁的地步。

进程的执行过程可以大致分为以下几个阶段:

创建阶段(Creation):当操作系统接收到创建新进程的请求(例如用户启动一个应用程序、系统启动一个服务进程等),会为新进程分配一个唯一的进程标识符(PID),并为其分配必要的资源,如内存空间用于存储进程的程序代码、数据、栈等。还会建立进程控制块(PCB),用于存储进程的相关信息,如进程状态、优先级、资源需求等。

就绪阶段(Ready):进程创建完成后,进入就绪队列等待被调度程序选中获得 CPU 资源执行。在这个阶段,进程已经具备了除 CPU 之外的所有执行条件。

运行阶段(Running):调度程序从就绪队列中选择一个进程,并将 CPU 分配给它,该进程进入运行状态。在运行过程中,进程执行其指令序列,对数据进行处理和操作。

阻塞阶段(Blocked):如果进程在运行过程中需要等待某个事件的发生(如等待 I/O 操作完成、等待资源分配、等待信号等),它会放弃 CPU,进入阻塞状态。此时,进程被移出 CPU 运行队列,直到等待的事件发生,进程才会重新回到就绪队列等待调度。

终止阶段(Termination):当进程完成其任务,或者出现错误、被用户或其他进程终止时,进程进入终止状态。此时,操作系统会回收进程所占用的资源,如内存、文件句柄等,并删除进程的 PCB。

链接(Linking)是指将不同的目标文件、模块或者程序片段组合在一起,形成一个可执行的程序或者库的过程

链接的类型主要有以下几种:

静态链接(Static Linking)

在程序执行前,就将所有需要的目标模块以及所依赖的库函数链接成一个完整的可执行程序。在链接过程中,链接器会将目标模块中的代码和数据合并到最终的可执行文件中。

打个比方 ,静态链接就像是您提前把所有需要的食材和调料都按照固定的配方和比例准备好,装在一个密封的餐盒里,要用的时候直接拿出来整个餐盒进行烹饪。

优点:生成的可执行文件可以独立运行,不需要依赖其他模块或库文件;执行速度相对较快,因为在运行时不需要再进行链接操作。

缺点:生成的可执行文件体积较大,因为包含了所有需要的代码和数据;如果多个程序都使用了相同的库函数,那么每个程序都会包含一份相同的库函数代码,造成空间浪费。

动态链接(Dynamic Linking)

在程序运行时,才将需要的模块或者库函数加载到内存中并进行链接。动态链接又分为两种:

装入时动态链接(Load-time Dynamic Linking):在程序装入内存时,由装入程序把动态库模块链接到应用程序中。

运行时动态链接(Run-time Dynamic Linking):在程序执行过程中,当需要调用某一模块时,才将该模块动态链接到应用程序中。

还是用前面的比方 ,动态链接就像是您做饭的时候,需要什么食材或者调料,再临时从冰箱或者橱柜里拿出来使用。

优点:生成的可执行文件体积较小,因为不需要包含所有的库函数代码;多个程序可以共享同一个库函数的代码,节省了内存空间;库函数更新后,不需要重新编译应用程序,只需要更新库文件即可。

缺点:运行时的链接操作会增加程序的启动时间;如果库文件不存在或者版本不匹配,可能会导致程序无法运行。

装入:

绝对装入:在编译时,如果知道程序将驻留在内存的什么位置,那么编译程序将产生绝对地址的目标代码。装入程序按照事先确定的地址,将程序和数据装入内存。这种方式只适用于单道程序环境,并且要求程序员清楚地了解内存的使用情况和程序的存放位置。

可重定位装入:根据内存的当前情况,将装入模块装入到内存的适当位置。在装入时对目标程序中指令和数据的地址进行修改,将逻辑地址转换为物理地址。通常使用重定位寄存器来存放装入模块在内存中的起始地址,在执行指令时,会将指令中的逻辑地址与重定位寄存器中的值相加,得到物理地址。

动态运行时装入:程序在装入内存后,并不会立即把程序中的逻辑地址转换为物理地址,而是在程序执行过程中,每当执行一条指令时才将指令中的逻辑地址转换为物理地址。这种方式需要一个重定位寄存器的支持,并且采用动态重定位的方式进行地址转换。这种方式的优点是程序可以在内存中移动,并且可以将程序分配到不连续的存储区中,提高内存的利用率。

上下限寄存器

上下限寄存器用于内存保护。其中上限寄存器存储着分配给一个进程的内存空间的上限地址,下限寄存器存储着该进程内存空间的下限地址。

当进程运行过程中需要访问内存时,系统会将访问的地址与上下限寄存器中的值进行比较。如果访问地址在这个上下限范围内,那么访问被允许;如果访问地址小于下限地址或者大于上限地址,就会产生越界错误,系统会采取相应措施,比如终止进程或者发出错误提示,以防止该进程非法访问其他进程的内存空间。

基址、限长寄存器

基址寄存器存放的是分配给进程的内存空间的起始地址,限长寄存器存放的是该内存空间的长度。

当进程访问内存时,系统将访问的地址与基址相加,得到实际物理地址。然后将这个物理地址与基址加上限长得到的地址范围进行比较。如果计算得到的物理地址在这个范围内,访问被允许;否则,就判定为越界访问,系统会进行相应处理。

给您举个例子:假设我们为进程 A 设置基址寄存器的值为 1000,限长寄存器的值为 500。当进程 A 发出一个内存访问请求,逻辑地址为 200。系统将基址 1000 和逻辑地址 200 相加,得到物理地址 1200。因为 1200 处于基址 1000 到基址加上限长(1000 + 500 = 1500)的范围内,所以这次内存访问是合法的;如果请求的逻辑地址是 600,那么计算得到的物理地址 1600 就超出了范围,此次访问就是非法的

连续分配

连续分配是指为一个进程分配的内存空间是连续的一片区域。

单一连续分配:在单道程序环境下,内存被分为系统区和用户区。系统区仅提供给操作系统使用,用户区则提供给当前运行的单个用户程序使用。这种分配方式简单,但只能用于单用户、单任务的操作系统,内存利用率低。

固定分区分配:将内存空间划分为若干个固定大小的区域,每个分区大小可以相同,也可以不同。每个分区只能装入一道作业。这种方式会产生内部碎片,降低了内存空间的利用率,但实现较为简单。

动态分区分配:根据进程的实际需要,动态地为其分配内存空间。在进程装入或执行过程中,通过系统的管理程序,从空闲分区中寻找一个合适的分区分配给进程。这种方式会产生外部碎片,需要通过紧凑技术来解决。

非连续分配

非连续分配是指允许一个程序分散地装入到不相邻的内存分区中。

分页存储管理:将用户程序的地址空间分为若干固定大小的页面,内存空间也划分为与页面大小相同的物理块。通过页表建立页面与物理块之间的映射关系。这种方式有效解决了外部碎片问题,提高了内存利用率,但存在一定的页内碎片。

分段存储管理:将用户程序的地址空间按照程序自身的逻辑关系划分为若干个段,每个段都有一个段名和段长。通过段表建立段与内存物理地址之间的映射。分段便于程序的模块化处理和共享。

段页式存储管理:先将用户程序按逻辑结构分段,再将每个段划分为若干个固定大小的页面。系统为每个进程建立段表和每个段对应的页表。这种方式结合了分段和分页的优点,同时也带来了一定的系统开销。

连续分配

连续分配是指为一个进程分配的内存空间是连续的一片区域。

单一连续分配:在单道程序环境下,内存被分为系统区和用户区。系统区仅提供给操作系统使用,用户区则提供给当前运行的单个用户程序使用。这种分配方式简单,但只能用于单用户、单任务的操作系统,内存利用率低。

固定分区分配:将内存空间划分为若干个固定大小的区域,每个分区大小可以相同,也可以不同。每个分区只能装入一道作业。这种方式会产生内部碎片,降低了内存空间的利用率,但实现较为简单。

动态分区分配:根据进程的实际需要,动态地为其分配内存空间。在进程装入或执行过程中,通过系统的管理程序,从空闲分区中寻找一个合适的分区分配给进程。这种方式会产生外部碎片,需要通过紧凑技术来解决。

非连续分配

非连续分配是指允许一个程序分散地装入到不相邻的内存分区中。

分页存储管理:将用户程序的地址空间分为若干固定大小的页面,内存空间也划分为与页面大小相同的物理块。通过页表建立页面与物理块之间的映射关系。这种方式有效解决了外部碎片问题,提高了内存利用率,但存在一定的页内碎片。

分段存储管理:将用户程序的地址空间按照程序自身的逻辑关系划分为若干个段,每个段都有一个段名和段长。通过段表建立段与内存物理地址之间的映射。分段便于程序的模块化处理和共享。

段页式存储管理:先将用户程序按逻辑结构分段,再将每个段划分为若干个固定大小的页面。系统为每个进程建立段表和每个段对应的页表。这种方式结合了分段和分页的优点,同时也带来了一定的系统开销。

动态分区分配的分配算法

首次适应算法(First Fit)

原理:从空闲分区表(链)的首地址开始查找,将第一个能够满足作业大小要求的空闲分区分配给作业。

优点:优先利用内存低地址部分的空闲分区,保留了高地址部分的大空闲区,为大作业的分配创造了条件。

缺点:低地址部分不断被划分,会留下许多难以利用的、小的空闲分区,并且每次分配都从头部开始查找,增加了查找开销。

举例:假设有一系列空闲分区,地址分别从 100KB 到 200KB、300KB 到 400KB、500KB 到 600KB。现在有一个大小为 50KB 的作业请求,首次适应算法会从第一个空闲分区 100KB 到 200KB 中分配 50KB 给该作业。

循环首次适应算法(Next Fit)

原理:从上一次分配的空闲分区的下一个空闲分区开始查找,直到找到第一个能满足要求的空闲分区。

优点:使空闲分区分布更加均匀,减少了查找空闲分区时的开销。

缺点:会导致缺乏大的空闲分区。

举例:假设上次分配是在 100KB 到 200KB 的空闲分区中进行,下一次作业到来时,会从 200KB 之后的空闲分区开始查找分配空间。

最佳适应算法(Best Fit)

原理:将空闲分区按容量从小到大的顺序形成空闲分区链(表),每次分配时,从最小的满足要求的空闲分区中分配。

优点:每次分配给作业的都是最适合该作业大小的空闲分区,能避免“大材小用”,使内存中的空闲分区尽可能得到充分利用。

缺点:会留下很多难以利用的小空闲分区(外部碎片)。

举例:有多个空闲分区,大小分别为 50KB、100KB、150KB,现在有一个 80KB 的作业请求,最佳适应算法会选择 100KB 的空闲分区进行分配,分割出 80KB 给作业,剩余 20KB 的空闲分区。

最坏适应算法(Worst Fit)

原理:将空闲分区按容量从大到小的顺序形成空闲分区链(表),每次分配时,总是从最大的空闲分区中分配。

优点:使剩下的空闲分区不至于太小,产生的碎片相对较少,有利于中小作业的分配。

缺点:不利于大作业的分配。

举例:假设存在空闲分区大小分别为 200KB、100KB、50KB,有一个 80KB 的作业请求,最坏适应算法会选择 200KB 的空闲分区进行分配,分割出 80KB 给作业,剩余 120KB 的空闲分区。

页式存储管理

页面:将进程的逻辑空间和内存空间都划分为大小相等的区域,这些区域称为页面(Page)。页面的大小是固定的,由系统决定。

地址结构:页式存储管理中的逻辑地址结构包含两部分:页号和页内偏移量。页号用于标识页面,页内偏移量用于确定在页面内的具体位置。

页表:是用于记录页号与内存中物理块号对应关系的数据结构。通过页表,系统可以将逻辑地址转换为物理地址。

地址变换机构及变换过程:当 CPU 给出一个逻辑地址后,地址变换机构会将逻辑地址分为页号和页内偏移量。以页号为索引查找页表,得到对应的物理块号,再将物理块号与页内偏移量组合,就得到了物理地址。

快表:是一种高速缓冲存储器,用来存放当前访问最频繁的少数页表项。快表的存在可以加速地址变换过程,如果在快表中找到了所需的页表项,就可以快速完成地址变换,否则仍需去内存中的页表查找。

分类

基本分页存储管理:要求作业在运行前,所有页面都需装入内存才能运行。这种方式可能会产生内部碎片,因为页面大小固定,最后一页可能未被完全填满。

请求分页存储管理:作业运行时,不需要一次性将所有页面都装入内存,而是在需要时才将页面调入内存。

段式存储管理

段表:记录段号与段起始地址、段长度等信息的对应关系。

地址变换机构:CPU 给出逻辑地址后,由地址变换机构将逻辑地址中的段号与段表进行匹配,得到该段的起始地址和段长,然后检查段内偏移量是否超过段长,若未超,则将段起始地址与段内偏移量相加得到物理地址。

段的共享与保护:段式存储便于段的共享,不同进程的段表中,对于相同功能的段,可以指向相同的物理内存区域来实现共享。通过段表中的段长和访问权限等信息,可以对段进行保护。

段页式存储管理

段表:记录段号、段长、页表长度和页表起始地址等信息。

页表:记录页号与物理块号的对应关系。

覆盖(Overlay)

覆盖技术是指将程序划分为若干个功能上相对独立的程序段,按照其自身的逻辑结构,使那些不会同时执行的程序段共享同一块内存区域。

例如,一个程序有 A、B、C 三个模块,在某一时刻,程序的执行只需要 A 和 B 模块,或者只需要 A 和 C 模块。那么就可以将内存空间划分为两个区域,在不同的时间段,分别将 A 和 B 或者 A 和 C 装入这两个区域运行。

覆盖技术主要在早期内存较小的系统中使用,它要求程序员清楚地了解程序的逻辑结构和运行过程,手动将程序划分为不同的覆盖段,并且确定各个覆盖段的执行顺序和调用关系,这增加了程序员的负担。

交换(Swapping)

交换技术是指把暂时不用的某个程序及其数据从内存移到外存(比如磁盘)中,以便腾出内存空间给其他程序使用;或者把指定程序从外存调入到内存中并运行。

系统会根据内存使用情况和进程的状态来决定交换的时机和对象。例如,当内存资源紧张,而某些进程处于阻塞状态暂时不需要占用内存时,系统可以将这些进程交换到外存;当需要运行某个在外存中的进程时,系统会将其交换到内存中。

交换技术在一定程度上缓解了内存不足的问题,但由于涉及到内外存的数据交换,会产生较大的系统开销,如 I/O 操作、进程切换等。

虚拟内存概念

虚拟内存是指系统借助于外存,为用户提供一个比实际物理内存大得多的、可寻址的“内存空间”。虚拟内存使得应用程序认为它拥有连续可用的内存(一个连续完整的地址空间),而实际上,它通常是被分隔成多个物理内存碎片,还有部分暂时存储在外部磁盘存储器上,在需要时进行数据交换。

局部性原理

局部性原理是虚拟内存技术的理论基础。局部性原理包括时间局部性和空间局部性。

时间局部性是指如果程序中的某条指令一旦执行,不久后该指令可能再次执行;如果某数据被访问过,不久后该数据可能再次被访问。

空间局部性是指一旦程序访问了某个存储单元,不久后,其附近的存储单元也将被访问。

虚拟内存特征

多次性:一个作业可以分多次被调入内存运行。

对换性:作业运行过程中,允许将暂时不用的代码和数据调出到外存,需要时再调入内存。

虚拟性:能够从逻辑上扩充内存容量,使用户看到的内存容量远大于实际的物理内存容量。

请求分页

页表机构:除了基本的页号对应物理块号等信息外,还增加了状态位(指示该页是否在内存)、访问字段(记录页面的访问次数或最近访问时间,用于页面置换算法)、修改位(指示页面是否被修改过)和外存地址(页面在外存中的存放位置)等。

缺页中断机构:当访问的页面不在内存时,产生缺页中断,请求操作系统将所需页面调入内存。

地址变换机构:在基本的分页地址变换机构基础上,增加了缺页中断处理等功能。

页面置换算法

最佳置换(OPT):选择未来最长时间内不会被访问的页面进行置换。这是一种理论上的最优算法,但由于无法预知未来页面的访问情况,所以在实际系统中无法实现,主要用于对比其他算法的性能。

先进先出(FIFO):选择在内存中驻留时间最久的页面进行置换。可能会出现Belady异常,即分配的物理页面数增加,缺页次数反而增加的现象。

最近最久未使用(LRU):选择最近一段时间内最久没有被使用的页面进行置换。需要较多硬件支持来记录页面的使用历史。

时钟(CLOCK)算法:给每页设置一个访问位,将内存中的页面通过链接指针连接成一个环形队列,当需要置换页面时,循环检查各页面的访问位,如果是 0 就置换,是 1 则将其置为 0,循环下去直到找到可置换的页面。

页面分配策略

预调页策略:根据程序的运行规律,预测即将使用的页面,提前将其调入内存。

请求调页策略:仅当进程在运行中需要访问的页面不在内存时,才将其调入内存。

抖动

如果分配给进程的物理页面数量过少,进程会频繁产生缺页中断,导致大部分时间都用于页面的换进换出,而不是执行程序,这种现象称为抖动(Thrashing)。

工作集

工作集是指在某段时间间隔内,进程实际要访问的页面集合。

地址翻译

当 CPU 给出一个虚拟地址时,首先查找TLB(Translation Lookaside Buffer,快表),如果TLB命中,就直接得到物理地址;如果TLB不命中,就去查找页表;如果页表中该页不在内存(缺页),就会产生缺页中断,将所需页面从外存调入内存;如果页表命中,得到物理地址后,如果该物理地址对应的数据不在Cache中(Cache不命中),就从主存中读取数据;如果主存中也没有(缺页),就从外存中读取数据。

文件管理实现层次结构

文件管理通常可以分为多个层次,包括用户接口层、文件目录层、存取控制层、逻辑文件系统层、物理文件系统层和设备驱动层等。

用户接口层:为用户提供与文件系统交互的方式,如命令行界面或图形界面。

文件目录层:管理文件目录,实现文件名到文件信息的映射。

存取控制层:负责检查用户对文件的访问权限,确保合法访问。

逻辑文件系统层:将用户的逻辑文件操作转换为对物理文件存储的操作。

物理文件系统层:处理文件在物理存储设备上的布局和分配。

设备驱动层:与硬件设备进行通信,实现实际的读写操作。

目录实现

线性列表:将目录中的文件和子目录信息以线性的方式存储。查找时需要顺序遍历列表,效率较低。

哈希表:通过对文件名进行哈希运算,快速定位文件或子目录的信息,提高查找速度。

文件分配

连续分配:为文件分配连续的磁盘空间。优点是顺序访问速度快,缺点是容易产生外部碎片,不利于文件的扩展。

链接分配:分为隐式链接和显式链接。隐式链接通过文件块的指针依次链接,显式链接则通过文件分配表(FAT)记录块的链接关系。优点是不会产生外部碎片,缺点是随机访问效率低。

索引分配:为文件建立索引表来记录文件块的位置。

索引链接:将多个索引块链接起来,以支持大文件。

多层索引:通过多层索引结构来进一步扩展支持更大的文件。

混合索引:结合多种索引方式,提高文件分配的灵活性和效率。

文件存储空间管理

空闲表法:用一张表记录空闲的磁盘块。

空闲链表法:将空闲磁盘块通过链表连接起来。

位示图法:通过位图来表示磁盘块的使用情况,0 表示空闲,1 表示已使用。

成组链接法:将空闲块分组管理,结合了空闲表法和空闲链表法的优点。

磁盘访问时间

磁盘访问时间由寻道时间、延迟时间和传输时间三部分组成。

寻道时间:是指磁头移动到指定磁道所需要的时间。这就好比您在图书馆找特定的书架。

延迟时间:是指磁盘旋转到指定扇区所需要的时间。可以想象成等待书架上特定的那本书转到您面前。

传输时间:是指从磁盘读出或写入数据所经历的时间。类似于从转到面前的那本书中读取或写入信息的过程。

调度算法

先来先服务(FCFS):按照请求到达的先后顺序进行处理。就像排队买东西,先来的先服务,很公平,但可能不是最有效率的。

最短寻找时间优先(SSTF):优先处理离当前磁头位置最近的请求。这种方式可能会导致某些离磁头远的请求长时间得不到服务,产生“饥饿”现象。

扫描算法(SCAN):磁头在磁盘上双向移动,在移动过程中服务到达的请求。类似于电梯,先往一个方向移动,服务沿途请求,到头后再反向移动。

循环扫描(C-SCAN):磁头单向移动,从一端到另一端,然后直接返回起始端,途中服务请求。

磁盘的管理

初始化:在磁盘首次使用时,需要进行初始化操作,如划分磁道、扇区等。

引导块:磁盘的第一个扇区,包含了引导操作系统启动的必要信息。

坏块:磁盘中无法正常存储和读取数据的部分。通常会有相应的处理机制,如标记坏块,避免使用。

比如说,想象一个磁盘是一个大仓库,寻道时间就是找到对应的货架,延迟时间是等待要找的货物转到面前,传输时间是拿取或存放货物的时间。调度算法就是决定先去哪个货架取货的规则。而初始化是给仓库划分区域,引导块是仓库的入口指南,坏块就是仓库中损坏不能用的地方。

I/O 控制方式

程序直接控制:在这种方式下,CPU 像个全神贯注的“监工”,不停地询问 I/O 设备“你准备好了吗?”。这期间 CPU 一直被占用,不能做其他事情,效率极低。例如,从键盘输入数据,CPU 要不断检查键盘缓冲区是否有数据,直到有数据才能进行后续处理。

中断驱动方式:I/O 设备准备好数据后,会主动“喊”CPU 来处理,就像员工完成任务后主动通知老板。CPU 收到中断信号后,暂停当前工作,去处理 I/O 数据,处理完再回到之前的工作。这大大提高了 CPU 的利用率。比如,磁盘读取数据完成后发送中断,CPU 响应中断并读取数据。

DMA 方式:DMA 控制器相当于一个“小助手”,它接管了数据在内存和 I/O 设备之间的传输工作,不需要 CPU 一直参与。传输完成后,DMA 控制器通知 CPU 。比如从磁盘往内存传输大量数据,DMA 控制器负责具体的数据传输,CPU 可以去做其他重要的事。

通道方式:通道是一个更强大的“专业团队”,能独立完成复杂的 I/O 操作,进一步减轻 CPU 的负担。例如,多个磁盘同时进行数据传输,通道可以协调和管理这些操作。

I/O 层次结构

用户层 I/O:这是用户与操作系统交互的接口,用户通过系统调用请求 I/O 操作。

设备独立性软件:它隐藏了设备的具体细节,让用户程序不需要关心使用的是哪种具体设备。比如,用户只需指定打印文件,而无需知道连接的是哪台打印机。

设备驱动层:这是与硬件设备直接打交道的部分,包含了设备的各种驱动程序,了解设备的特性和操作方法。

中断处理层:负责处理 I/O 设备发出的中断信号,进行相应的处理。

硬件层:就是实实在在的物理设备,如硬盘、键盘、鼠标等。

I/O 调度

I/O 调度就像是交通警察指挥交通。它要根据 I/O 请求的特点和系统的状态,决定这些请求的执行顺序。比如,优先处理那些等待时间长或者对系统性能影响大的请求,以减少磁盘的寻道时间和旋转延迟,提高系统的整体 I/O 性能。

磁盘高速缓存

磁盘高速缓存是在内存中划出的一块区域,用于保存最近从磁盘读取的数据或者即将要写入磁盘的数据。它利用了程序的局部性原理,即程序在一段时间内往往会重复访问某些数据。当需要的数据在高速缓存中时,就可以直接从内存读取,而不必再去访问较慢的磁盘,从而加快数据访问速度。

缓冲区

单缓冲:只有一个缓冲区,比如从磁盘读取数据到缓冲区,然后再从缓冲区到用户进程,这两个操作不能同时进行。

双缓冲:有两个缓冲区,一个用于输入,一个用于输出,可以实现输入和输出的并行,提高效率。

循环缓冲:多个缓冲区组成一个环形结构,当一个缓冲区数据处理完后,可以循环使用其他缓冲区。

缓冲池:由多个可供多个进程共享的缓冲区组成,可以更灵活地分配和管理缓冲区资源。

缓冲区与高速缓存的对比

缓冲区主要是为了协调不同速度的设备之间的数据传输,减少设备之间的等待时间。而高速缓存则是为了加速对经常访问数据的访问速度,减少对较慢存储设备(如磁盘)的访问次数。

设备使用方式

独占式使用设备:比如打印机,同一时间只能被一个进程使用,如果多个进程同时请求,就需要排队等待。

分时式共享使用设备:像磁盘,多个进程可以在不同的时间片内交替使用,从而实现共享。

SPOOLing 技术(假脱机技术)

想象一下有很多人要打印文件,但只有一台打印机。SPOOLing 技术就创建了一个“虚拟打印机”,大家的打印任务先被存储在磁盘上的一个区域(输出井),然后由一个专门的后台进程按照先来后到的顺序依次将文件打印出来。这样,用户感觉自己的打印任务立即被接受了,实际上是在排队等待打印。

分配原则与分配方式

静态分配:在作业开始执行前就一次性分配好所需的设备,这种方式简单但不够灵活,如果设备在作业运行期间空闲,也不能分配给其他作业使用。

动态分配:在作业执行过程中,根据需要动态地分配设备。这种方式更灵活,能提高设备的利用率,但管理起来相对复杂。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值