文章目录
IO设备
1.系统架构
上图是一个典型系统架构:
- 外围总线,比如鼠标,磁盘等,负责最慢的
- 通用IO总线
- 内存总线,负责最快的,造价最高
2.标准设备
一个简化的设备接口层包括三个寄存器
- 状态寄存器
- 命令寄存器
- 数据寄存器
3.使用轮询的方式进行交互
- 操作系统反复读取状态寄存器(轮询),直到设备可以接受命令
- 操作系统将数据发送到数据寄存器
- 操作系统将命令写入命令寄存器
- 操作系统再次反复读取状态寄存器(轮询),然后判断是否执行完成
4.使用中断的方式进行交互
轮询过程会大量浪费CPU时间,所以我们使用中断,CPU的轮询将不再进行,而是向设备发出一个请求后就让对应的进程睡眠,CPU然后切换到其它进程,设备完成操作之后,就会抛出一个硬件中断,再唤醒对应的进程
如果IO请求速度很快,就不要使用中断,因为马上就可以返回,使用中断开销反而更大
5.利用DMA进行更高效的数据传送
如果我们要发送很大的数据到设备的数据寄存器,也会使CPU任务繁重,解决方案就是使用DMA,操作系统告诉DMA引擎数据在内存位置之后就去处理其它请求了,DMA完成会抛出一个中断告诉操作系统,如下图C就是DMA在处理
6.操作系统如何和设备进行通讯
- 方式1是使用操作系统独有的特权IO指令,比如in和out,操作系统需要指定存入数据的寄存器和一个代表设备的特定端口
- 方式2是使用内存映射IO,硬件将设备寄存器作为内存地址提供,操作系统读写对应的内存地址,然后硬件把他们转移到设备上,方式1和方式2目前都在用
7.设备驱动程序
我们需要让我们的操作系统更加通用,可以工作在各种设备上,与设备无关,我们可以使用设备驱动程序来封装交互细节
比如文件系统完全不知道磁盘类型,它只需要简单的向通用块层发送读写请求,块设备层将请求路由到对应设备驱动,再由设备驱动来完成真正的底层操作,驱动会真正的和设备寄存器进行交互
目前,驱动程序在整个内核代码比例越来越大
磁盘驱动器
1.磁盘的基本构成
上图所示
- 磁盘由大量的扇区组成,上面的每一个数字代表一个扇区(512字节)
- 每一个同心圆是一个磁道,一个表面会有非常非常多的磁道,数百个磁道只有头发宽
- 外侧同心圆扇区一般会多一些,而不是像上面画的那样
- 左下角那个杆子有个磁头可以读取数据,也可以变化磁道,同时,磁盘会旋转
- 扇区一般会倾斜,也就是上图11扇区和12扇区偏斜了2个扇区,这样的好处时,磁头变换后能够更快的读12
- 顺序读比随机读要快的多
- 磁盘也有缓存,它很小,只有几M或十几M,磁头可以缓存读取数据旁边扇区的数据,也就是句柄
- 如果放入内存就向操作系统回报写入完成,就叫做后写缓存,这样可能会出现问题,如果直到数据数据落盘才回报,叫直写
2.完整的IO过程
- 完整的磁盘读取包括三个过程,IO过程就是下面三个时间之和
- 寻道时间,最大寻道时间可能是平均寻道时间的2到3倍
- 等待转动,可以通过每分钟转动次数RPM来算,比如15000,就是250转每秒,4ms一圈,平均转动时间就是2ms
- 传输数据,这个占用时间很小
3.磁盘调度
磁盘调度的根本目标是最短任务有限(SJF shortest job first)
⑴最短寻道时间优先
就是先去离得最近的磁道取数据,这样有个问题,可能会有磁道的数据饿死
⑵电梯
就是先按一个方向扫描,扫描到一个需要读写的扇区后,判断此方向还有无需要读写的,没有就反向扫描,这样来来回回的扫描,这样避免了饿死的情况
⑶最短定位时间(最优方式)
电梯算法和最短寻道时间都忽视了磁盘的旋转
最短定位时间就是根据具体情况来,根据旋转和磁道的时间来推断到底使用最短寻道时间,还是电梯算法,假设寻道时间很长,那么电梯算法就不合适了
⑷其它
- 系统一般会等待一会,然后将多个请求一起给磁盘,磁盘通过最优方式来读写数据
- 如果请求取块33,8,34这3个扇区,那么调度程序会将33,34请求合并成一个
RAID
RAID又叫做廉价冗余磁盘阵列,由多块磁盘,内存和处理器组成,对外看像一块大硬盘
我们需要在3个维度来评价一个RAID架构
- 容量
- 可靠性
- 性能,包括随机/顺序读和随机/顺序写
1.RAID0
也就是没有冗余,在性能和容量上最佳,它在性能和容量上是其他RAID的上限,但它可靠性很差
2.RAID1
一个磁盘同时由一个副本
在容量方面,它存储容量只能有实际容量的一半
在可靠性方面,两个相同磁盘有一