我正在使用 ubuntu 18.04-4,并希望将一个大目录(我的项目的 yocto 构建目录)从我的移动到外部驱动器(ext4 格式)。外部驱动器是一个 512 GB 的空驱动器。每当我尝试使用或~/Desktop
将文件夹复制到外部驱动器时,经过数小时的复制,我都会收到以下错误:cp -r
rsync -ah
No space left on device (28)
当我检查驱动器上的空间时(复制失败后),我发现它实际上已经满了!
df -hT
显示以下 2 条相关内容:
Filesystem Type Size Used Avail Use% Mounted on
/dev/sda1 ext4 246G 212G 23G 91% /
/dev/sdb1 ext4 469G 445G 24K 100% /media/builder/WorkSpace
du -sh
我的源文件夹显示源是 111 GB。
在发出cp
(或rsync
)命令之前,df -hT
显示:
Filesystem Type Size Used Avail Use% Mounted on
/dev/sdb1 ext4 469G 73M 445G 1% /media/builder/WorkSpace
所以目标驱动器肯定是空的。
关于我已经用完了 Inode 的建议似乎并不适用于我的情况。从上面的 df -hT 输出可以看出,我的情况实际上使用了所有空间。
目标驱动器刚刚格式化,而且绝对足够大。为什么复制的数据比源文件夹(以及整个源磁盘)大得多?这可能是什么原因造成的?
编辑:关于我已经用完了 Inode 的建议似乎并不适用于我的情况。从上面的 df -hT 输出可以看出,我的情况实际上使用了所有空间。
我尝试使用的具体命令如下:
sudo cp -r Desktop/Yocto_test /media/builder/Workspace/
rsync -ah /home/builder/Desktop/Yocto_test /media/builder/WorkSpace
与该(目标)磁盘相关的“df”命令的结果是:
Filesystem 1K-blocks Used Available Use% Mounted on /dev/sdb1
491173784 466153780 0 100% /media/builder/WorkSpace
df -i
产量:
Filesystem Inodes IUsed IFree IUse% Mounted on /dev/sdb1
31260672 15285870 15974802 49% /media/builder/WorkSpace
评论中要求的一些其他测试:
df -hi | grep -E 'Inodes|sd[ab]1'
Filesystem Inodes IUsed IFree IUse% Mounted on
/dev/sda1 16M 7.4M 8.3M 48% /
/dev/sdb1 30M 15M 16M 49% /media/builder/WorkSpace
du -xms ~/Desktop/Yocto_test/ /media/builder/WorkSpace
113145 /home/builder/Desktop/Yocto_test/
455157 /media/builder/WorkSpace
答案1
我终于明白了为什么会发生这种情况,这不是由稀疏文件、块大小问题甚至 Inode 耗尽引起的!
问题是 Yocto(创建了我尝试复制的目录中的大多数文件的构建工具)非常喜欢使用硬链接。它创建的数百万个文件中的大多数实际上都是指向同一目录中其他文件的硬链接。因此它们不会占用额外的空间。
cp(和 rsync)默认不保留硬链接。当它们遇到硬链接文件时,它们将为其创建一个全新的 inode,并最终将 inode 的大小乘以指向它的硬链接的数量!
这也解释了为什么我可以tar czvf
访问目录。Tar 的默认行为是保留硬链接。
我现在可以使用cp -a
以下方法成功地将我的目录复制到外部存储:
sudo cp -a Yocto_test /media/builder/WorkSpace/
我希望这能帮助其他遇到同样问题的人。感谢大家的建议!
答案2
您很可能遇到了块大小难题:ext4 文件系统即使对最小的文件也会使用整个块。这意味着,如果您将一个小文件(例如 300 字节)从 512B 阻塞设备复制到 4K 阻塞设备,则使用的空间将增加四倍。
同样,目录使用的空间将增加四倍 - 因此深层文件夹结构将占用相当大的空间。
您可以做的事情:在新磁盘上创建一个大文件并为其分配一个循环设备,然后使用小块大小格式化它并使用它来存储小文件。