操作系统(一):概念导读

整理《Operating System Concepts》 第七版前两章的理论和概念,内容均为原书和中文版翻译的摘录,其中原书摘录部分由我 按个人理解简化、翻译为中文,可能存在一些不准确之处

绪论(第一章)

定义操作系统

  • 操作系统(operating system) 是管理计算机硬件的一个程序,它同时作为用户和硬件的中间层,为应用程序提供了基础。
  • 一个计算机系统可被大致划分为四个部件: 硬件(hardware)操作系统应用程序(application programs)用户(users)
  • 硬件(hardware) 包括: 中央处理器(central processing unit)存储器(memory)输入输出(I/O)设备 。操作系统控制并协调多个用户的多道程序。
  • 从计算机的视角看,操作系统类似一个 资源管理器(resource allocator) ,它扮演了硬件资源管理者的角色。另一个略微有所不同的角度是,操作系统是一个控制程序,这个 控制程序(control program) 管理用户程序的执行以防止错误的发生和对计算机不合法的使用。
  • 计算机系统最基本的目的是执行用户程序,并让用户问题的解决变得更容易。

操作系统组织

  • 计算机用于启动的初始化程序被称作 引导程序(bootstrap program) ,它被存储在只读存储器(ROM)或电擦除只读存储器(EEPROM),也就是常说的固件。
  • 一个事件的发生通常通过硬件或软件的 中断(interrupt) 来触发。硬件可能在任何时候通过向 CPU 发送一个信号来 触发(trigger) 中断,该信号通常经由总线传递。软件可能通过执行被称作 系统调用(system call) 的特殊指令来触发中断。
  • 计算机程序必须在主存(也被称作 随机访问存储器(random-access memory) )中执行。主存是 CPU 能直接访问的唯一的大容量存储,它通常由被称作 动态随机访问存储器(dynamic random-access memory,DRAM) 的半导体器件实现。主存是 易失(volatile) 存储,当电源关闭或其它问题出现时,其内容会丢失。因此多数计算机系统提供了 二级存储(secondary storage) 作为主存的扩展,二级存储设备通常是 磁盘(magnetic disk)
  • 操作系统对每一个设备控制器均设置有一个 设备驱动(device driver) ,要启动一个 I/O 操作需经过如下步骤:
    • 设备驱动设置设备控制器内部对应的寄存器
    • 设备控制器检查其内部寄存器并确定要执行的行为
    • 设备控制器启动数据传输,数据 从设备发送给本地缓存
    • 一旦数据传输结束,设备控制器通过触发一个中断通知设备驱动
    • 设备驱动将控制权交还给操作系统;如果 I/O 操作是读行为,则携带读取的数据或者指向数据的指针;如果 I/O 操作是其他行为,则返回状态信息。
  • 大量数据移动通常使用 直接存储器访问(direct memory access,DMA) 。在为 I/O 设备设置缓冲区、指针、计数器后,设备控制器将整块数据直接从它的缓冲区发送到主存(或相反方向)而不经过 CPU。传输一块数据只会触发一次 CPU 中断。

计算机系统体系与结构

  • 多处理器系统(multiprocessor system) ,也被称作 并行系统(parallel system)轻耦合系统(lightly coupled system) 有以下三个主要优点:
    • 增加吞吐量(throughput)
    • 性价比高 :相比多个单处理器系统,因为多处理器系统可以共享 外围设备(peripherals)大容量存储器(mass storage) 和电源,因此花费更少。
    • 增加可靠性(reliability) :单处理器出现故障只会减缓系统而不会导致系统终止。根据存活硬件均衡提供服务的能力被称作 故障弱化(graceful degradation) 。有些系统具有 容错能力(fault tolerant) ,当任何一个单件出错时,系统能够继续运行。
  • 多处理器系统主要有两种类型:
    • 非对称多处理器(asymmetric multiprocessing) :每个处理器被赋予一定特殊作业,一个主处理器用于控制系统,其它的处理器要么从主处理器获取信息,要么执行预定义的作业。
    • 对称多处理器(symmetric multiprocessing,SMP) :每个处理器均可执行操作系统中的所有作业,处理器之间不存在主从关系。
  • 多道程序(multiprogramming) 通过组织作业(代码或数据)增加了 CPU 的利用率(utilization),CPU 无论何时均有一个作业在执行。
  • 分时(time sharing) ,或者 多工(multitasking) 是多道程序在逻辑上的扩展,CPU 在多个程序间跳转执行,因为跳转速度很快,对于用户而言就可以与各个同时运行的程序交互。 分时需要 交互式(interactive) 的计算机系统,用户和系统之间应该可以直接交流,且 响应时间(response time) 应当足够短。
  • 一个被装入主存并执行的程序被称作 进程(process) 。分时和多道程序需要主存中同时保持多个作业,因为主存通常不足以同时容纳这些作业,所以它们在执行前被存放在硬盘的 作业池(job pool) 中,它容纳了所有等待分配主存的进程。
  • 如果多个作业因为主存空间不足而无法同时装载,那么系统要在作业间进行 作业调度(job scheduling)
  • 在分时系统中,操作系统必须保证响应时间,这一点有时通过进程在主存和硬盘之间的 交换(swapping) 完成。一个更普遍的方式是 虚拟内存(virtual memory) ,它使用户可以运行远大于 物理内存(physical memory) 的程序。

操作系统运行

  • 现代操作系统均为 中断驱动(interrupt driven) ,事件几乎都通过中断或陷阱来触发。
  • 一个 陷阱(trap) 或者说 异常(exception) ,是软件产生的中断。触发的原因要么是错误的产生(例如除 0 操作或违例内存访问),要么是用户程序执行了对操作系统服务的特殊请求。
  • 为了保证操作系统程序正确执行,我们需要区分系统程序段和用户程序段。因此设置了两个独立的操作 模式(modes)用户模式(user mode)内核/管理/系统/特权模式(kernel/supervisor/system/privileged mode) 。计算机硬件中需要加入一个 模式位(mode bit) 用于说明当前的模式为内核(0)还是用户(1)。
  • 在系统启动时,硬件系统处于内核模式。之后操作系统被加载并且在用户模式中执行用户应用。当一个陷阱或者中断发生,硬件将从用户模式切换到内核模式。
  • 我们将一些机器指令指定为可能产生有害作用的 特权指令(privileged instructions) ,硬件只允许特权指令在内核模式中运行。一旦系统调用被执行,它将被硬件视为一个软中断,中断向量将被传递给系统内部的一个服务程序,并且模式位切换至内核模式。
  • 定时器(timer) 可使计算机在一定时间后被中断。在将控制权交还给用户之前,操作系统必须保证定时器已被设置,一旦定时器触发中断,控制权将自动交还给操作系统,操作系统会将该中断视作一个致命的错误(fatal error)或者给这个程序更多的执行时间。

进程管理

  • 程序是被动的实体,而进程是主动(active)的实体。
  • 一个进程要完成任务需要如下资源:CPU,存储器,文件和 I/O 设备。一个单线程的进程有一个 程序计数器(program counter) 指定下一条要执行的指令,多线程的进程有多个程序计数器。
  • 进程是系统中的工作单元。通过在单 CPU 的复用,所有的进程都有机会并行执行。
  • 操作系统需要对进程管理及以下相关行为负责:
    • 创建或删除用户或系统进程
    • 挂起或继续进程
    • 为进程同步提供机制
    • 为进程通信提供机制
    • 为死锁的处理提供机制

操作系统结构(第二章)

操作系统服务

操作系统应提供如下服务。

  • 用户接口(user interface) ,包括:
    • 命令行接口(command-line interface,CLI)
    • 批处理接口(batch interface)
    • 图形化用户接口(graphical user interface,GUI)
  • 程序执行(program execution) :操作系统要能够将程序加载到主存并执行程序
  • 输入/输出操作(I/O operations) :运行中的程序可能需要涉及到文件或 I/O 设备的读写操作
  • 文件系统控制(file-system manipulation)
  • 通信(communications) :通信可能通过 共享内存(shared memory)消息传递(message passing) 实现
  • 错误检测(error detection) :操作系统应当能始终检测到可能的错误
  • 资源分配(resource allocation) :一些资源需要特殊的分配行为(如 CPU、主存和文件存储),有的还需要请求和释放代码(如 I/O 设备)
  • 统计(accounting) :操作系统需要对每个用户使用了多少不同的计算机资源做统计
  • 安全防护(protection and security) :保证所有对系统资源的请求都得以控制

用户接口和系统调用

  • 有的操作系统将命令解释器(command interpreter)作为系统内核的一部分,有的(如 Windows XP 和 UNIX)将命令解释器作为一个特殊的程序。在存在多个可选命令解释器的系统中,它们通常被称作 壳(shell) 。命令解释器的主要功能是获取并执行下一条用户指定的指令,有两种执行的方式:
    • 命令解释器本身包含了执行命令的代码:可执行命令的数量决定了命令解释器的大小
    • 通过系统程序实现多数指令:命令解释器本身并不理解指令的含义,它仅仅通过命令指定一个文件,将其装载至主存并执行。例如 rm file.txt 将程序 rm 加载并传入参数 file.txt 执行
  • 图形用户接口提供了一个桌面。
  • 系统调用(system call) 为系统服务提供了一个接口。多数程序开发者并不接触这一细节等级的代码,他们通常使用 应用程序接口(application programming interface,API) 来编写程序。API 为应用程序开发者提供了一组函数,最常见的三组 API 如:Windows 系统的 Win32 API、基于 POSIX 系统的 POSIX API 和 Java API。使用 API 的背后实际涉及了系统调用。
  • 系统调用和中断的异同点
    • 二者均有索引(系统调用编号-系统调用表、中断向量表),二者的执行均需切换到内核模式
    • 二者触发条件不同:系统调用是主动请求(会被硬件视为软中断),中断是外部触发
  • 中断和陷阱的不同点
    • 二者起点不同:陷阱是正在执行的程序主动发起的,中断是外部错误或动作产生
    • 二者处理方式不同:程序的陷阱(异常)在响应后将停止执行,而程序在中断时保存断点,中断处理结束后从断点恢复执行
  • 多数程序设计语言的运行时支持系统(一系列包含在编译器链接库中的函数)提供了 系统调用接口(system-call interface) ,它们将程序代码和操作系统提供的系统调用链接起来。每个系统调用都有一个对应的编号,系统调用接口维护了一个编号-系统调用的索引,它们截取应用程序调用的 API,调用操作系统内核中相关的系统调用,并返回系统调用状态及其他返回值。
  • 向操作系统传递参数有三种方法:通过寄存器传递、内存的块/表、压入/弹出堆栈。
  • 系统调用可被大致分为五类: 进程控制(process control)文件管理(file manipulation)设备管理(device manipulation)信息维护(information maintenance)通信(communications)
  • 一个单任务系统: MS-DOS,它在计算机启动时运行一个命令解释器,当运行程序时,它将程序装入内存,并修改命令解释器的大部分内容来为新程序提供尽可能多的空间。之后将指令指针设为程序的第一条指令并运行程序,要么产生错误引起中断(此错误代码会被保存),要么程序执行一个系统调用以终止。最终命令解释器剩余部分程序继续执行,并从磁盘重新装入命令解释器的其他部分。这些步骤完成后,命令解释器会向用户/下一程序提供上一次运行的结果(保存的错误代码)。
  • 多任务系统:FreeBSD,用户登录到系统时,从用户选择的 Shell 开始执行。为了启动新进程,Shell 执行 fork() 系统调用,所选择的程序通过 exec() 装入内存并执行。根据命令发布方式,Shell 要么等待进程结束,要么在后台执行进程并继续响应用户输入。
  • 两种通信模型:
    • 消息传递模型(message-passing model) :通信进程通过彼此之间交换消息传递信息,直接/间接通过一个共同的邮箱。通信实体可能是同一主机的不同进程,也可能是通过网络相连的另一主机的进程。进程之间通过 主机名(host name)进程名(process name) 作为标识符区分。
    • 共享内存模型(shared-memory model) :进程使用 shared memory createshared memory attach 系统调用来获得其它进程所拥有内存区域的访问权。操作系统通常需要组织一个进程访问另一个进程的内存,要使用共享内存模型,需要两/多个进程都同意取消这一限制。数据的形式和位置由进程协商决定,不受操作系统控制,进程必须保证它们不会同时向同一地方写入。
    • 区别:消息传递对交换少量数据更有效,对于计算机之间的通信也比共享内存更容易实现;共享内存允许最大速度通信(本地可以内存速度),并且比较方便,但需要保护和同步。

操作系统设计和实现

  • 系统程序(system program) 为开发程序和执行程序提供了一个方便的环境,它们可分为:
    • 文件管理(file management)
    • 状态信息(status information)
    • 文件修改(file modification)
    • 程序语言支持(programming-language support)
    • 程序装入和执行(program loading and execution)
    • 通信(communications)
  • 操作系统设计目标:分为 用户 目标 和 系统 目标
    • 用户目标:系统应当方便、容易使用、容易学习、可靠、安全、快速
    • 系统目标:操作系统应该容易设计、实现和维护,应该灵活、可靠、高效而没有错误
  • 策略(policy)机制(mechanism) 的区分:机制决定如何做( how to do),而策略决定做什么( what will be done)

操作系统结构

  • 简单结构:利用最小的空间提供最多的功能,没有被划分为模块,如 MS-DOS 和最初的 UNIX。应用程序能够访问最底层的、基本的设备驱动,因此易受恶意程序的伤害。
  • 分层方法(Layered Approach) :采用自顶向下方法,将总的功能和特征划分为模块。模块化的其中方法是分层方法:将操作系统分为若干层(级),最底层(层0)为硬件,最高层(层N)为用户接口,分层结构类似一个同心圆。分层法最大的 优点在于构造和调试的简单化 (每层只能利用较低层的功能和服务、每层为高层隐藏了一定数据结构、操作和硬件存在),主要困难在于 对层的详细定义相比其他方法的低效
  • 微内核(microkernels) :将操作系统中所有非基本部分从内核中移走,将它们实现为系统程序或用户程序,从而得到更小的内核。微内核通常包括最小的进程、内存管理和通信功能。Windows NT 系统采用了分层微内核,有些 UNIX 系统也采用了此种方式。
    • 微内核的主要功能是使客户程序和运行在用户空间的各种服务之间通信,客户程序和服务之间不会直接交互,而是通过微内核的 消息传递
    • 因为新服务可在用户空间增加而不需修改内核,因此 便于扩充操作系统 ;因为大多数服务作为用户而不是内核进程运行,因此提供了 更好的安全性和可靠性
    • 因为使用消息传递,系统功能总开销增加,因此 系统性能下降
  • 模块(modules) :用面向对象技术生成模块化的内核,动态加载模块。内核可以提供核心服务,也可动态实现特定功能。该方法和微内核方法类似,核心模块只有核心功能以及其他模块加载、通信的相关信息,但模块方法中, 模块之间不需要调用消息传递来通信
  • 示例:Mac OS X操作系统的结构,底层为 Mach 微内核,提供内存管理、远程程序调用(remote process call,RPC)和进程间通信(IPC)工具;BSD 提供 BSD 命令行接口,支持网络、文件系统、POSIX API 实现。

虚拟机和系统生成

  • 虚拟机的基本思想是单个计算机(CPU、内存、硬盘、网卡等)硬件抽象为几个不同的执行部件。
  • 虚拟机除了提供与基本硬件相同的接口外,不提供额外功能。每个进程都有一个与底层机器完全相同的(虚拟)副本。
  • 虚拟机为每个虚拟系统提供 小型磁盘(minidisk) ,系统在物理磁盘上为小型磁盘分配所需要的磁道来实现。所有小型磁盘的大小之和必须小于可用的物理磁盘。
  • 底层物理机器有两种模式:用户模式和内核模式,虚拟机软件本身在物理机器上运行在用户模式中,而虚拟机在虚拟系统中运行在内核模式,每个虚拟系统有虚拟用户模式和虚拟内核模式,这两种模式均运行在物理用户模式。
  • 虚拟的 I/O 操作可能需要更少(脱机操作)或更多(解释执行)的时间。
  • 优点:可用于研究、开发操作系统;不同系统资源具有完全的保护,各个虚拟机之间完全独立。
  • 操作系统通常设计成能运行在一类计算机上,对于某类特定的计算机场所,配置生成系统的过程称为 系统生成(system generation,SYSGEN) 。需要考虑的信息有:使用什么CPU、多少可用内存、哪些可用设备、需要什么操作系统选项和参数值。这些信息确定后,系统管理员可用这些信息修改操作系统的源代码副本以完全重新编译操作系统;或者创建一个表,从预先编译过的库中选取模块,将这些模块连接起来生成操作系统;或者构造一个完全由表驱动的系统,所有代码都是系统的组成部分, 选择发生在执行时而不是编译时 ,现代多数操作系统均为此种方式。

系统引导

  • 装入内核以启动计算机的过程称为 引导(booting) 系统,多数计算机中均有一小块代码,称为 引导程序(bootstrap program)引导装载程序(bootstrap loader) ,这段代码将定位内核,将其装入内存并开始执行。引导程序被存放在只读存储器中。
  • 对于大型操作系统(多数通用操作系统),引导程序存储在固件中,操作系统保存在磁盘上。引导程序运行后会从磁盘固定位置(0区块)读取整个引导块到内存,并执行这个 引导块(boot block) 中的代码。这个引导块足够复杂,它将一个完整的操作系统装载到内存开始执行。

专栏目录:计算机理论基础
此专栏的上一篇文章:计组与体系结构笔记(六):输入/输出与存储系统
此专栏的下一篇文章:操作系统(二):进程与线程

参考资料:《操作系统概念 英文第七版》,恐龙书,英文名《Operating System Concepts》,作者 Abraham Silberschatz、Peter Baer Galvin、Greg Gagne

原创作品,允许转载,转载时无需告知,但请务必以超链接形式标明文章原始出处(http://blog.forec.cn/2016/11/22/os-concepts-1/) 、作者信息(Forec)和本声明。

分享到