从 C 可执行文件增加 ext4 文件系统 linux 中文件大小而不在文件中创建漏洞的最快方法是什么?
What is the fastest way to increase the size of a file in linux on a ext4 filesystem from a C executable without creating holes in the file?
据我所知,增加文件大小的最快方法是使用 ftruncate() 或 lseek() 到所需大小并写入一个字节。在这种情况下,这不符合我的需要,因为文件中产生的漏洞不会在文件系统中保留 space。
是使用 calloc() 和 write() 的最佳替代方案吗?
int increase_file_size_(int fd, int pages) {
int pagesize = 4096;
void* data = calloc(pagesize, 1);
for(int i = 0; i < pages; ++i) {
// In a real world program this would handle partial writes and interruptions
if (write(fd, data, pagesize) != pagesize) {
return -1;
}
return 0;
}
也许使用 writev 可以使这变得更快。
下一个版本应该会更快,因为 calloc 必须零初始化更少的内存,更多的数据适合 CPU 缓存。
int increase_file_size_(int fd, int pages) {
int pagesize = 4096/16;
void* data = calloc(pagesize, 1);
struct iovec iov[16];
for(int i = 0; i < 16; ++i) {
iov[i].iov_base = data;
iov[i].iov_len = pagesize ;
}
for(int i = 0; i < pages; ++i) {
// In a real world program this would handle partial writes and interruptions
if (writev(fd, data, pagesize) != pagesize * 16) {
return -1;
}
return 0;
}
我可以试验看看哪种方法和哪种页面大小更快。但是,是否有另一种方法被认为是扩展文件的正常最佳实践?我应该对其他方法进行性能测试吗?
谢谢。
看看 posix_fallocate()
函数:它为文件保留 space 而不必写入任何数据来占用 space。分配的 space 有点像一个稀疏文件,即使你没有明确地向它写入任何内容,你也可以从中读取,但与稀疏文件不同的是,它实际上减少了空闲 space 在文件系统中。您可以放心,稍后可以写入文件的该区域,而无需 space.
中的 运行
请注意 posix_fallocate()
似乎无法保证分配的 space 的 内容 如果您在写入之前阅读它。我认为 Linux 实现将 return 所有零字节,类似于稀疏文件,但您可能不应该依赖它。在你写真正的东西之前把它当作垃圾。
另请注意,并非所有文件系统驱动程序都支持 posix_fallocate()
利用的预分配功能,我认为如果预分配不支持,它会退回到实际将数据写入文件(正常方式)不支持。典型的 Linux 文件系统,如 ext4 和 XFS 是可以的,但如果你在 FAT 或 NTFS 之类的系统上尝试,你的程序可能会在 I/O 上阻塞一段时间。
据我所知,增加文件大小的最快方法是使用 ftruncate() 或 lseek() 到所需大小并写入一个字节。在这种情况下,这不符合我的需要,因为文件中产生的漏洞不会在文件系统中保留 space。
是使用 calloc() 和 write() 的最佳替代方案吗?
int increase_file_size_(int fd, int pages) {
int pagesize = 4096;
void* data = calloc(pagesize, 1);
for(int i = 0; i < pages; ++i) {
// In a real world program this would handle partial writes and interruptions
if (write(fd, data, pagesize) != pagesize) {
return -1;
}
return 0;
}
也许使用 writev 可以使这变得更快。 下一个版本应该会更快,因为 calloc 必须零初始化更少的内存,更多的数据适合 CPU 缓存。
int increase_file_size_(int fd, int pages) {
int pagesize = 4096/16;
void* data = calloc(pagesize, 1);
struct iovec iov[16];
for(int i = 0; i < 16; ++i) {
iov[i].iov_base = data;
iov[i].iov_len = pagesize ;
}
for(int i = 0; i < pages; ++i) {
// In a real world program this would handle partial writes and interruptions
if (writev(fd, data, pagesize) != pagesize * 16) {
return -1;
}
return 0;
}
我可以试验看看哪种方法和哪种页面大小更快。但是,是否有另一种方法被认为是扩展文件的正常最佳实践?我应该对其他方法进行性能测试吗?
谢谢。
看看 posix_fallocate()
函数:它为文件保留 space 而不必写入任何数据来占用 space。分配的 space 有点像一个稀疏文件,即使你没有明确地向它写入任何内容,你也可以从中读取,但与稀疏文件不同的是,它实际上减少了空闲 space 在文件系统中。您可以放心,稍后可以写入文件的该区域,而无需 space.
请注意 posix_fallocate()
似乎无法保证分配的 space 的 内容 如果您在写入之前阅读它。我认为 Linux 实现将 return 所有零字节,类似于稀疏文件,但您可能不应该依赖它。在你写真正的东西之前把它当作垃圾。
另请注意,并非所有文件系统驱动程序都支持 posix_fallocate()
利用的预分配功能,我认为如果预分配不支持,它会退回到实际将数据写入文件(正常方式)不支持。典型的 Linux 文件系统,如 ext4 和 XFS 是可以的,但如果你在 FAT 或 NTFS 之类的系统上尝试,你的程序可能会在 I/O 上阻塞一段时间。