《现代操作系统》-读书笔记-第一章-引论

《现代操作系统》-读书笔记-第一章-引论

软件中最基础的部分是操作系统,它运行在内核态(也称为管态、核心态)。在这个模式中,操作系统具有对所有硬件的完全访问权,可以执行机器能够运行的任何指令。软件的其余部分运行在用户态下。在用户态下,只使用了机器指令中的一个子集。特别是那些会影响机器的控制或可进行I/O的操作指令,在用户态中的程序是禁止的。

如图所示:

什么是操作系统

很难给出操作系统的准确定义。它运行在内核态中,有如下文中的两个基本任务,为应用程序员(实际上是应用程序)提供一个资源集的清晰抽象,并管理这些硬件资源。

作为扩展机器的操作系统

抽象是管理复杂性的一个关键。如操作系统中,文件API就是对硬盘的抽象。操作系统的一个主要任务是隐藏硬件,呈现给程序(以及程序员)良好、清晰、优雅、一致的抽象。

操作系统的实际客户是应用程序(通过程序员),它们直接与操作系统及其抽象打交道。

作为资源管理者的操作系统

资源管理包括用一下两种不同方式实现多路复用(共享)资源:

  • 在时间上复用:当一种资源在时间上复用时,不同的程序或用户轮流使用它。先是第一个获取资源,然后下一个,以此类推。例如,若在系统中只有一个CPU,而多个程序需要在该CPU上运行,操作系统则首先把该CPU分配个某个程序,在它运行了足够长的时间之后,另一个程序得到CPU,然后是下一个,如此进行下去。至于资源是如何实现时间复用的,则是操作系统的任务。

  • 在空间上复用:每个客户都得到资源的一部分,从而取代了客户排队。例如:通常在若干运行程序之间分割内存,这样每一个运行程序都可同时入驻内存(例如,为了轮流使用CPU)。有关空间复用的其他资源还有磁盘。在许多系统中,一个磁盘同时为许多用户保存文件。分配磁盘空间并记录谁正在使用哪个磁盘块。是操作系统的典型人物。

操作系统历史

第一代(1945~1955):真空管和穿孔卡片

第二代(1955~1965):晶体管和批处理系统

第三代(1965~1980):集成电路和多道程序设计

第四代(1980年至今):个人计算机机

第五代(1990年至今):移动计算机

计算机硬件简介

处理器

计算机的大脑是CPU,它从内存中取出指令并执行。在每个CPU基本周期中,首先从内存中取出指令,解码以确定其类型和操作熟,接着执行之,然后取指、解码并执行下一条指令。

每个CPU都有一套可执行的专门指令集。所以,x86处理器不能执行ARM程序,而ARM处理器也不能执行x86程序。由于用来访问内存以得到指令或数据的时间,要比执行指令的时间耗时更长,因此,所有CPU内都有一些用来保存关键变量和临时数据的寄存器。这样,通常在指令集中提供一些指令,用以将一个字从内存调入寄存器,或者用两者产生一个结果,如将两个字相加并把结果放入寄存器或内存中。

几个重要的寄存器:

程序计数器,它是对程序员可见的专用寄存器,它保存了将要取出的下一条指令的内存地址。在指令取出之后,程序计数器就被更新以便指向后继的指令。

堆栈指针,它指向内存中当前栈的顶端。该栈包含了每个执行过程的栈帧。一个过程的栈帧中保存了有关的输入参数、局部变量以及那些没有保存在寄存器中的临时变量。

程序状态字(Program Status Word,PSW),这个寄存器中包含了条件码位(由笔记指令设置)、CPU优先级、模式(用户态或内核态),以及各种其他控制位。用户程序通常读入整个PSW,但是,只对其中的少量字段写入。在系统调用和I/O中,PSW的作用很重要。

一个CPU在它执行指令n时,还可以对指令n+1解码,并且读取指令n+2,这样的机制称为流水线(pipeline)。如下图所示:

在多数流水线设计中,一但一条指令被取进流水线中,它就必须执行完毕,即便前一条取出的指令是条件转移,它也必须执行完毕。这使得编译器和操作系统的编写者很头疼,因为造成了机器中首先这些软件的复杂问题,而机器必须处理这些问题。

超标量CPU:在这种设计中,有多个执行单元,例如,一个CPU用于整数运算符,一个CPU用于浮点算术运算符,一个CPU用于布尔运算。两个或更多的指令被同时取出、解码并装入暂存缓冲区中,直至它们执行完毕。这种设计存在一种隐患,即程序的指令经常不按顺序执行。通常硬件负责运算的结果和顺序,但仍有部分复杂的情况强加给操作系统处理。

存储器

在任何一种计算机汇总,第二种主要的部件都是存储器。在理想情形下,存储器应该极为迅速(快于执行一条指令,这样CPU不会受到存储器的限制),容量充分大,并且价格非常便宜。但是目前的技术无法同时满足这三个目标,于是出现了不同的处理方式。存储器系统采用了一种分层次的结构。

如上图所示,顶层的存储器速度较高,容量较小,与底层的存储器相比每位成本较高,其差别往往是十亿数量级。

寄存器:它们用与CPU相同的材料制成,所以和CPU一样快。访问没有延时,典型存储容量,在32位CPU中为32*32位,而在64位CPU中为64*64位。在这两种情形下,其存储容量都小于1KB。程序必须在软件中自行管理这些寄存器(即决定如何使用它们)。

高速缓存:其作用是为了更好的利用局部性原理,减少CPU访问主存的次数。简单地说,CPU正在访问的指令和数据,其可能会被以后多次访问到,或者是该指令和数据附近的内存区域,也可能会被多次访问。因此,第一次访问这一块区域时,将其复制到cache中,以后访问该区域的指令或者数据时,就不用再从主存中取出。现代CPU中设计了两个缓存:L1缓存L2缓存,两者的差别在于时序,对于L1缓存的访问,不存在任何延时;而对于L2缓存的访问,则会延时1或2个时钟周期。

主存:也称为随机访问存储器(Random Access Memory,RAM),所有不能在高速缓存中得到满足的访问请求都会转往主存。

磁盘

磁盘唯一的问题是随机访问数据时大约慢了三个数量级。其低速的原因是因为磁盘是一种机械装置。

I/O设备

I/O设备也与操作系统有密切的相互影响。I/O设备一般包括两个部分:设备控制器和设备本身。

控制器:它是插在电路板上的一块芯片或一组芯片,这块电路板物理的控制设备。它从操作系统接收命令。例如,从设备读取数据,并且完成数据的处理。每类设备控制器都是不同的,所以,需要不同的软件进行控制。专门与控制器对话,发出命令并接受响应的软件,称为设备驱动程序(device driver)

实现输入和输出的方式有三种:

  • 忙等待(busy waiting),其缺点是要占据CPU,CPU一直轮训设备直到对应的I/O操作完成
  • 中断
  • 直接存储器访问(Direct memory Access,DMA)

总线

如上图所示,系统中有很多总线,每条总线的传输速度和功能都不同。

启动计算机

在计算机启动时,基本输入输出系统(Basic Input Output System,BIOS)的程序开始启动。开始检查各种设备。

然后,BIOS通过尝试存储在CMOS存储器中的设备清单决定启动设备。启动设备上的第一个扇区被读入内存并执行。这个扇区中包含一个对保存在启动扇区末尾的分区表检查程序,以确定哪个分区是活动的。然后,从该分区读入第二个启动装载模块。来自活动分区的这个装载模块被读入操作系统,并启动之。

操作系统大观园

操作系统已经存在了半个多世纪,在这段时间,出现了各种操作系统。如:

  • 大型机操作系统
  • 服务器操作系统

  • 多处理器操作系统

  • 个人计算机操作系统

  • 掌上计算机操作系统

  • 嵌入式操作系统

  • 传感器节点操作系统

  • 实时操作系统

  • 智能卡操作系统

操作系统概念

进程

进程(Process),的本质是正在执行的一个程序。与每个进程相关的是地址空间(address space),这是从某个最小的存储位置(通常是零)到某个最大值到存储位置的列表。在这个地址空间中,进程可以进行读写。该地址空间存放有可执行程序、程序的数据以及程序的堆栈。与每个进行相关的还有资源集,通常包括寄存器(含有程序计数器和堆栈指针)、打开文件的清单、突出的报警、有关进程清单,以及运行该程序所需要的所有其他信息。进程基本上是容纳运行一个程序所需要所有信息的容器。

地址空间

在较复杂的操作系统允许在内存中同时运行多道程序。为了避免它们互相干扰(包括操作系统),需要要有某种保护机制。通常,每个进程有一些可以使用的地址集合,典型值从0开始直到某个最大值。

在本质上,操作系统创建一个了一个地址空间的抽象,作为进程可以引用地址的集合。该地址空间与机器的物理内存解耦,可能大于也可能小于该物理空间。

文件

支持操作系统的另一个关键概念是文件系统。在文件可以读取之前,必须先在磁盘上定位和打开文件,在文件读取之后应该关闭文件,有关的系统调用则用于完成这类操作。

每个进程有一个工作目录(working directory)

在读写文件之前,首先要打开文件,检查其访问取消。若权限许可,系统将返回一个小整数,称为文件描述符(file descriptor),供后续操作使用。若禁止访问,系统则返回一个错误码。

特殊文件(special file),提供了特殊文件是为了使I/O设备看起来像文件一般。有两类特殊文件:块特殊文件(block special file)和字符特殊文件(character special file)。块特殊文件是指那些由可随机存取的块组成的设备,如磁盘等。字符特殊文件用于打印机、调制解调器和其他接收或输出字符流设备。

管道(pipe),是一个特性既与进程有关揶揄文件有关。它是一种虚文件,可以连接两个进程。

输入/输出

所有的计算机都有用来获取输入和产生输出的物理设备。每个操作系统都有管理其I/O设备的I/O子系统。

保护

管理系统的安全性完全依靠操作系统,例如,文件仅供授权用户访问等。

shell

UNIX命令解释器,称为shell

系统调用

操作系统分为用户态和内核态,通常在PSW中有一个二进制位控制这两种模式。在内核态中,CPU可以执行指令集中的每一条指令,并且使用硬件的每种功能。而在用户态下,仅允许执行整个指令集的一个子集和访问所有功能的一个子集。

为了操作系统中获得服务,用户程序必须使用系统调用(System call)以陷入内核并调用操作系统。TRAP指令把用户态转换为内核态,并启用操作系统。当有关工作完成之后,在系统调用后面的指令把控制权返回给用户程序。

任何单CPU计算机一次只能执行一条指令。

由C程序进行的调用形式如下:

count = read(fd, bufer, nb )

如果系统调用不能执行,不论是因为无效参数,还是磁盘错误,count都会被置为01,而在全局变量errno中放入错误号。正常执行如下图:

用于进程管理的系统调用

在UNIX中fork(派生)是唯一可以在POSIX中创建进程的途径。它创建一个原有进程的精确副本,包括所有的文件描述符、寄存器内容等。在fork之后,原有的进程及其副本(父与子)就分开了。fork调用返回一个值,在子进程中该值为0,并且在父进程中等于子进程的进程标示符(Process IDentifier,PID)。

在UNIX中,进程将其存储空间划分为三段:正文段(如程序代码)、数据段(如变量)、以及堆栈段。数据向上增长。堆栈在需要时自动向中间增长。

用于文件管理的系统调用

要读写一个文件,先要使用open打开该文件。

用户目录管理的系统调用

各种系统调用

Windows Win32 API

操作系统结构

操作系统有以下结构:

  • 单体系统
  • 层次式系统

  • 微内核

  • 客户端 – 服务器模式

  • 虚拟机

  • 外核

依靠C的世界

操作系统很多部分有C(有时是C++)组成的程序。

C语言:一项C语言中有而Java和Python中没有的特点是显式指针(explicit pointer)。指针是一种指向(即包含对象的地址)一个变量或数据结构中的变量。

头文件:包含供一个或多个代码文件使用的声明以及定义。头文件还可以包括简单的宏。

大型编程项目:通过make来进行构建

运行模式:操作系统代码都是直接在硬件上执行的,不用解释器,也不是即时编译。

有关操作系统的研究

ACM:http://www.acm.org

IEEE计算机协会:http://www.computer.org

USENIX:http://ww.usenix.org

小结

考察操作系统有两种观点:资源管理观点和扩展机器的观点。在资源管理的观点中,操作系统的任务上有效的管理系统的各个部分。在扩展的机器观点中,系统的任务是为了用户提供比实际机器更便于运行的抽象。

所有操作系统构建所依赖的基本概念是进程、存储管理、I/O管理、文件管理和安全。

任何操作系统 核心是它可处理的系统调用集。这些系统调用真实的说明了操作系统所做的工作。

说点什么

This site uses Akismet to reduce spam. Learn how your comment data is processed.

  Subscribe  
提醒