dm-raid

设备映射器 RAID (dm-raid) 目标提供了从 DM 到 MD 的桥梁。它允许使用设备映射器接口访问 MD RAID 驱动程序。

映射表接口

目标名为“raid”,它接受以下参数:

<raid_type> <#raid_params> <raid_params> \
  <#raid_devs> <metadata_dev0> <dev0> [.. <metadata_devN> <devN>]

<raid_类型>

raid0

RAID0 条带化(无弹性)

raid1

RAID1 镜像

raid4

RAID4,带专用最后一个奇偶校验盘

raid5_n

RAID5,带专用最后一个奇偶校验盘,支持接管,与 raid4 相同

  • 临时布局

raid5_la

RAID5 左不对称

  • 旋转奇偶校验 0,数据连续

raid5_ra

RAID5 右不对称

  • 旋转奇偶校验 N,数据连续

raid5_ls

RAID5 左对称

  • 旋转奇偶校验 0,数据重新开始

raid5_rs

RAID5 右对称

  • 旋转奇偶校验 N,数据重新开始

raid6_zr

RAID6 零重新开始

  • 旋转奇偶校验零(从左到右),数据重新开始

raid6_nr

RAID6 N 重新开始

  • 旋转奇偶校验 N(从右到左),数据重新开始

raid6_nc

RAID6 N 连续

  • 旋转奇偶校验 N(从右到左),数据连续

raid6_n_6

RAID6,带专用奇偶校验盘

  • 奇偶校验和 Q-syndrome 在最后 2 个磁盘上;用于从/到 raid4/raid5_n 接管的布局

raid6_la_6

与 “raid_la” 相同,外加专用最后一个 Q-syndrome 盘

  • 用于从 raid5_la 接管到/从 raid6 的布局

raid6_ra_6

与 “raid5_ra” 相同,外加专用最后一个 Q-syndrome 盘

  • 用于从 raid5_ra 接管到/从 raid6 的布局

raid6_ls_6

与 “raid5_ls” 相同,外加专用最后一个 Q-syndrome 盘

  • 用于从 raid5_ls 接管到/从 raid6 的布局

raid6_rs_6

与 “raid5_rs” 相同,外加专用最后一个 Q-syndrome 盘

  • 用于从 raid5_rs 接管到/从 raid6 的布局

raid10

各种受 RAID10 启发的算法,通过附加参数选择(参见下面的 raid10_format 和 raid10_copies)

  • RAID10:条带化镜像(又名“镜像上的条带化”)

  • RAID1E:集成相邻条带镜像

  • RAID1E:集成偏移条带镜像

  • 和其他类似的 RAID10 变体

参考:https://www.snia.org/sites/default/files/SNIA_DDF_Technical_Position_v2.0.pdf 第 4 章

<#raid_参数>: 后面跟着的参数数量。

<raid_参数> 包括:

强制参数
<块大小>

以扇区为单位的块大小。此参数通常称为“条带大小”。它是唯一一个强制参数,并且放在首位。

后面是可选参数(顺序任意)
[同步|不同步]

强制或阻止 RAID 初始化。

[重建 <idx>]

重建驱动器号‘idx’(第一个驱动器为 0)。

[守护进程休眠 <毫秒>]

位图守护进程清除位的运行间隔。更长的间隔意味着更少的位图 I/O,但故障后重新同步可能需要更长时间。

[最小恢复速率 <KB/秒/盘>]

限制 RAID 初始化

[最大恢复速率 <KB/秒/盘>]

限制 RAID 初始化

[主要写入 <idx>]

将驱动器索引‘idx’标记为主要写入。

[最大预写 <扇区>]

参见 ‘--write-behind=’ (man mdadm)

[条带缓存 <扇区>]

条带缓存大小(仅限 RAID 4/5/6)

[区域大小 <扇区>]

区域大小乘以区域数量就是阵列的逻辑大小。位图记录了每个区域的设备同步状态。

[raid10_副本 <# 副本>], [raid10_格式 <近|远|偏移>]

这两个选项用于更改 RAID10 配置的默认布局。可以指定副本数量,但默认值为 2。副本的放置方式也有三种变体——默认是“近”。近距离副本是大多数人对镜像的理解。如果这些选项未指定,或者给定‘raid10_copies 2’和/或‘raid10_format near’,则 2、3 和 4 个设备的布局如下:

2 个驱动器

3 个驱动器

4 个驱动器

A1 A1

A1 A1 A2

A1 A1 A2 A2

A2 A2

A2 A3 A3

A3 A3 A4 A4

A3 A3

A4 A4 A5

A5 A5 A6 A6

A4 A4

A5 A6 A6

A7 A7 A8 A8

2 设备布局相当于双向 RAID1。4 设备布局是传统 RAID10 的样子。3 设备布局可以称为“RAID1E - 集成相邻条带镜像”。

如果是‘raid10_copies 2’和‘raid10_format far’,那么 2、3 和 4 个设备的布局如下:

2 个驱动器

3 个驱动器

4 个驱动器

A1 A2

A1 A2 A3

A1 A2 A3 A4

A3 A4

A4 A5 A6

A5 A6 A7 A8

A5 A6

A7 A8 A9

A9 A10 A11 A12

A2 A1

A3 A1 A2

A2 A1 A4 A3

A4 A3

A6 A4 A5

A6 A5 A8 A7

A6 A5

A9 A7 A8

A10 A9 A12 A11

如果是‘raid10_copies 2’和‘raid10_format offset’,那么 2、3 和 4 个设备的布局如下:

2 个驱动器

3 个驱动器

4 个驱动器

A1 A2

A1 A2 A3

A1 A2 A3 A4

A2 A1

A3 A1 A2

A2 A1 A4 A3

A3 A4

A4 A5 A6

A5 A6 A7 A8

A4 A3

A6 A4 A5

A6 A5 A8 A7

A5 A6

A7 A8 A9

A9 A10 A11 A12

A6 A5

A9 A7 A8

A10 A9 A12 A11

这里我们看到与“RAID1E - 集成偏移条带镜像”非常相似的布局。

[delta_磁盘 <N>]

delta_disks 选项值(-251 < N < +251)触发设备移除(负值)或设备添加(正值),适用于支持重塑的 RAID 级别 4/5/6 和 10。RAID 级别 4/5/6 允许添加设备(元数据和数据设备元组),raid10_near 和 raid10_offset 只允许添加设备。raid10_far 完全不支持任何重塑。必须保留最少数量的设备以强制执行弹性,即 raid4/5 为 3 个设备,raid6 为 4 个设备。

[数据偏移 <扇区>]

此选项值定义了每个数据设备中数据开始的偏移量。这用于提供异地重塑空间,以避免在更改条带布局时覆盖数据,因此可以在任何时候发生中断/崩溃而不会丢失数据。例如,在向前重塑期间向现有 RAID 集合添加设备时,异地空间将分配在每个 RAID 设备的开头。支持此类设备添加的内核 raid4/5/6/10 MD 个性化将从现有第一个条带(那些具有较少条带数的条带)从 data_offset 开始读取数据,以用较多的条带数填充新条带,计算冗余块(CRC/Q-syndrome),并将该新条带写入偏移量 0。所有 N-1 个其他新条带也将应用相同的方法。这种异地方案也用于更改 RAID 类型(即分配算法),例如从 raid5_ls 更改为 raid5_n。

[日志设备 <dev>]

此选项为 raid4/5/6 RAID 集合添加一个日志设备,并使用它来弥补因组件设备非原子更新而导致的“写入漏洞”,该漏洞可能在恢复期间导致数据丢失。日志设备以直写方式使用,因此与非日志的 raid4/5/6 集合相比,写入会被限制。使用 raid4/5/6 日志设备无法进行接管/重塑;在请求这些操作之前必须将其取消配置。

[日志模式 <模式>]

此选项将日志化的 raid4/5/6 RAID 集合(参见上面的‘journal_dev <dev>’)的缓存模式设置为‘直写’或‘回写’。如果选择‘回写’,日志设备必须具有弹性,并且本身不能出现‘写入漏洞’问题(例如使用 raid1 或 raid10),以避免单点故障。

<#raid_设备数量>: 组成阵列的设备数量。

每个设备由两个条目组成。第一个是包含元数据的设备(如果有);第二个是包含数据的设备。目标版本 1.8.0 最多支持 64 个元数据/数据设备条目。1.9.0 支持最多 253 个,这由所使用的 MD 内核运行时强制执行。

如果在创建时驱动器发生故障或缺失,可以在给定位置的元数据和数据驱动器都用‘-’表示。

示例表

# RAID4 - 4 data drives, 1 parity (no metadata devices)
# No metadata devices specified to hold superblock/bitmap info
# Chunk size of 1MiB
# (Lines separated for easy reading)

0 1960893648 raid \
        raid4 1 2048 \
        5 - 8:17 - 8:33 - 8:49 - 8:65 - 8:81

# RAID4 - 4 data drives, 1 parity (with metadata devices)
# Chunk size of 1MiB, force RAID initialization,
#       min recovery rate at 20 kiB/sec/disk

0 1960893648 raid \
        raid4 4 2048 sync min_recovery_rate 20 \
        5 8:17 8:18 8:33 8:34 8:49 8:50 8:65 8:66 8:81 8:82

状态输出

‘dmsetup table’显示用于构建映射的表。可选参数始终按上面列出的顺序打印,其中“sync”或“nosync”始终在其他参数之前输出,无论最初加载表时使用的顺序如何。可以重复的参数按值排序。

‘dmsetup status’提供有关阵列状态和健康状况的信息。输出如下(通常为单行,但在此处展开以清晰显示)

1: <s> <l> raid \
2:      <raid_type> <#devices> <health_chars> \
3:      <sync_ratio> <sync_action> <mismatch_cnt>

第 1 行是设备映射器生成的标准输出。

第 2 行和第 3 行由 RAID 目标生成,最好通过示例解释

0 1960893648 raid raid4 5 AAAAA 2/490221568 init 0

这里我们可以看到 RAID 类型是 raid4,有 5 个设备——所有设备都处于“活动”状态,并且阵列已完成 2/490221568 的初始恢复。以下是各个字段的更完整描述:

<raid_类型>

与用于创建阵列的 <raid_类型> 相同。

<健康字符>

每个设备一个字符,表示:

  • ‘A’ = 存活且同步

  • ‘a’ = 存活但未同步

  • ‘D’ = 死亡/失败。

<同步比率>

表示阵列已完成由‘sync_action’描述的过程的比例。如果‘sync_action’是“check”或“repair”,则“resync”或“recover”过程可以被认为是完整的。

<同步动作>

以下可能状态之一:

空闲
  • 未执行同步操作。

冻结
  • 当前操作已暂停。

重新同步
  • 阵列正在进行初始同步或在不干净关机后重新同步(可能借助位图)。

恢复
  • 阵列中的设备正在重建或替换。

检查
  • 正在执行用户发起的阵列完整检查。所有块都被读取并检查一致性。发现的差异数量记录在 <不匹配计数> 中。此操作不会对阵列进行任何更改。

修复
  • 与“check”相同,但会纠正差异。

重塑
  • 阵列正在进行重塑。

<不匹配计数>

在 RAID1/10 镜像副本之间发现的差异数量,或在 RAID4/5/6 中发现的错误奇偶校验值。此值仅在对阵列执行“check”操作后才有效。健康的阵列的‘mismatch_cnt’为 0。

<数据偏移>

当前数据偏移量,指向 RAID 集合每个组件设备上用户数据开始的位置(参见相应的 RAID 参数以支持异地重塑)。

<日志字符>

  • ‘A’ - 活动直写式日志设备。

  • ‘a’ - 活动回写式日志设备。

  • ‘D’ - 故障日志设备。

  • ‘-’ - 无日志设备。

消息接口

dm-raid 目标将通过“消息”接口接受某些操作。(有关消息接口的更多信息,请参阅‘man dmsetup’。)这些操作包括:

“空闲”

停止当前同步操作。

“冻结”

冻结当前同步操作。

“重新同步”

启动/继续重新同步。

“恢复”

启动/继续恢复过程。

“检查”

启动对阵列的检查(即“擦洗”)。

“修复”

启动阵列修复。

丢弃支持

硬件供应商对丢弃支持的实现各不相同。当一个块被丢弃时,一些存储设备在读取该块时会返回零。这些设备设置了‘discard_zeroes_data’属性。其他设备将返回随机数据。令人困惑的是,一些宣传‘discard_zeroes_data’的设备在读取丢弃的块时并不能可靠地返回零!由于 RAID 4/5/6 使用多个设备中的块来计算奇偶校验块,并且(出于性能原因)依赖于‘discard_zeroes_data’的可靠性,因此设备的一致性非常重要。块可能会在 RAID 4/5/6 条带的中间被丢弃,如果后续读取结果不一致,奇偶校验块可能随时被以不同方式计算;这使得奇偶校验块对于冗余而言毫无用处。如果您打算在 RAID 4/5/6 中启用丢弃,了解您的硬件如何处理丢弃非常重要。

鉴于存储设备在这方面的行为不可靠,即使报告了‘discard_zeroes_data’,默认情况下 RAID 4/5/6 的丢弃支持也是禁用的——这以牺牲部分性能为代价确保了数据完整性。

正确支持‘discard_zeroes_data’的存储设备正越来越多地被内核列入白名单,因此可以信任。

对于受信任的设备,可以设置以下 dm-raid 模块参数以安全地启用 RAID 4/5/6 的丢弃支持:

‘devices_handle_discards_safely’

版本历史

1.0.0  Initial version.  Support for RAID 4/5/6
1.1.0  Added support for RAID 1
1.2.0  Handle creation of arrays that contain failed devices.
1.3.0  Added support for RAID 10
1.3.1  Allow device replacement/rebuild for RAID 10
1.3.2  Fix/improve redundancy checking for RAID10
1.4.0  Non-functional change.  Removes arg from mapping function.
1.4.1  RAID10 fix redundancy validation checks (commit 55ebbb5).
1.4.2  Add RAID10 "far" and "offset" algorithm support.
1.5.0  Add message interface to allow manipulation of the sync_action.
       New status (STATUSTYPE_INFO) fields: sync_action and mismatch_cnt.
1.5.1  Add ability to restore transiently failed devices on resume.
1.5.2  'mismatch_cnt' is zero unless [last_]sync_action is "check".
1.6.0  Add discard support (and devices_handle_discard_safely module param).
1.7.0  Add support for MD RAID0 mappings.
1.8.0  Explicitly check for compatible flags in the superblock metadata
       and reject to start the raid set if any are set by a newer
       target version, thus avoiding data corruption on a raid set
       with a reshape in progress.
1.9.0  Add support for RAID level takeover/reshape/region size
       and set size reduction.
1.9.1  Fix activation of existing RAID 4/10 mapped devices
1.9.2  Don't emit '- -' on the status table line in case the constructor
       fails reading a superblock. Correctly emit 'maj:min1 maj:min2' and
       'D' on the status line.  If '- -' is passed into the constructor, emit
       '- -' on the table line and '-' as the status line health character.
1.10.0 Add support for raid4/5/6 journal device
1.10.1 Fix data corruption on reshape request
1.11.0 Fix table line argument order
       (wrong raid10_copies/raid10_format sequence)
1.11.1 Add raid4/5/6 journal write-back support via journal_mode option
1.12.1 Fix for MD deadlock between mddev_suspend() and md_write_start() available
1.13.0 Fix dev_health status at end of "recover" (was 'a', now 'A')
1.13.1 Fix deadlock caused by early md_stop_writes().  Also fix size an
       state races.
1.13.2 Fix raid redundancy validation and avoid keeping raid set frozen
1.14.0 Fix reshape race on small devices.  Fix stripe adding reshape
       deadlock/potential data corruption.  Update superblock when
       specific devices are requested via rebuild.  Fix RAID leg
       rebuild errors.
1.15.0 Fix size extensions not being synchronized in case of new MD bitmap
       pages allocated;  also fix those not occurring after previous reductions
1.15.1 Fix argument count and arguments for rebuild/write_mostly/journal_(dev|mode)
       on the status line.