5.5 真实世界

Xv6允许在内核中执行时以及在执行用户程序时触发设备和定时器中断。定时器中断迫使定时器中断处理程序进行线程切换(调用yield),即使在内核中执行时也是如此。如果内核线程有时花费大量时间计算而不返回用户空间,则在内核线程之间公平地对CPU进行时间分割的能力非常有用。然而,内核代码需要注意它可能被挂起(由于计时器中断),然后在不同的CPU上恢复,这是xv6中一些复杂性的来源。如果设备和计时器中断只在执行用户代码时发生,内核可以变得简单一些。

在一台典型的计算机上支持所有设备是一项艰巨的工作,因为有许多设备,这些设备有许多特性,设备和驱动程序之间的协议可能很复杂,而且缺乏文档。在许多操作系统中,驱动程序比核心内核占用更多的代码。

UART驱动程序读取UART控制寄存器,一次检索一字节的数据;因为软件驱动数据移动,这种模式被称为程序I/O(Programmed I/O)。程序I/O很简单,但速度太慢,无法在高数据速率下使用。需要高速移动大量数据的设备通常使用直接内存访问(DMA)。DMA设备硬件直接将传入数据写入内存,并从内存中读取传出数据。现代磁盘和网络设备使用DMA。DMA设备的驱动程序将在RAM中准备数据,然后使用对控制寄存器的单次写入来告诉设备处理准备好的数据。

当一个设备在不可预知的时间需要注意时,中断是有意义的,而且不是太频繁。但是中断有很高的CPU开销。因此,如网络和磁盘控制器的高速设备,使用一些技巧减少中断需求。一个技巧是对整批传入或传出的请求发出单个中断。另一个技巧是驱动程序完全禁用中断,并定期检查设备是否需要注意。这种技术被称为轮询(polling)。如果设备执行操作非常快,轮询是有意义的,但是如果设备大部分空闲,轮询会浪费CPU时间。一些驱动程序根据当前设备负载在轮询和中断之间动态切换。

UART驱动程序首先将传入的数据复制到内核中的缓冲区,然后复制到用户空间。这在低数据速率下是可行的,但是这种双重复制会显著降低快速生成或消耗数据的设备的性能。一些操作系统能够直接在用户空间缓冲区和设备硬件之间移动数据,通常带有DMA。

copyright by duguosheng all right reserved,powered by Gitbook该文件修订时间: 2021-08-19 13:50:18

results matching ""

    No results matching ""