在 Linux 系统,循环设备(loop device)是一种特殊类型的设备,它允许将一个文件或一个分区视为一个块设备。循环设备可以用于创建虚拟磁盘镜像、加密文件系统、文件系统的压缩和解压缩等操作。

losetup 命令是 Linux 用于管理循环设备的命令。losetup 命令适用于任何 Linux 发行版,包括 Ubuntu,CentOS,RedHat,Debian,Fedora 和 Arch Linux。

在本教程中,我们将说明如何在 Linux 使用 losetup 命令。包括使用 losetup 命令查看创建虚拟磁盘镜像,说明 losetup 命令的选项等。

losetup 命令

在讨论如何使用 losetup 命令之前,让我们先回顾一下基本语法。下面是 losetup 命令语法形式 。

 losetup [options] [<loopdev>] <file>

其中 OPTIONS 是 losetup 命令的选项,可选参数,loopdev 是循环设备的名称 ,可选参数,File 是最后的可选参数,用于指定关联的文件。

在不指定任何选项与参数运行 losetup 命令时, losetup 命令将会打印所有循环设备与关联文件的信息。

losetup
NAME        SIZELIMIT OFFSET AUTOCLEAR RO BACK-FILE                                        DIO LOG-SEC
/dev/loop1          0      0         1  1 /var/lib/snapd/snaps/gnome-3-34-1804_93.snap       0     512
.....
/dev/loop10         0      0         1  1 /var/lib/snapd/snaps/hugo_16793.snap               0     512

在  losetup 命令输出中,你可能除了看到有循环设备名称与关联文件的信息之外,你应该还注意其它的信息,例如关联文件 inode 号码。

  • NAME  循环设备名称
  • BACK-FILE  循环设备关联的文件
  • BACK-INO  关联的文件的 inode 号码
  • BACK-MAJ:MIN  关联文件的主:次设备号
  • MAJ:MIN  循环设备的主:次设备号

AUTOCLEAR  是否清除文件与设备文件关联

如果将 AUTOCLEAR 标志设置为 1,当循环设备卸载时,循环设备与文件映射关系将被删除,并且循环设备将被释放。这意味着在卸载循环设备时,关联文件或设备将不再与该循环设备相关联。

如果将 AUTOCLEAR 标志设置为 0,循环设备在被卸载时将不会自动清除,映射关系将保留,以便稍后再次使用。

因此,AUTOCLEAR 选项允许您在卸载循环设备时选择是否自动清除与之相关联的文件或设备的映射关系。

你可以使用 losetup 命令 --offset 选项设置 OFFSET 的值,这意味着在创建循环设备时指定从关联文件的特定位置开始映射。

创建循环设备

要创建一个循环设备,可以使用 losetup 命令并指定循环设备和要关联的文件,以下是创建循环设备的基本语法:

losetup [options] loopdev file

loopdev 是循环设备的名称,通常你不需要预先创建循环设备,可以直接指定任意设备名称,例如 /dev/loopXX,XX 可以是任意数字。但文件必须是已存在的文件。

当使用 losetup 命令的 --find 选项时,你也可以省略循环设备的名称。--find 选项将会自动查找下一个可用循环设备的名称。

一般情况下,你可能还需要在创建循环设备后打印循环设备的名称。因此请使用 losetup 命令 --show 选项。以下命令,可能是你经常用于创建循环设备的命令。

sudo losetup --find --show file

例如,我们需要创建一个 10 MB大小的空磁盘镜像文件,首先运行 dd 命令创建文件file.img 在当前目录。

dd if=/dev/zero of=file.img bs=1MiB count=10

创建循环设备文件并打印循环设备的名称:

sudo losetup --find --show file.img
/dev/loop27

创建文件系统并进行格式化运行 mkfs 命令:

sudo mkfs -t ext4 /dev/loop27

使用 mkdir 命令创建挂载点并运行 mount 命令挂载循环设备:

sudo mount /dev/loop27 /mnt/myfreax/loop27
ls /mnt/myfreax/loop27

现在,你就可以挂载点上创建文件与目录。

如果你尝试一个已挂载循环设备再关联其它文件。终端将会打印消息 losetup: file1.img: failed to set up loop device: Device or resource busy。

例如继续在循环设备 /dev/loop27 关联文件 file1.img,运行命令 sudo losetup /dev/loop27 file1.img。

sudo losetup /dev/loop27 file1.img
losetup: file1.img: failed to set up loop device: Device or resource busy

列出循环设备

要列出所有循环设备,可以使用 losetup 命令的 -a 选项,也可以在不指定任何选项与参数运行 losetup 命令即可列出所有循环设备。

losetup
losetup -a

除此之外你也可以使用  losetup 命令 -J / --json 选项以 JSON格式保存循环设备的列表。

losetup -J
{
   "loopdevices": [
      {"name":"/dev/loop1", "sizelimit":0, "offset":0, "autoclear":true, "ro":true, "back-file":"/var/lib/snapd/snaps/snapd_19457.snap", "dio":false, "log-sec":512},
      .....
      {"name":"/dev/loop10", "sizelimit":0, "offset":0, "autoclear":true, "ro":true, "back-file":"/var/lib/snapd/snaps/gnome-42-2204_120.snap", "dio":false, "log-sec":512}
   ]
}

losetup 命令默认打印所有列数据息,你也可以使用 -O / --output 选项打印指定的列数据。例如以下命令仅打印循环设备名称和关联文件大小的限制。

losetup -O NAME,SIZELIMIT

你可能在处理数据时不需要头部的列名称,因此可以使用 losetup 命令的 --noheadings 选项不打印列名称。

losetup   -O  NAME,SIZELIMIT --noheadings
/dev/loop1          0
....
/dev/loop20         0
/dev/loop10         0

删除循环设备

要删除循环设备,可以使用 losetup 命令的 -d / --detach 选项后跟一个或者多个循环设备的名称。

准确的说,这不是删除而是分离。在删除循环设备之前,请先卸载该循环设备,否则不能够再关联其它文件。

如果你不知道循环设备的名称可以运行 losetup 命令列出所有循环设备的信息。

losetup -d <loopdev> <loopdev>....

例如以下命令将会删除循环设备 /dev/loop27,/dev/loop28。

sudo umount /dev/loop27
losetup -d /dev/loop27 /dev/loop28

设置关联文件开头的偏移量

你可以使用 losetup 命令 --offset / -o 选项设置 OFFSET 的值,这意味着在创建循环设备时指定从关联文件的特定位置开始映射。

losetup -o <offset> <loopdev> <file>

其中,<offset> 是以字节为单位的偏移量,表示从后备文件的开头开始的偏移量。<loopdev> 是循环设备的名称,可以是任何合法的设备名称,例如 /dev/loop0<file> 是要关联的文件的路径。

通过指定 OFFSET 选项,您可以将循环设备从后备文件的指定偏移量处开始映射。这对于访问文件中的特定部分或跳过文件中的特定部分非常有用。例如,如果您希望只映射文件的后半部分,可以通过指定适当的偏移量来实现。

请注意,使用 OFFSET 选项时,您需要确保指定的偏移量值是正确的,以便正确地映射关联文件的指定部分。

设置分区扫描标识

你可以使用 losetup 命令 --partscan / -P 选项设置 PARTSCAN 的值,这意味您可以指定是否在循环设备执行分区扫描。

losetup -P <loopdev> <file>

其中,<loopdev> 是循环设备的名称,可以是任何合法的设备名称,例如 /dev/loop0<file> 是您要关联文件的路径。

通过指定 --partscan / -P 选项,您可以启用在循环设备上的分区扫描。这将使操作系统自动检测和创建循环设备上的分区设备节点。这样,您可以通过访问循环设备的分区来读取和写入分区中的数据。

请注意,使用 PARTSCAN 选项时,您需要确保关联文件包含一个分区表(如MBR或GPT),使操作系统能够正确识别和创建分区设备节点。此选项仅在循环设备关联的文件包含分区表时才有效。

创建只读设备

你可以使用 losetup 命令 -r / --read-only 选项设置 RO 的值,这意味您可以将循环设备设置为只读,禁止对其进行写操作。

losetup -r  <loopdev> <file>

其中,<loopdev> 是循环设备的名称,可以是任何合法的设备名称,例如 /dev/loop0<file> 是您要关联的后备文件的路径。

通过指定 -r / --read-only 选项,循环设备将被设置为只读模式,意味着您不能对循环设备进行写操作。这对于保护关联文件的内容免受意外修改或删除非常有用。

请注意,使用 -r / --read-only 选项时,您需要确保关联文件有读权限。否则,无法将循环设备设置为只读模式。

设置关联文件的大小限制

你可以使用 losetup 命令 -r / --read-only 选项设置 SIZELIMIT 的值,这意味您可以限制循环设备映射的文件的大小。

losetup --sizelimit <num> <loopdev> <file>

其中,<num> 是以字节为单位的文件大小限制值。<loopdev> 是循环设备的名称,可以是任何合法的设备名称,例如 /dev/loop0<file> 是关联文件的路径。

通过指定  -r / --read-only  选项,您可以限制循环设备映射的关联文件的大小。这将导致循环设备只能访问和读取文件中的指定的字节数。

请注意,使用 -r / --read-only 选项时,您需要确保指定的大小限制值是正确的,以便正确地限制循环设备映射的关联文件的大小。这可以用于限制对文件的部分访问,特别是在处理大型文件时。

使用直接 IO 访问关联文件

你可以使用 losetup 命令 --direct-io 选项设置 DIO 的值,您可以控制循环设备的IO访问方式。

losetup --direct-io <loopdev> <file>

其中,<loopdev>是循环设备的名称,可以是任何合法的设备名称,例如 /dev/loop0<file> 是您要关联文件的路径。

通过指定 --direct-io 选项,循环设备在访问关联文件时将使用直接IO (Direct I/O) 。直接 IO 绕过操作系统的缓存机制,直接将数据从磁盘读取到应用程序的内存中,或将数据从应用程序的内存写入到磁盘中。这可以提高 IO 性能,尤其是在处理大型文件时。

请注意,使用 --direct-io 选项时,您需要确保系统支持直接IO,并且关联文件的访问权限正确设置。

此选项可能不适用于所有系统和文件系统类型。在某些情况下,使用直接 IO 可能会导致性能下降。因此,在使用 --direct-io 选项之前,请确保了解直接 IO 在您的环境中的影响和适用性

设置逻辑扇区大小

逻辑扇区大小,也称为操作系统扇区大小,是暴露给操作系统和应用程序的扇区大小。它是用于在软件级别读取和写入存储设备的扇区大小。

对于大多数文件系统,扇区的大小固定为 512 字节,对于虚拟磁盘,逻辑扇区大小必须设置为 512 或 4096 字节。

你可以使用 losetup 命令 --sector-size 选项设置 LOG-SEC 的值,也就是设置循环设备的扇区大小。

losetup --sector-size <4096/512> <loopdev> <file>

其中,<4096/512> 你只能设置两个数值的其中一个。<loopdev> 是您为循环设备指定的名称,可以是任何合法的设备名称,例如 /dev/loop0<file>是要关联文件的路径。

结论

至此你已熟悉如何在 Linux 使用 losetup 命令查看创建虚拟磁盘镜像,创建,删除循环设备,调整循环设备容量,大小等选项。如果您有任何问题或反馈,请随时发表评论。