我希望实现Linux命令cp -Rf <src_dir>/* <dst_dir>
的行为,它复制了&#39; src_dir&#39;中的所有内容。进入&#39; dst_dir&#39;递归地
我在网上寻求帮助并得到了一些解决方案,但他们做了以下任何我不想做的事情:
使用rename(src_dir, dst_dir)
,它基本上会移动&#39;内容而不是副本。
我需要保留&#39; src_dir&#39;的内容。完整。
打开以阅读&#39; src_dir&#39;中的每个文件。 我想这样做,无需打开文件和阅读内容。
使用C而不使用system("cp -Rf <src_dir>/* <dst_dir>")
可以实现上述目标吗?
(从最初的评论中得知最初的lang令人困惑之后,编辑了原始问题)
答案 0 :(得分:2)
我当时想要实现linux系统命令的行为
1)cp将'src_dir'中的所有内容递归复制到'dst_dir',
使用C(并且没有linux系统调用)可以实现上述目标吗?
当然不是;请记住,system call是应用程序与Linux内核交互的主要方式:查看syscalls(2)以获取详尽的系统调用列表(您可能需要stat(2) ...) 。不要将系统调用与对C库system(3)函数的调用混淆(使用fork(2),execve(2),waitpid(2)等等。)
但是,您可能对nftw(3)感兴趣(当然,这是在多个系统调用之上实现的)。再看opendir(3)&amp; readdir(3)
如果不通过系统调用,您无法在文件系统上进行任何更改。
(问题已变为)
上述是否可以在不使用系统的情况下使用C实现(“cp -Rf / *”)?
是;您可以先使用nftw(3)扫描文件树(或使用readdir(3)等进行适当的播放...),然后检测要制作的目录(使用mkdir(2) ...);您将适当地制作目录并明确复制文件内容(例如使用stdio(3)函数或open(2),read(2),write(2),close(2)系统调用....)。请注意,open(2)(由fopen(3) ...调用)需要从文件中读取或写入任何内容(即使使用mmap(2) ...)当然,要复制文件,你需要打开它,打开它的新副本,读取它并在循环中写入副本,并关闭源文件和目标文件。但是,一旦完成复制,您应该关闭(源文件和目标文件)。顺便说一下,给定的process可能有数百(或数千)个打开的文件描述符(参见setrlimit(2) ...),而opendir(3)也会消耗一个。
(您打开的文件描述符的数量(大多数是目录,opendir(3))受文件树深度的限制,因此实际上可能很小,不到一百;并且使用聪明的使用nftw(3)缓存甚至可以避免这种情况)
BTW,cp
是GNU coreutils的一部分free software,因此您可以研究其源代码。您也可以使用strace(1)来了解cp
正在做什么。
阅读Advanced Linux Programming和Operating System : Three Easy Pieces(两者都可免费下载,PDF格式的章节)
无法使用单个system call复制一个文件的内容。你需要一个循环。但另请参阅我不推荐的Linux特定copy_file_range(2),更好地循环POSIX read(2)和write(2)