在具有多个磁盘和跨越慢速 (HDD) 和快速 (SSD) 驱动器的软件 RAID 的现代 Linux 系统上,如何缓存对文件系统的写入?
对于 md-raid RAID1,阵列可以配置为 和--write-mostly
,--write-behind
这表明从较快的磁盘执行读取,而对较慢的磁盘的写入可能会滞后。但它是如何在内核级别缓存的呢?内核是否缓存 md-raid 层之前或之后的磁盘写入?在 write() 调用结束时,数据是否保证写入非磁盘之一--write-behind
?
对于btrfs
RAID1,同样的情况会如何发生?没有任何--write-behind
功能,那么脏页是在设备级别还是文件系统级别进行计数的? write() 在什么时候返回?
可调参数如何vm.dirty_*ratio
影响这些设置?
答案1
--write-mostly
,由驱动程序内部--write-behind
处理。保留元数据,例如写入意图位图(对于后写功能是必需的),它基本上记录哪些数据已写入以及哪些数据仍然丢失。当数据尚未到达主要写入设备时,如果发生断电事件,这是必要的。在这种情况下,受影响的数据区域将重新同步(在您的情况下从 SSD 读取,写入 HDD)。md
md
但它是如何在内核级别缓存的呢?
对于 write-behind 情况,md 驱动程序基本上在内部复制写入请求。主写入请求发送到主驱动器并告诉上层“好吧,我已经完成了”;然后,复制的写入请求将保留在 RAID 的后写侧,并且可能需要更长时间才能完成,希望没有人注意到。
然后,RAID 层采取许多步骤来确保在队列中仍有待处理的后写请求时,不会从以写为主的设备读取数据。为什么要从以写为主的设备读取数据?好吧,SSD 可能已经出现故障,所以就只剩下这个了。它很复杂,并且 write-behind 引入了一些极端情况。
这可能也是为什么它仅支持 RAID-1 级别,而不支持任何其他级别的原因。尽管理论上将 SSD 本质上作为 RAID-0 并在后写模式下使用两个奇偶校验 HDD 可能有意义,但不支持像这样的后写 RAID-6。它只是 RAID-1,即使在那里也很少使用。
其他缓存设置不受此影响,基本上整个缓存机制根本不关心md
驱动程序如何在内部实现事物。缓存做它的事,md 做它的事。因此,文件系统缓存对于 md 之上的文件系统与裸驱动器之上的文件系统的工作原理相同。 (实际情况比这复杂一点,但你可以这样想。)
答案2
对于 md-raid RAID1,阵列可以配置为 和
--write-mostly
,--write-behind
这表明从较快的磁盘执行读取,而对较慢的磁盘的写入可能会滞后。但它是如何在内核级别缓存的呢?内核是否缓存 md-raid 层之前或之后的磁盘写入?
之后,由于此功能是 md-raid 特有的。
您应该将此 md-raid 功能视为缓冲,而不是缓存。它受到以下mdadm
选项的限制:
--写在后面=
指定应启用后写模式(仅对 RAID1 有效)。如果指定了参数,它将设置允许的最大未完成写入数。默认值为 256。
我只能认为它也受到正常内核和硬件缓冲的限制(即,如果较小的话)。正常内核缓冲受和的限制nr_requests
。max_hw_sectors_kb
请参阅/sys/class/block/$write_behind_device/queue/
。硬件缓冲是指驱动器上的写入缓存。
在 write() 调用结束时,数据是否保证写入非磁盘之一
--write-behind
?
当然,假设您的意思是 write() 是在使用 O_SYNC / O_DSYNC 打开的文件上,或者您实际上是指 write()+fsync()。如果不是,则根本不存在任何保证。