2012-04-28 603 views
2

我遇到了以下问题。当我在Linux中使用cp命令将文件A复制到文件B时,这些文件的大小是不同的,例如, A是6.4M,而B是7.0M。即使我在同一目录中执行此操作(以避免不同驱动器上的块大小不同),也会发生这种情况。使用cp时文件大小发生变化

这是怎么回事?如何避免?它会改变文件吗?

另外还有一些奇怪的行为。如果我将文件A应用于文件B并尝试立即检查B的大小,则它给出0或例如6.2M,一段时间后B的大小为7.0M并且恒定。是否有可能捕获一些中间复制结果?那为什么这么慢?

+4

图片或它没有发生。 – 2012-04-28 15:39:40

+3

这可能会发生在稀疏文件中,具体取决于您如何确定“文件大小”。 – Mat 2012-04-28 15:40:24

+0

那么它会更改文件(其内部结构)?它如何影响二进制文件? – user938720 2012-04-28 15:42:23

回答

4

假设coreutilsducp

cp复制一个文件时,它尝试使用启发式来保留其“稀疏性”。

默认情况下,稀疏的SOURCE文件被粗糙的启发式检测到,并且相应的DEST文件也变得稀疏。

因此,如果试探失败,cp将创建一个纯文本文件,无孔。在这种情况下,副本的磁盘使用量将大于源–的磁盘使用量,但明显的文件大小应该相同,并且内容应该相同(尝试cmp)。

使用stat可以查看文件的外观尺寸和磁盘使用情况(以及更多信息)。

$ dd if=/dev/zero of=./sparse bs=1 count=1 seek=10240000 
1+0 records in 
1+0 records out 
1 byte (1 B) copied, 1.4101e-05 s, 70.9 kB/s 
$ cp sparse copy1 
$ cp --sparse=never sparse copy2 
$ ll 
-rw-r--r-- 1 me users 10240001 Apr 28 17:59 copy1 
-rw-r--r-- 1 me users 10240001 Apr 28 18:00 copy2 
-rw-r--r-- 1 me users 10240001 Apr 28 17:59 sparse 
$ du sparse copy* 
4 sparse 
4 copy1 
10004 copy2 
$ stat sparse copy* 
    File: `sparse' 
    Size: 10240001 Blocks: 8   IO Block: 4096 regular file 
... 
    File: `copy1' 
    Size: 10240001 Blocks: 8   IO Block: 4096 regular file 
... 
    File: `copy2' 
    Size: 10240001 Blocks: 20008  IO Block: 4096 regular file 
$ cmp sparse copy1 && echo identical 
identical 
$ cmp sparse copy2 && echo identical 
identical 
1

有一定数量的臭虫与FIEMAP:

http://lwn.net/Articles/429349/

http://lkml.indiana.edu/hypermail/linux/kernel/0906.1/00436.html

http://www.spinics.net/lists/linux-ext4/msg24337.html

所以我怀疑马车CP Coreutils的任何试图使用FIEMAP和内核中的buggy文件系统无法正确处理FIEMAP。升级你的内核和coreutils软件包。

+0

感谢您的评论。我只是在XFS格式的文件系统上使用cp时遇到了这种情况,而在ext4上工作正常。时间来重新格式化很多文件系统... – 2013-12-15 17:28:55

相关问题