复制文件而不使用 C 中的标准库函数
Posted
技术标签:
【中文标题】复制文件而不使用 C 中的标准库函数【英文标题】:Copy file without using standard library function in C 【发布时间】:2022-01-22 11:18:13 【问题描述】:如何在不使用 Linux 中的标准 C 库函数的情况下复制文件?换句话说,我想直接用系统调用复制一个文件。有可能吗?
【问题讨论】:
是的,这是可能的。打开文件读取和写入副本.. 读取和写入。如果不允许使用fopen
等,请使用非标准的低级平台特定功能。
当然。您正在为什么操作系统编程?
对不起,我没有提到它。我想在 Linux 64 上做。
然后使用open
、read
、write
和close
。它们都在man
页面的2
部分中。
这几乎和fopen
/fread
/fwrite
/fclose
一样简单。 (实际上要简单一点:f
的输入减少了四个,read
和 write
的参数也减少了一个!:-))
【参考方案1】:
文件直接与系统调用。有可能吗?
在伪代码中,使用sendfile
:
int in = open("input", ...);
fstatat(in, &stat);
int out = open("output", ...);
sendfile(in, out, NULL, stat.st_size);
【讨论】:
你应该循环调用sendfile
。它可能不会发送所有字节,在这种情况下需要重新启动。
另外,请注意手册页警告 - "Other Unix systems implement sendfile() with different semantics and prototypes. It should not be used in portable programs."
也就是说,如果您不需要它是可移植的,sendfile()
非常快速和高效,因为传输是在内核空间中完成的.
有趣的事实:在 Linux 5.3 及更高版本上,copy_file_range(2)
需要两个 FD、两个偏移量和一个长度。但是像 sendfile 一样,它仍然可以在复制的字节数少于请求的情况下提前返回,因此仍应在循环中调用。 (系统调用自 4.5 以来就存在,但在 5.3 之前,如果文件不在同一个 FS 上,它将返回 -EXDEV。我认为它最初是为了像 cp --reflink=auto
那样在 btrfs / zfs 上进行 CoW 重新链接,但现在可以回退到内核副本。) sendfile 做 CoW 吗?以上是关于复制文件而不使用 C 中的标准库函数的主要内容,如果未能解决你的问题,请参考以下文章