如何在Linux(Red Hat Linux)系统上快速创建大文件?
dd将完成这项工作,但是/dev/zero
当您需要一个数百GB的文件进行测试时,读取和写入驱动器可能需要很长时间......如果您需要重复这样做,那么时间真的会增加.
我不关心文件的内容,我只是想快速创建它.如何才能做到这一点?
使用稀疏文件不适用于此.我需要为文件分配磁盘空间.
dd
从其他答案是一个很好的解决方案,但它为此目的缓慢.在Linux(和其他POSIX系统)中,我们fallocate
使用所需的空间而不必实际写入它,可以与大多数现代的基于磁盘的文件系统一起使用,速度非常快:
例如:
fallocate -l 10G gentoo_root.img
这是一个常见问题 - 尤其是在当今的虚拟环境环境中.不幸的是,答案并不像人们想象的那样直截了当.
dd是明显的第一选择,但是dd本质上是一个副本,它强制你编写每个数据块(因此,初始化文件内容)......并且初始化占用了大量的I/O时间.(想要花更长的时间吗?使用/ dev/random而不是/ dev/zero!那么你将使用CPU以及I/O时间!)最后,dd是一个糟糕的选择(尽管基本上是VM"创建"GUI使用的默认值.例如:
dd if=/dev/zero of=./gentoo_root.img bs=4k iflag=fullblock,count_bytes count=10G
truncate是另一种选择 - 并且可能是最快的......但那是因为它创建了一个"稀疏文件".本质上,稀疏文件是具有大量相同数据的磁盘的一部分,并且底层文件系统通过不真正存储所有数据来"欺骗",而只是"假装"它就在那里.因此,当您使用truncate为您的VM创建一个20 GB的驱动器时,文件系统实际上并没有分配20 GB,但它会欺骗并说有20 GB的零,即使磁盘上只有一个磁道实际上(真的)可能正在使用中.例如:
truncate -s 10G gentoo_root.img
fallocate是最后-和最佳 - 选择与VM磁盘分配使用,因为它基本上是"储备"(或"分配"所有你正在寻找的空间,但它并没有刻意去写东西所以.当你使用fallocate来创建一个20 GB的虚拟驱动器空间时,你确实得到了一个20 GB的文件(不是"稀疏文件",你也不会为它写任何东西而烦恼 - 这意味着几乎任何东西都可以在那里 - 有点像一个全新的磁盘!)例如:
fallocate -l 10G gentoo_root.img
xfs_mkfile 10240m 10Gigfile
fallocate -l 10G 10Gigfile
mkfile 10240m 10Gigfile
prealloc 10Gigfile 10737418240
尝试mkfile
myfile作为替代dd
.使用该-n
选项可以记录大小,但在将数据写入它们之前不会分配磁盘块.如果没有该-n
选项,则空间为零填充,这意味着写入磁盘,这意味着需要时间.
mkfile源自SunOS,并不是随处可用.大多数Linux系统的xfs_mkfile
工作方式完全相同,不仅仅是在XFS文件系统上,尽管名称相同.它包含在xfsprogs(用于Debian/Ubuntu)或类似的命名包中.
大多数Linux系统也有fallocate
,它只适用于某些文件系统(如btrfs,ext4,ocfs2和xfs),但速度最快,因为它分配了所有文件空间(创建了无孔文件),但没有初始化任何文件系统它的.
truncate -s 10M output.file
将立即创建一个10 M文件(M代表1024*1024字节,MB代表1000*1000 - 与K,KB,G,GB相同......)
编辑:正如许多人所指出的,这不会在您的设备上物理分配文件.有了这个,您实际上可以创建一个任意大文件,无论设备上的可用空间如何,因为它创建了一个"稀疏"文件.
因此,在执行此操作时,您将推迟物理分配,直到访问该文件.如果要将此文件映射到内存,则可能无法获得预期的性能.
但这仍然是一个有用的命令
seek是你想要的文件大小,以字节为单位 - 1.
dd if=/dev/zero of=filename bs=1 count=1 seek=1048575
seek的示例是您想要的文件大小(以字节为单位)
#kilobytes
dd if=/dev/zero of=filename bs=1 count=0 seek=200K
#megabytes
dd if=/dev/zero of=filename bs=1 count=0 seek=200M
#gigabytes
dd if=/dev/zero of=filename bs=1 count=0 seek=200G
#terabytes
dd if=/dev/zero of=filename bs=1 count=0 seek=200T
从dd联机帮助页:
BLOCKS和BYTES之后可以跟随以下乘法后缀:c = 1,w = 2,b = 512,kB = 1000,K = 1024,MB = 1000*1000,M = 1024*1024,GB = 1000*1000*对于T,P,E,Z,Y,1000,G = 1024*1024*1024,依此类推.
我不太了解Linux,但是这里是我多年前在DC Share上伪造大文件的C代码.
#include < stdio.h >
#include < stdlib.h >
int main() {
int i;
FILE *fp;
fp=fopen("bigfakefile.txt","w");
for(i=0;i<(1024*1024);i++) {
fseek(fp,(1024*1024),SEEK_CUR);
fprintf(fp,"C");
}
}
制作1 GB文件:
dd if=/dev/zero of=filename bs=1G count=1
您也可以使用"是"命令.语法很简单:
#yes >> myfile
按"Ctrl + C"停止此操作,否则会占用所有可用空间.
要清理此文件,请运行:
#>myfile
将清理此文件.
我认为你不会比dd快得多.瓶颈是磁盘; 无论你怎么做,写入数百GB的数据都需要很长时间.
但是这可能适用于您的应用程序.如果您不关心文件的内容,那么创建一个内容是程序动态输出的"虚拟"文件怎么样?而不是打开()文件,使用popen()打开到外部程序的管道.外部程序在需要时生成数据.一旦管道打开,它就像一个普通文件,因为打开管道的程序可以fseek(),rewind()等.当你需要时,你需要使用pclose()而不是close()完成管道.
如果您的应用程序需要将文件设置为特定大小,则由外部程序来跟踪"文件"中的位置,并在达到"结束"时发送eof.