# 2.1 抽象系统资源

当谈及操作系统时，人们可能会问的第一个问题是为什么需要它？也就是说，我们可以将图1.2中的系统调用实现为一个库，应用程序可以与之链接。在此方案中，每个应用程序甚至可以根据自己的需求定制自己的库。应用程序可以直接与硬件资源交互，并以应用程序的最佳方式使用这些资源（例如，实现高性能或可预测的性能）。一些嵌入式设备或实时系统的操作系统就是这样组织的。

这种库函数方法的缺点是，如果有多个应用程序在运行，这些应用程序必须表现良好。例如，每个应用程序必须定期放弃中央处理器，以便其他应用程序能够运行。如果所有应用程序都相互信任并且没有错误，这种协同操作的分时方案可能是可以的。 然而更典型的情况是， 应用程序互不信任且存在bug，所以人们通常希望提供比合作方案更强的隔离。 

为了实现强隔离， 最好禁止应用程序直接访问敏感的硬件资源，而是将资源抽象为服务。 例如，Unix应用程序只通过文件系统的`open`、`read`、`write`和`close`系统调用与存储交互，而不是直接读写磁盘。这为应用程序提供了方便实用的路径名，并允许操作系统（作为接口的实现者）管理磁盘。即使隔离不是一个问题，有意交互（或者只是希望互不干扰）的程序可能会发现文件系统比直接使用磁盘更方便。

同样，Unix在进程之间透明地切换硬件处理器，根据需要保存和恢复寄存器状态，这样应用程序就不必意识到分时共享的存在。这种透明性允许操作系统共享处理器，即使有些应用程序处于无限循环中。

另一个例子是，Unix进程使用`exec`来构建它们的内存映像，而不是直接与物理内存交互。这允许操作系统决定将一个进程放在内存中的哪里；如果内存很紧张，操作系统甚至可以将一个进程的一些数据存储在磁盘上。`exec`还为用户提供了存储可执行程序映像的文件系统的便利。

Unix进程之间的许多交互形式都是通过文件描述符实现的。文件描述符不仅抽象了许多细节（例如，管道或文件中的数据存储在哪里），而且还以简化交互的方式进行了定义。例如，如果流水线中的一个应用程序失败了，内核会为流水线中的下一个进程生成文件结束信号（EOF）。

图1.2中的系统调用接口是精心设计的，既为程序员提供了便利，又提供了强隔离的可能性。Unix接口不是抽象资源的唯一方法，但它已经被证明是一个非常好的方法