Btrfs
来自 Btrfs 文档
- Btrfs 是 Linux 上一种现代的写时复制 (COW) 文件系统,旨在实现高级功能,同时注重容错、修复和易于管理。
准备工作
对于用户空间实用程序,请安装包含基本操作所需的 btrfs-progs 包。
如果您需要从 Btrfs 文件系统启动(即,您的内核和 initramfs 位于 Btrfs 分区上),请检查您的 引导加载程序是否支持 Btrfs。
文件系统创建
以下介绍了如何创建一个新的 Btrfs 文件系统。要将 Ext3/4 分区转换为 Btrfs,请参阅 #Ext3/4 转换为 Btrfs。要使用无分区设置,请参阅 #无分区 Btrfs 磁盘。
有关更多信息,请参阅 mkfs.btrfs(8)。
单个设备上的文件系统
要在分区 /dev/partition 上创建 Btrfs 文件系统
# mkfs.btrfs -L mylabel /dev/partition
Btrfs 元数据的默认节点大小为 16 KiB,而数据的默认扇区大小等于页面大小并自动检测。要为元数据使用更大的节点大小(必须是扇区大小的倍数,最多允许 64 KiB),请通过 -n 开关指定 nodesize 的值,如下所示的示例使用 32 KiB 块
# mkfs.btrfs -L mylabel -n 32k /dev/partition
多设备文件系统
- Btrfs 的 RAID 5 和 RAID 6 模式存在致命缺陷,不应“用于除测试用一次性数据之外的任何用途”。已知问题列表和部分变通方法。有关状态更新,请参阅 btrfs(5) § RAID56 STATUS AND RECOMMENDED PRACTICES。
- 默认情况下,systemd 会禁用
/var/log/journal的 CoW,这可能导致 RAID 1 数据损坏(参见 #禁用 CoW)。为防止此问题,请创建一个空文件/etc/tmpfiles.d/journal-nocow.conf来覆盖/usr/lib/tmpfiles.d/journal-nocow.conf(参见 tmpfiles.d(5) § CONFIGURATION DIRECTORIES AND PRECEDENCE)。
可以使用多个设备来创建 RAID。支持的 RAID 级别包括 RAID 0、RAID 1、RAID 10、RAID 5 和 RAID 6。从内核 5.5 开始支持 RAID1c3 和 RAID1c4(RAID 1 级别的 3 副本和 4 副本)。可以使用 -d 和 -m 选项分别配置数据和元数据的 RAID 级别。默认情况下,数据只有一个副本(single),元数据是镜像的(raid1)。这类似于创建 JBOD 配置,其中磁盘被视为一个文件系统,但文件不重复。有关如何创建 Btrfs RAID 卷的更多信息,请参阅 使用 Btrfs 进行多设备使用。
# mkfs.btrfs -d single -m raid1 /dev/part1 /dev/part2 ...
为了在池中使用多个 Btrfs 设备,您必须在 /etc/mkinitcpio.conf 中包含 udev 挂钩、systemd 挂钩或 btrfs 挂钩。有关更多信息,请参阅 Mkinitcpio#通用挂钩 文章。
创建文件系统后,建议运行以下命令来扫描多设备 Btrfs 文件系统并进行注册,这样就可以仅指定一个成员来挂载多设备文件系统
# btrfs device scan
- 之后可以向多设备文件系统添加设备。有关更多信息,请参阅 Btrfs wiki 文章。
- 设备大小可以不同。但是,如果 RAID 配置中的一个驱动器大于其他驱动器,那么额外的空间将不会被使用。
- 某些 引导加载程序(如 Syslinux)不支持多设备文件系统。
- Btrfs 不会自动从最快的设备读取数据,因此混合不同类型的磁盘会导致性能不一致。有关详细信息,请参阅 [1]。
有关多设备 Btrfs 文件系统特有的维护建议,请参阅 #RAID。
配置文件
Btrfs 使用 配置文件的概念来配置镜像、奇偶校验和条带化。在标准的 RAID 术语中,这称为RAID 级别。对于同一个 Btrfs 文件系统,元数据(mkfs.btrfs(8) 的 -m 选项)和数据(mkfs.btrfs(8) 的 -d 选项)的配置文件可以不同。
一些值得注意的配置文件
- single
- 无镜像、无条带化、无奇偶校验,允许将多个设备映射到一个文件系统,在 mdadm 术语中称为
LINEAR。 - raid0
- 无镜像、条带化、无奇偶校验,允许设备间的并行访问,但与传统的 mdadm RAID 不同,它不限于相同大小的设备。
- raid1
- 镜像、无条带化、无奇偶校验,允许从一次驱动器故障中恢复。
配置文件系统
写时复制 (CoW)
默认情况下,Btrfs 始终对所有文件使用 写时复制。写入不会就地覆盖数据;而是将修改后的块副本写入新位置,并更新元数据以指向新位置。有关实现细节以及优缺点,请参阅 Btrfs Sysadmin Guide 部分。
禁用 CoW
nodatacow 文件。当与 RAID 1 结合使用时,断电或其他损坏源可能导致数据不同步。要禁用对已挂载子卷中新创建文件的写时复制,请使用 nodatacow 挂载选项。这只会影响新创建的文件。对于现有文件,仍然会发生写时复制。nodatacow 选项还会禁用压缩。有关详细信息,请参阅 btrfs(5)。
- 来自 btrfs(5) § MOUNT OPTIONS:“在一个文件系统内,无法用
nodatacow挂载某些子卷,而用datacow挂载其他子卷。第一个挂载的子卷的挂载选项将应用于任何其他子卷。” - 即使禁用了写时复制,在某些情况下仍然可能会触发它。有关详细信息,请参阅下面的 #仍然触发 CoW 的情况。
要禁用单个文件/目录的写时复制,请执行以下操作
$ chattr +C /dir/file
$ mv /path/to/dir /path/to/dir_old $ mkdir /path/to/dir $ chattr +C /path/to/dir $ cp -a --reflink=never /path/to/dir_old/. /path/to/dir $ rm -rf /path/to/dir_old请确保在此过程中数据未被使用。有关
--reflink=never 选项用法的更多信息,请参阅下面的 #对复制的影响。仍然触发 CoW 的情况
如果一个具有 NOCOW 属性 (+C) 的文件有多个引用(例如,通过 cp 使用 reflink 创建的副本或 Btrfs 创建的快照),写时复制 *仍然* 会被触发。
对复制的影响
当使用 cp 复制文件时,NOCOW 属性不是由源文件决定的,而是由目标路径决定的——要么继承自目录,要么由子卷是否以 nodatacow 选项挂载来决定。仅当源文件和目标文件都具有或都不具有 NOCOW 属性时,才可能进行 Reflink 复制。实际行为取决于 --reflink 选项,有三种可能的结果
- 使用
--reflink=auto(默认):如果 NOCOW 属性匹配,则使用 reflink;否则,将执行深拷贝。 - 使用
--reflink(或--reflink=always):如果 NOCOW 属性匹配,则使用 reflink;如果它们不同,操作将失败。 - 使用
--reflink=never:始终执行深拷贝。
有关 --reflink 选项的更多信息,请参考 cp(1)。
对快照的影响
如果一个文件已禁用写时复制 (NOCOW) 并且拍摄了 快照,那么在快照后对文件块的第一次写入将是 COW 操作,因为快照会锁定旧的文件块。但是,文件将保留 NOCOW 属性,并且对同一文件块的任何后续写入都将是就地写入,直到下一个快照。
频繁的快照可能会降低 NOCOW 的有效性,因为第一次写入仍然需要 COW。要完全避免对此类文件的写时复制,请将它们放入单独的子卷中,并且不要对此子卷拍摄快照。
压缩
Btrfs 支持透明和自动压缩。这可以减小文件大小,并通过减少写入放大来显著延长闪存介质的寿命。请参阅 Fedora:Changes/BtrfsByDefault#Compression、[2] 和 [3]。它还可以提高性能,在某些情况下(例如,单线程大量文件 I/O),但显然会在其他情况下(例如,多线程和/或 CPU 密集型任务的大文件 I/O)损害性能。通常使用最快的压缩算法 zstd 和 lzo 可以获得更好的性能,一些基准测试提供了详细的比较。
压缩类型
Btrfs 支持 zlib (由 zlib 提供的 DEFLATE)、lzo (LZO) 和 zstd (由 zstd 实现的 Zstandard) 压缩算法。LZO 没有压缩级别,而 zlib 和 zstd 有可调的压缩级别(zlib:1-9;zstd:-15 到 -1、1-15,必须是整数)。更高的级别提供更好的压缩,但需要更多处理时间。更改级别将以不同的方式影响 CPU 和 I/O 吞吐量,因此在更改前后应进行检查/基准测试。有关压缩类型的更多信息,请参阅 btrfs(5) § COMPRESSION。
zstd (特别是级别 -15 到 -1) 的 btrfs-progs 的系统,如果您使用此选项,可能无法读取或修复您的文件系统。启用压缩
针对文件系统
compress=alg[:level] 挂载选项可以自动启用对文件系统每次写入的压缩考虑,其中 alg 为 zlib、lzo、zstd 或 no(表示不压缩),可选的 level 指定压缩级别(未指定或设置为 0 时默认为 3;不适用于 lzo)。使用此选项,Btrfs 将检查文件写入的第一个数据块是否收缩。如果收缩,则对该文件的所有写入都将被压缩。如果未收缩,则将该文件标记为 NOCOMPRESS,并且当前写入和该文件的所有后续写入都不会被压缩 [4]。这样做是为了防止磁盘等待写入所有数据并尝试压缩,直到数据完全提供给 Btrfs。
- 压缩挂载选项在同一文件系统的所有挂载点之间共享(包括不同的子卷和绑定挂载)[5]。
- 如果一个文件的写入无法被压缩,后续写入也不会被压缩。
或者,您可以使用 btrfs property set / compression alg 命令将压缩属性设置在 btrfs 子卷上,它将持久存在并应用,无论如何挂载,其中 alg 可以是 zstd 或 zstd:n,其中 n 是压缩级别。
可以使用 compress-force=alg[:level] 挂载选项代替,它会使 Btrfs 检查每次写入的每个数据块并单独决定是否压缩它们。在多个混合使用系统上的经验测试表明,与 compress=zstd 相比,使用 compress-force=zstd 可以显著提高空间节省(从 10% 到 20%),但这会导致(略微)更高的 CPU 使用率和更长的写入时间,而没有明显的好处。然而,强制压缩与官方 Btrfs 指南相悖。
只有在添加上述任一挂载选项后创建或修改的文件才会被自动压缩。
compress 选项:mount -o compress=zstd /dev/sdxY /mnt/。在配置过程中,将相同的 compress 挂载选项添加到 fstab 中的根文件系统。针对现有文件
要将压缩应用于现有文件,请使用 btrfs filesystem defragment -calg 命令,其中 alg 为 zlib、lzo 或 zstd。要指定压缩级别,请使用 -L 选项,否则使用默认级别(不适用于 lzo)。例如,要使用 zstd 和压缩级别 1 重新压缩所有文件,请运行以下命令
# btrfs -v filesystem defragment -r -czstd -L1 /
cp 创建的副本)的文件进行碎片整理可能会导致两个不相关的文件,可能极大地增加磁盘使用量。使用上述方法压缩文件不是持久的;其他写入操作将应用原始压缩设置。
以下两种方法可以为单个文件持久启用压缩
$ chattr +c file $ btrfs property set file compression zstd
第一个命令使用了继承自 ext2 文件系统的文件属性的旧版接口,并且不够灵活,默认使用 zlib 压缩算法。第二个命令可以指定压缩算法,但尚未实现指定压缩级别的功能,因此使用默认级别 3(不适用于 lzo)。
查看压缩类型和比例
compsize 接受文件或目录列表(或整个 Btrfs 文件系统),并输出使用的压缩类型和实际压缩比例(压缩大小/未压缩大小)。未压缩的大小可能与 du(1) 等其他程序给出的数字不符,因为每个 extent 只计算一次——即使它有多个 reflink,或者它的部分不再被任何地方使用但尚未被垃圾回收。
-x 选项将其限制在单个文件系统上,这在 compsize -x / 等情况下很有用,可以防止它尝试访问非 Btrfs 子目录并导致整个运行失败。
子卷
"Btrfs 子卷不是块设备(也不能被当作块设备处理),相反,Btrfs 子卷可以被视为一个 POSIX 文件命名空间。这个命名空间可以通过文件系统的顶层子卷访问,也可以独立挂载。" [6]
每个 Btrfs 文件系统都有一个 ID 为 5 的顶层子卷。此子卷不能被移除或被另一个子卷替换。顶层子卷在文件系统中的路径为 /,其他子卷则嵌套在顶层子卷下方。但是,子卷可以在文件系统中移动,它们的路径可能会改变,而它们的 ID 不会。
默认情况下,在挂载文件系统时会挂载顶层子卷。选项允许挂载特定子卷。
子卷的一个主要用例是快照。
更多详情请参阅以下链接
创建子卷
要创建子卷,Btrfs 文件系统必须已挂载。
# btrfs subvolume create /path/to/subvolume
- 您可以使用
--parents来自动创建父目录(如果它们不存在)。 - 如果顶层子卷未挂载,并且您想在其中创建子卷,可以通过指定
subvolid=5来临时挂载它。请参阅 #挂载子卷。
列出子卷
要查看 path 所属文件系统的所有子卷列表
# btrfs subvolume list -t path
-t 触发更易读的表格视图。
删除子卷
要删除子卷
# btrfs subvolume delete /path/to/subvolume
如果子卷包含其他需要删除的子卷,请添加 -R/--recursive 选项。或者,子卷可以像普通目录一样删除(rm -r、rmdir)。
挂载子卷
可以使用 subvol=/path/to/subvolume 或 subvolid=objectid 挂载选项来挂载子卷。可以通过在文件系统顶层创建各种子卷,然后将它们挂载到相应的挂载点来模拟传统的独立分区。
例如,以下命令将顶层子卷挂载到 /mnt/ 并创建了两个名为 subvol_root 和 subvol_home 的子卷。当顶层子卷被卸载时,新子卷将被挂载到 /mnt/ 和 /mnt/home/
# mount device /mnt/ -o subvolid=5 # btrfs subvolume create /mnt/subvol_root/ # btrfs subvolume create /mnt/subvol_home/ # umount /mnt/ # mount -o subvol=/subvol_root device /mnt/ # mount -o subvol=/subvol_home --mkdir device /mnt/home/
使用 subvol 挂载选项引用子卷需要使用相对于顶层子卷的路径。这可能与顶层子卷的挂载路径不同。
- 建议使用
subvol=/path/to/subvolume挂载,而不是 subvolid,因为在恢复 #快照时 subvolid 可能会发生变化,从而需要更改挂载配置。 - 通过不使用顶层子卷 (ID=5) 作为
/(默认设置)来简化子卷布局的更改。相反,可以考虑创建一个子卷来存放您的实际数据,并将其挂载为/。
请参阅 Snapper#建议的文件系统布局、Btrfs SysadminGuide#管理快照 和 SysadminGuide#布局 以获取使用子卷的示例文件系统布局。
将子卷挂载为根目录
要将子卷用作根挂载点,请将其设置为默认子卷,或通过内核参数使用 rootflags=subvol=/path/to/subvolume 指定子卷。编辑 /etc/fstab 中的根挂载点并指定 subvol= 挂载选项。或者,子卷可以用其 ID 指定,rootflags=subvolid=objectid 作为内核参数,subvolid=objectid 作为 /etc/fstab 中的挂载选项。建议使用 subvol=/path/to/subvolume 挂载,而不是 subvolid,因为在恢复 #快照时 subvolid 可能会发生变化,需要更改挂载配置,否则系统将无法启动。
更改默认子卷
如果不提供 subvol= 挂载选项,则会挂载默认子卷。要更改默认子卷,请执行
# btrfs subvolume set-default subvolume-id /
其中 subvolume-id 可以通过列出来查找。
使用 btrfs subvolume set-default 更改默认子卷将使文件系统的顶层不可访问,除非使用 subvol=/ 或 subvolid=5 挂载选项 [7]。
- GRUB 的
grub-mkconfig脚本 *不* 尊重 Btrfs 的默认子卷设置。如果/是顶层子卷,它永远不会指定subvol=/或subvolid=5挂载选项,这可能导致启动失败。如果/不是顶层子卷,它将始终指定相应的subvol选项,从而无法通过简单地设置默认子卷来回退(bug 报告)。当前可以通过手动修改grub.cfg中的rootflags内核参数(参见 #挂载子卷)或使用工具在 GRUB 中自动创建快照的启动项(参见 #启动到快照)来解决。此外,如果grub.cfg的实际位置发生变化,例如包含/boot的子卷发生变化,您需要再次运行grub-install。参见 此论坛帖子。 - 如果您计划使用 同步和备份程序之一,建议不要更改默认子卷,因为它可能在恢复除默认子卷之外的任何子卷的快照时导致问题。例如,Timeshift 在文件系统的默认子卷下创建一个名为
timeshift-btrfs的路径来存储快照,并且更倾向于为根和主目录使用单独的非默认子卷。
配额
磁盘配额的概念在 Unix 世界中有着悠久的传统。传统配额基于文件所有权,通过限制用户拥有的所有文件的总大小来控制空间使用。虽然这种方法对于文件管理来说很简单,但在目录级别的限制方面存在不足,通常需要在安装时进行分区,并且缺乏动态调整功能。Btrfs 采用了与传统 Unix 系统不同的配额设计理念,不支持传统的基于 用户或组 的配额功能。这是因为其现代存储特性(如 #快照、#写时复制 (CoW)、#重复数据删除 和 #压缩)使得传统的配额空间计算极其复杂且不准确 [8]。作为替代,Btrfs 使用基于子卷的配额机制,目前提供两种实现方法——传统的 #配额组 (qgroups) 和较新的 #简单配额 (squotas)(在 2023 年底发布的内核 6.7 中引入),以达到类似的空间管理效果。尽管这增加了管理复杂性,但它提供了更灵活和精确的存储控制能力,允许在不分区的情况下限制目录大小,并支持动态配额调整。
配额组 (qgroups)
最近的内核改进(5.15 及更高版本)修复了许多 历史问题,但 一些限制仍然存在,特别是在高级应用场景中,例如深度嵌套的子卷或复杂的 qgroup 层级结构。自 2016 年以来在这里写的建议——在启用 qgroups 之前仔细评估具体用例——至今仍然适用。请务必参考最新的 Btrfs 文档 以获取当前详细信息。值得注意的是,为了解决 qgroups 的性能问题,Btrfs 引入了 #简单配额 (squotas) 功能,提供了一种灵活性稍低但性能更好的替代解决方案。
Btrfs 的精确配额支持是通过子卷之上的 qgroups 实现的。Qgroups 使用 qgroupids 表示,格式为 level/ID。子卷的级别为 0,此时可以省略 0/,相应的 ID 是子卷 ID。例如,0/5 表示顶层子卷的 qgroup。也可以使用子卷路径而不是 0/ID 的表示形式。Qgroups 形成一个 *树* 层级结构,但一个 qgroup 可以有多个父 qgroup [9]。叶子 qgroup 级别为 0,直接对应子卷。所有更高级别的 qgroup 的 ID 都可以自由指定。更高级别的 qgroup 包含更低级别的 qgroup,同级组不能嵌套,但级别并不表示嵌套深度。例如,子 qgroup 0/5 可以分配给 qgroup 5/100。
总引用空间和独占引用空间
每个 qgroup 主要跟踪两个值:*总引用空间*和*独占引用空间*。*总引用空间*指的是从 qgroup 内部可访问的所有数据占用的存储空间,而*独占引用空间*指的是仅被 qgroup 中的 **子卷** 引用(并且不被 qgroup 外的 **子卷** 引用)的数据占用的存储空间。
启用/禁用 qgroups
使用以下命令为包含 path 的文件系统启用 qgroups
# btrfs quota enable path
将 enable 改为 disable 可禁用 qgroups。
创建/销毁 qgroups
与子卷对应的 0 级 qgroups 始终自动创建。即使在启用配额之前就创建了子卷,在启用配额时也会自动创建相应的 qgroups。同样,在 删除子卷 时,将自动删除相应的 qgroups 并自动解除与最初包含这些 qgroups 的更高级别 qgroups 的关联。
使用以下命令在包含 path 的文件系统中创建 qgroup qgroupid
# btrfs qgroup create qgroupid path
将 create 改为 destroy 可销毁 qgroup。销毁 qgroup 类似于使用 rm -d 删除目录——如果 qgroup 有子 qgroups,必须先删除关系;如果只有父 qgroups,关系将自动删除。
分配/移除子 qgroups
使用以下命令在包含 path 的文件系统中将 src 分配为 dst 的子 qgroup,请注意 dst 必须比 src 级别更高
# btrfs qgroup assign src dst path
将 assign 改为 remove 可移除此关系。
限制/取消限制 qgroups
您可以限制 qgroups 的总引用空间或独占引用空间,或同时限制两者。例如,使用以下命令将包含 path 的文件系统中 qgroupid 的 **总引用空间** 限制为不超过 1GiB
# btrfs qgroup limit 1G qgroupid path
如果省略 qgroupid,则尝试将 path 解释为子卷路径。在 limit 之后添加 -e 选项,以限制 **独占引用空间**。将 size 改为 none 可移除限制。
列出 qgroups
使用以下命令列出包含 path 的文件系统中的所有 qgroups
# btrfs qgroup show path
btrfs qgroup show 使用磁盘数据,因此可能需要在显示准确统计信息之前执行 sync。为此,您可以添加 --sync 选项(在 show 之后),以首先对包含 path 的文件系统执行强制同步操作。输出中的“Path”列可能显示一些具有以下含义的特殊值
<toplevel>: 对应顶层子卷的 Qgroup。<under deletion>: 对应此 qgroup 的子卷已被删除(其目录已移除),但子卷元数据尚未完全清理。
btrfs subvolume sync path subvolid 等待包含 path 的文件系统中子卷的完全删除(可以指定多个子卷 ID;如果未指定,则等待文件系统中所有当前待处理的子卷删除完成)。但请注意,首先需要卸载子卷。<squota space holder>:(仅适用于 #简单配额 (squotas))对应此 qgroup 的子卷已完全删除,但相关统计信息仍被保留。这是因为简单配额仅将 extent 归属给首次分配它们的子卷,并且虽然该子卷已完全删除,但这些 extent 仍被其他子卷引用。
根据您的需求,您可以添加一些显示选项(在 show 之后)。常用选项包括
-p: 显示父 qgroups。-c: 显示子 qgroups。-r: 显示总引用空间限制。-e: 显示独占引用空间限制。-f: 仅列出对应包含 path 的子卷的 qgroups。-F: 仅列出对应包含 path 的子卷的 qgroups 以及包含这些 qgroups 的更高级别 qgroups。
有关更多选项,请参阅 btrfs-qgroup(8) § show。
配额重扫描
配额重扫描 读取文件系统中所有 extent 的元数据,并相应地更新每个 qgroup 的统计信息。
Btrfs qgroups 可以处理许多复杂的 extent 共享和取消共享场景(包括子卷和子 qgroups 的删除),同时保持总引用空间和独占引用空间的准确计数。然而,当 qgroup 关系发生变化时(手动 分配/移除子 qgroups),由于记录的数据不足(仅记录总引用空间和独占引用空间,不明确记录哪些 extent 属于共享或独占),通常需要对整个文件系统进行配额重扫描。此时,qgroups 将被标记为“不一致”,表示需要配额重扫描的状态。
在当前实现中,唯一的例外是当 qgroup 的总引用空间等于其独占引用空间时,这意味着所有数据都是独占的。在这种情况下,当对该子卷执行分配/移除操作时,只需同时将该 qgroup 的引用空间添加到/从中减去父 qgroup 的总引用空间和独占引用空间。
从内核版本 4.19 开始,手动 分配/移除子 qgroups 会自动触发配额重扫描(在必要时)。但是,由于配额重扫描开销很大,一次只能执行一次,并且此方法不能在返回前等待重扫描完成,因此您可以添加 --no-rescan 选项(在 assign/remove 之后)来避免自动触发,并在之后手动触发。
使用以下命令手动触发包含 path 的文件系统的配额重扫描
# btrfs quota rescan path
该命令立即返回。添加 -w(--wait)选项(在 rescan 之后)可在返回前等待重扫描完成(即使已开始)。使用 -W(--wait-norescan)选项仅等待当前正在进行的重扫描完成。使用 -s(--status)选项可返回当前进度。
简单配额 (squotas)
Qgroups 可以处理许多复杂的 extent 共享和取消共享场景(包括子卷和子 qgroups 的删除),同时保持总引用空间和独占引用空间的准确计数。然而,这种灵活性是有代价的:许多计算操作是全局性的,这意味着当 extent 引用关系发生变化时,它们会影响引用该 extent 的所有 qgroups 的统计信息。这可能导致交易提交速度变慢,尤其是在快照数量急剧增加时,导致不可接受的延迟。
为了解决 qgroups 的这一限制,Btrfs 支持第二套配额语义:简单配额 (squotas)。Squotas 重用 qgroup API 和层级结构模型,但不跟踪共享和独占使用情况。相反,squotas 将所有 extent 归属给首次分配它们的子卷。通过引入少量新的元数据记录,这使得所有计费决策都可以在涉及数据块分配或释放的操作中本地完成,完全避免了复杂且耗时的反向引用解析过程。
Squotas 需要在文件系统级别启用,只需将 -s(--simple)选项(在 enable 之后)添加到 启用 qgroups 命令中。请注意,如果 qgroups 已启用,您需要先 禁用 qgroups,然后再启用 squotas,否则它将不会生效 [10]。由于其简单的计算方法,squotas 模式不需要(也不能)执行 #配额重扫描。除了这两点之外,squotas 的操作与 qgroups 完全相同,但显示的和限制的所谓“总引用空间”和“独占引用空间”都是通过上述方法计算的值(将所有 extent 归属给首次分配它们的子卷)。由于 squotas 需要记录首次分配 extent 的子卷,因此它们仅对启用后写入的 extent 生效。如果在非空文件系统上启用 squotas,首次启用时的统计信息将为 0,因此只有在空子卷上启用 squota 限制然后写入数据,才能确保统计信息的准确性。
提交间隔
数据写入文件系统的分辨率由 Btrfs 本身和系统范围的设置决定。Btrfs 默认的检查点间隔为 30 秒,在此期间新数据会被提交到文件系统。可以通过在 /etc/fstab 中为 Btrfs 分区添加 commit 挂载选项来更改此设置。
LABEL=arch64 / btrfs defaults,compress=zstd,commit=120 0 0
系统范围的设置也会影响提交间隔。它们包括 /proc/sys/vm/* 下的文件,超出了本文档的范围。相关的内核文档可在 https://docs.linuxkernel.org.cn/admin-guide/sysctl/vm.html 获取。
SSD TRIM
Btrfs 文件系统能够从支持 TRIM 命令的 SSD 驱动器上释放未使用的块。异步丢弃支持使用挂载选项 discard=async 提供,并且自 linux 6.2 起默认启用。释放的 extent 不会立即丢弃,而是将它们分组,稍后由单独的工作线程进行修剪,从而提高提交延迟。
异步丢弃可以与周期性修剪安全地一起使用 [11]。
有关启用和使用 TRIM 的更多信息,请参见 固态硬盘#TRIM。
用法
Swap 文件
Btrfs 和 Linux 交换子系统实现存在一些限制 [12]
- 不支持跨多个设备的 Btrfs 文件系统上的交换文件
- 数据 配置文件 必须是
single - 无法为包含活动交换文件的子卷创建快照
- 交换文件必须是预分配的(即,不能有空洞)
- 必须为交换文件单独 禁用 写时复制(即,交换文件必须具有 NOCOW 属性)
最后两项交换文件的限制由 btrfs filesystem mkswapfile 命令自动处理。
有关交换文件的通用信息,请参见 交换#交换文件。
要正确创建 Btrfs 上的交换文件,请先 创建一个子卷 来存储交换文件,因为之后无法为该子卷创建快照。例如,创建 /swap 子卷
# btrfs subvolume create /swap
在 /swap/ 中创建一个 4GiB 的交换文件 swapfile
# btrfs filesystem mkswapfile --size 4g --uuid clear /swap/swapfile
--size 选项指定交换文件大小,默认为 2 GiB,最小为 40 KiB。
激活 Swap 文件
# swapon /swap/swapfile
最后,编辑 fstab 配置文件以添加交换文件的条目
/etc/fstab
/swap/swapfile none swap defaults 0 0
有关更多信息,请参阅 fstab#Usage。
有关删除交换文件和其他详细信息,请参见 交换#交换文件。
显示已用/可用空间
通用的 Linux 用户空间工具,如 df(1) 会不准确地报告 Btrfs 分区的可用空间,因为它们不计算文件和元数据的使用情况。建议使用 btrfs filesystem usage 来查询 Btrfs 分区。例如,要查看设备分配和使用统计信息的完整明细
# btrfs filesystem usage /
RAID5 或 RAID6 配置文件 与同一文件系统中的其他配置文件共存(例如,元数据使用 DUP,而数据使用 RAID5),btrfs filesystem usage 和 btrfs filesystem df 将显示不准确的结果 [13]。或者,btrfs filesystem df 允许快速检查已分配空间的使用情况,而无需 root 权限
$ btrfs filesystem df /
有关更多信息,请参见 [14]。
分析文件系统某个子集空间使用情况的工具(如 du(1) 或 ncdu(1))也存在相同限制,因为它们不考虑 #写时复制 (CoW) 或透明 #压缩。相反,请参阅 btduAUR 和 compsize 获取支持 Btrfs 的替代方案。
碎片整理
Btrfs 通过挂载选项 autodefrag 支持在线碎片整理;请参阅 btrfs(5) § MOUNT OPTIONS。要手动整理根目录(不向下遍历子卷、挂载点和目录符号链接),请使用
# btrfs filesystem defragment -r /
cp、#快照 或 重复数据删除 后的文件)。这可能会导致空间使用量显著增加,具体取决于被破坏的 reflink [15]。-r 的目录参数不会递归地整理文件,但会整理某些内部树(extent tree 和子卷树)。这令人困惑,并可能在将来被移除。RAID
Btrfs 为 #多设备文件系统 提供原生“RAID”功能。Btrfs RAID 与 mdadm 不同的显著特性包括自愈冗余阵列和在线平衡。有关更多信息,请参阅 Btrfs wiki 页面。Btrfs 系统管理员页面还 有一个部分 包含一些更深层技术背景。
Scrub
Btrfs Wiki Glossary 中提到 Btrfs scrub 是“[一个在线文件系统检查工具。读取文件系统上的所有数据和元数据,并使用校验和和 RAID 存储中的副本(如果存在)来识别和修复任何损坏的数据]”。
手动启动
启动包含 / 的文件系统的(后台)scrub
# btrfs scrub start /
检查正在运行的 scrub 的状态
# btrfs scrub status /
使用服务或计时器启动
btrfs-progs 包提供了 btrfs-scrub@.timer 单元,用于每月对指定的挂载点进行 scrubbing。通过转义的路径 启用 该计时器,例如,对于 / 使用 btrfs-scrub@-.timer,对于 /home 使用 btrfs-scrub@home.timer。您可以使用 systemd-escape -p /path/to/mountpoint 来转义路径;有关详细信息,请参阅 systemd-escape(1)。
您也可以通过 启动 btrfs-scrub@.service(使用相同的编码路径)来运行 scrub。与 btrfs scrub(以 root 用户身份)相比,其优点是 scrub 的结果将记录在 systemd journal 中。
在大容量 NVMe 驱动器上,如果冷却不足(例如在笔记本电脑中),scrubbing 可能会足够快且足够长地读取驱动器,使其变得非常热。如果您正在使用 systemd 运行 scrubs,您可以使用 systemd.resource-control(5) 中描述的 IOReadBandwidthMax 选项,通过使用 drop-in 文件 来轻松限制 scrubbing 的速率。
Balance
"balance 将文件系统中的所有数据重新通过分配器。它主要用于在添加或移除设备时重新平衡文件系统中的数据在各个设备上。如果设备发生故障,balance 将为冗余 RAID 级别重新生成丢失的副本。" [16] 参见 上游 FAQ 页面。
在单设备文件系统上,balance 也可能有助于(暂时)减少已分配但未使用的(元)数据块的数量。有时这对于修复 “文件系统已满”问题 是必需的。
# btrfs balance start --bg / # btrfs balance status /
快照
"快照只是一个子卷,它通过 Btrfs 的 COW 功能与另一个子卷共享其数据(和元数据)。" 参见 Btrfs Wiki SysadminGuide#Snapshots 和 Btrfs 文档 获取详细信息。
创建快照
# btrfs subvolume snapshot source [dest/]name
要创建只读快照,请添加 -r 标志。要创建只读快照的可写版本,只需为其创建一个快照即可。
- 可以通过
btrfs property set -f -ts '/path/to/snapshot' ro false将快照就地从只读转换为可写。但是,不建议这样做,因为它 会导致问题,影响任何未来的增量发送/接收。创建新的可写快照可以避免此类问题。 - 快照不是递归的。每个嵌套的子卷将在快照内显示为空目录。
发送/接收
可以使用 send 命令将子卷发送到 stdout 或文件。这通常在通过管道传输到 Btrfs receive 命令时最有用。例如,要将名为 /root_backup 的快照(可能是您之前从 / 制作的快照)发送到 /backup,您可以执行以下操作
# btrfs send /root_backup | btrfs receive /backup
发送的快照 *必须* 是只读的。上述命令对于将子卷复制到外部设备(例如上面挂载在 /backup 的 USB 磁盘)很有用。
接收端将自动创建子卷。不需要手动创建。
另一个创建 /mnt/arch-v2/subvolumes/@var 的示例
# btrfs send --proto 2 --compressed-data '/mnt/arch/snapshots/@var' | btrfs receive '/mnt/arch-v2/subvolumes/'
示例中使用的参数 --proto 2 和 --compressed-data 可能有助于更有效地发送(假定数据已压缩)。
您也可以只发送两个快照之间的差异。例如,如果您已经发送了上面 root_backup 的副本,并在您的系统上创建了一个名为 root_backup_new 的新只读快照,那么要仅将增量差异发送到 /backup,请执行
# btrfs send -p /root_backup /root_backup_new | btrfs receive /backup
现在,将在 /backup 中找到一个名为 root_backup_new 的新子卷。
有关如何使用此进行增量备份和自动化工具的信息,请参阅 Btrfs Wiki 的增量备份页面 和 #增量备份到外部驱动器。
去重
利用写时复制 (copy-on-write),Btrfs 能够在不实际复制数据的情况下复制文件或整个子卷。然而,每当文件被修改时,都会创建一个新的 *真正* 的副本。重复数据删除 (Deduplication) 更进一步,它主动识别具有相同序列的数据块,并将它们合并为一个具有相同写时复制语义的扩展 (extent)。
专门用于 deduplicate Btrfs 格式分区的工具包括 duperemove 和 bees。您也可以选择仅基于文件的 deduplicate 数据,而不是使用 e.g. rmlint-gitAUR, rdfind, jdupesAUR 或 dduper-gitAUR。有关这些程序可用功能的概述和更多信息,请查看 上游 Wiki 条目。
调整大小
您可以将文件系统增长到设备上可用的最大空间,或者指定一个确切的大小。在尝试增加文件系统大小时,请确保先增加设备或逻辑卷的大小。在为设备上的文件系统指定确切大小时,无论是增加还是减小,请确保新大小满足以下条件:
- 新大小必须大于现有数据的大小;否则,会导致数据丢失。
- 新大小必须等于或小于当前设备大小,因为文件系统大小不能超出可用空间。
将文件系统大小扩展到设备的最大可用大小
# btrfs filesystem resize max /
将文件系统扩展到特定大小
# btrfs filesystem resize size /
将 size 替换为所需的字节数。您还可以为该值指定单位,例如 K (kibibytes)、M (mebibytes) 或 G (gibibytes)。或者,您可以通过在值前加上加号 (+) 或减号 (-) 来分别指定增加或减少当前大小。
# btrfs filesystem resize +size / # btrfs filesystem resize -size /
已知问题
在尝试之前,应该了解一些限制。
加密
Btrfs 没有内置的加密支持,但目前有一个基于 Fscrypt 的加密整合工作正在进行中 [17]。
但是,用户可以在运行 mkfs.btrfs 之前加密分区,请参阅 dm-crypt/Encrypting an entire system。另一种方法是 堆叠文件系统加密。
btrfs check 问题
btrfs check 工具存在已知问题,在进一步阅读之前不应运行;请参阅 #btrfs check 部分。
技巧与提示
无分区 Btrfs 磁盘
Btrfs 可以占用整个数据存储设备,取代 MBR 或 GPT 分区方案,使用 子卷 来模拟分区。然而,使用无分区设置并非必需,只需在现有 分区 上 创建 Btrfs 文件系统,该分区是使用其他方法创建的。无分区的单磁盘设置存在一些限制:
要创建无分区的 Btrfs 磁盘,请运行以下命令:
# mkfs.btrfs /dev/sdX
例如,使用 /dev/sda 而不是 /dev/sda1。后者将格式化现有分区而不是替换整个分区方案。因为根分区是 Btrfs,请确保 btrfs 已编译到内核中,或者将 btrfs 放入 mkinitcpio.conf#MODULES 并 重新生成 initramfs。
像对待具有 主引导记录 的数据存储设备一样安装 引导加载程序。请参阅 Syslinux#Manually 或 GRUB/Tips and tricks#Install to partition or partitionless disk。如果您的内核因 Failed to mount /sysroot. 而无法启动,请在 /etc/default/grub 中添加 GRUB_PRELOAD_MODULES="btrfs" 并 生成 grub 配置。
转换
Ext3/4 转 Btrfs 转换
从安装 CD 启动,然后执行以下命令进行转换:
# btrfs-convert /dev/partition
挂载分区并检查文件以测试转换。务必更改 /etc/fstab 以反映此更改(将 *type* 改为 btrfs,并将 *fs_passno* - 最后一个字段 - 改为 0,因为 Btrfs 在启动时不会进行文件系统检查)。另请注意,分区的 UUID 将会更改,因此在使用 UUID 时请相应地更新 fstab。chroot 进入系统并重建引导加载程序的菜单列表(请参阅 Install from existing Linux)。如果转换的是根文件系统,在 chroot 状态下,重新生成 initramfs,否则系统将无法成功启动。
- 如果出现任何问题,例如无法挂载或向新转换的 Btrfs 写入文件,只要备份子卷
/ext2_saved仍然存在,总有一个选择可以回滚。使用btrfs-convert -r /dev/partition命令进行回滚;这将丢弃对新转换的 Btrfs 文件系统的任何修改。 - 如果挂载转换后的 ext 分区时出现类似
ERROR: dev extent devid 1 physical offset XXX len XXX is beyond device boundary XXX的错误,可以通过先在分区后创建一些空闲空间来使转换成功。回滚转换,然后使用resize2fs将分区缩小 50000 个块,然后再将其增大 5000 个块(创建 45000 个空闲块)。然后再次尝试转换。有关更多信息,请参阅 上游 bug 报告。
确认没有问题后,通过删除备份 ext2_saved 子卷来完成转换。请注意,没有它将无法恢复到 ext3/4。
# btrfs subvolume delete /ext2_saved
请记住,先前安装的某些应用程序必须适配 Btrfs。
NTFS 转 Btrfs 转换
可以使用 ntfs2btrfsAUR 或 ntfs2btrfs-gitAUR 来转换 NTFS。
卸载目标文件系统并运行转换,可以指定确切的压缩和校验和类型。
# ntfs2btrfs -c zstd -h crc32c /dev/partition
如果在转换后一切正常,您可以删除 image/ntfs.img(用于恢复原始文件系统的映像)。
转换后
在将现有文件系统转换为 Btrfs 后,您可以采取一些步骤。
使文件数据更连续
# btrfs filesystem defrag -v -r -f -t 32M /mnt/filesystem
#Balance 使 Btrfs 元数据更紧凑
损坏恢复
btrfs check 工具存在已知问题,请参阅 #btrfs check 部分。btrfs-check 不能在挂载的文件系统上运行。要能够在不从 live USB 启动的情况下使用 btrfs-check,请将其添加到初始 ramdisk 中。
/etc/mkinitcpio.conf
BINARIES=(btrfs)
然后,如果启动时出现问题,该实用程序将可用于修复。
有关更多信息,请参阅 btrfs-check(8)。
启动到快照
要启动到快照,与将子卷挂载为根分区相同的过程适用,如 mounting a subvolume as your root partition 部分所述,因为快照可以像子卷一样挂载。
- 如果使用 GRUB,您可以通过 grub-btrfs 或 grub-btrfs-gitAUR 帮助,在重新生成配置时自动将 Btrfs 快照填充到您的引导菜单中。
- 如果使用 rEFInd,则可以通过 refind-btrfsAUR 帮助,在 启用
refind-btrfs.service后,自动将 Btrfs 快照填充到您的引导菜单中。 - 如果使用 Limine,您可以安装 limine-snapper-syncAUR,该工具会在您的 Snapper 列表发生变化后自动生成快照条目到您的引导菜单,只需 启用
limine-snapper-sync.service即可。有关更多信息,请参阅 Limine#Snapper snapshot integration for Btrfs。
与 systemd-nspawn 一起使用 Btrfs 子卷
请参阅 systemd-nspawn#Use Btrfs subvolume as container root 和 systemd-nspawn#Use temporary Btrfs snapshot of container 文章。
减少访问时间元数据更新
由于 Btrfs 的写时复制特性,仅仅访问文件就可能触发元数据复制和写入。减少访问时间更新的频率可以消除这种意外的磁盘使用并提高性能。有关可用选项,请参阅 fstab#atime options。
增量备份到外部驱动器
以下软件包使用 btrfs send 和 btrfs receive 将备份增量发送到外部驱动器。请参阅它们的文档,了解它们在实现、功能和要求方面的差异。
- snbk — 由 snapper 提供的命令行工具,用于将 snapper 快照复制到远程或本地备份。
- btrbk — 用于创建 Btrfs 子卷的快照和远程备份的工具。
- snap-sync — 使用 Snapper 快照备份到外部驱动器或远程计算机。
以下软件包允许将 snapper 快照备份到非 Btrfs 文件系统
- snapborg — 类似于 borgmatic 的工具,将 snapper 快照与 borg 备份集成。
自动快照
对于 Btrfs 快照的管理和自动创建,可以使用快照管理器,例如 Snapper、Timeshift 或 Yabsnap。
自动通知
桌面通知可以帮助您立即注意到严重的 Btrfs 问题,与没有通知相比,能提供更好的警觉性。
btrfs-desktop-notificationAUR 为以下事件提供桌面通知:
- 启动到任何只读快照或系统。
- dmesg 日志中出现的 Btrfs 警告、错误或致命消息。
有关更多信息和配置,请参阅 https://gitlab.com/Zesko/btrfs-desktop-notification。
space cache v1 已弃用
如果您的 Btrfs 文件系统是使用旧的默认值创建的,您可能会在系统日志中看到类似以下的警告:
BTRFS warning (device sdb4): space cache v1 is being deprecated and will be removed in a future release, please use -o space_cache=v2
要将 Btrfs 空间缓存从旧的 v1 格式转换为较新的 v2 格式并解决此警告,您可以修改分区的挂载选项,在 fstab 中包含 space_cache=v2,或者手动执行转换:
# umount /dev/partition # mount /dev/partition -o rw,space_cache=v2 /mnt # umount /mnt
转换的结果可以在 systemd journal 日志中查看,例如:
kernel: BTRFS info (device ...): creating free space tree kernel: BTRFS info (device ...): setting compat-ro feature flag for FREE_SPACE_TREE (0x1) kernel: BTRFS info (device ...): setting compat-ro feature flag for FREE_SPACE_TREE_VALID (0x2) kernel: BTRFS info (device ...): cleaning free space cache v1 kernel: BTRFS info (device ...): enabling free space tree
故障排除
有关一般故障排除,请参阅 Btrfs 故障排除页面和 Btrfs 问题 FAQ。
GRUB
分区偏移量
当您尝试将 core.img 嵌入到分区磁盘时,可能会出现偏移量问题。这意味着将 GRUB 的 core.img 直接嵌入到无分区磁盘(例如 /dev/sdX)上的 Btrfs 池中是 可以的。
GRUB 可以引导 Btrfs 分区,但模块可能比其他 文件系统 更大。grub-install 创建的 core.img 文件可能不适合驱动器 MBR 和第一个分区之间的前 63 个扇区(31.5KiB)。最新的分区工具,如 fdisk 和 gdisk,通过将第一个分区偏移约 1MiB 或 2MiB 来避免此问题。
缺少根
遇到以下情况的用户:从 RAID 风格的设置启动时出现 error no such device: root,然后编辑 /usr/share/grub/grub-mkconfig_lib,并从行 echo " search --no-floppy --fs-uuid --set=root ${hints} ${fs_uuid}" 中删除两个引号。重新生成 grub 的配置,系统应该可以无错误地启动。
启动时间长
有时,大型(> 4TB)Btrfs 卷可能需要很长时间才能挂载,从而减慢启动速度。将组树更改为块组树可以有所帮助。
# btrfstune --convert-to-block-group-tree /dev/sdX
挂载超时
有时,特别是对于大型 RAID1 阵列,启动时挂载可能会超时,并出现类似的日志消息:
Jan 25 18:05:12 host systemd[1]: storage.mount: Mounting timed out. Terminating. Jan 25 18:05:46 host systemd[1]: storage.mount: Mount process exited, code=killed, status=15/TERM Jan 25 18:05:46 host systemd[1]: storage.mount: Failed with result 'timeout'. Jan 25 18:05:46 host systemd[1]: Failed to mount /data. Jan 25 18:05:46 host systemd[1]: Startup finished in 32.943s (firmware) + 3.097s (loader) + 7.247s (kernel)> Jan 25 18:05:46 host kernel: BTRFS error (device sda): open_ctree failed
可以通过在 fstab 中提供更长的 systemd 特定的挂载选项 x-systemd.mount-timeout 来轻松解决此问题。例如:
UUID=xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx /data btrfs rw,relatime,x-systemd.mount-timeout=5min 0 0
BTRFS: open_ctree failed
截至 2014 年 11 月,systemd 或 mkinitcpio 中似乎存在一个 bug,导致使用 mkinitcpio.conf 中 btrfs hook 的多设备 Btrfs 文件系统在系统上出现以下错误:
BTRFS: open_ctree failed mount: wrong fs type, bad option, bad superblock on /dev/sdb2, missing codepage or helper program, or other error In some cases, useful info is found in syslog - try dmesg|tail or so. You are now being dropped into an emergency shell.
一种解决方法是将 mkinitcpio.conf 中的 HOOKS 数组中的 btrfs 删除,而是将 btrfs 添加到 MODULES 数组中。然后 重新生成 initramfs 并重启。
如果您尝试挂载一个缺少其中一个设备的 RAID 阵列,也会出现相同的错误。在这种情况下,您必须将 degraded 挂载选项添加到 /etc/fstab。如果您的根位于该阵列上,还必须将 rootflags=degraded 添加到您的 内核参数。
截至 2016 年 8 月,该 bug 的一种潜在解决方法是在 /etc/fstab 中仅通过单个驱动器挂载阵列,并允许 Btrfs 自动发现并附加其他驱动器。基于组的标识符,如 UUID 和 LABEL,似乎会导致失败。例如,一个由 'disk1' 和 'disk2' 组成的双设备 RAID1 阵列会分配一个 UUID,但不要使用 UUID,而在 /etc/fstab 中仅使用 /dev/mapper/disk1。有关更详细的解释,请参阅以下 博客文章。
另一种可能的解决方法是将 udev hook 从 mkinitcpio.conf 中移除,并用 systemd hook 替换它。在这种情况下,btrfs 应该 *不* 在 HOOKS 或 MODULES 数组中。
有关更多信息和讨论,请参阅 原始论坛线程和 FS#42884。
btrfs check
btrfs check 命令,强烈建议在执行带 --repair 选项的 btrfs check 之前创建 备份 并查阅 btrfs-check(8)。btrfs-check 命令可用于检查或修复未挂载的 Btrfs 文件系统。然而,此修复工具仍然不成熟,甚至无法修复那些不会导致文件系统无法挂载的某些文件系统错误。
持续的驱动器活动
自 内核 版本 6.2 起,discard=async mount(8) 选项默认设置。据 报告,这可能导致在某些驱动器上即使处于空闲状态也会持续驱动器活动,因为 discard 队列填充速度比处理速度快。这可能导致更高的功耗,尤其是在 NVMe 驱动器上。
截至内核版本 6.3,默认的 discard iops_limit 已从 100 更改为 1000 以解决此问题。您可以在旧内核版本上手动将其设置为所需值,例如:
# echo 1000 > /sys/fs/btrfs/uuid/discard/iops_limit
其中 uuid 是 Btrfs 文件系统的 UUID。1000 的限制需要通过实验来调整。
要在启动时设置参数,可以使用 systemd-tmpfiles,例如通过创建以下文件:
/etc/tmpfiles.d/btrfs-discard.conf
w /sys/fs/btrfs/uuid/discard/iops_limit - - - - 1000
或者,可以通过在 fstab 中使用 nodiscard 挂载选项来完全禁用异步 discard,并改用 定期 TRIM。
设备总字节数最多应为 X,但找到 Y
如果一个驱动器从另一台计算机移动,或者设备的顺序已更改,并且报告的大小差异很小(最多几个兆字节),则可能是 HPA (Host Protected Area) 在起作用。
要验证 HPA 是否已启用,请使用 hdparm。
# hdparm -N DEVICE
输出提供两个数字:可见扇区数和实际扇区数。如果它们不同,则 HPA 已启用。
如果主板强制设置了此项,并且固件不提供关闭此项的选项,则唯一的选择是缩小受影响的文件系统。这在原始计算机或不应用 HPA 的任何计算机上最容易完成。
设备空间不足
博客文章 Fixing Btrfs Filesystem Full Problems 建议并解释了以下检查/步骤:
- 立即清理空间(删除历史快照)
- 您的文件系统真的满了?元数据和/或数据块不平衡(运行
btrfs balance) - 您的文件系统真的满了?数据块不平衡
- 您的文件系统真的满了?元数据不平衡
- 由于文件系统已满而无法运行 Balance(暂时向 btrfs 文件系统添加一个设备,如 USB 密钥或 loop 设备,使用
btrfs device add,然后再运行btrfs balance)。
有关 ENOSPC(“磁盘空间不足”)的最新说明,请参阅 ENOSPC - No available disk space | Forza's Ramblings。
参见
- 官方网站
- 性能相关
- 杂项