首页 > 代码库 > du与df区别以及出现较大差距时解决方法
du与df区别以及出现较大差距时解决方法
在linux下查看磁盘使用率,最常用到的是df和du,但是有时就会发现du 和df出来的结果并不完全相同,有时候还有很大差距
1. 两个命令的解释
du --disk usage
df -- disk free
2.du 和df 工作原理
2.1 du工作原理
du命令会对待统计的文件逐个调用fstat这个系统调用,来获取文件大小。它的数据是基于文件获取的,有很大的灵活性。不一定非
要针对一个分区,可以跨多个分区操作,如果针对的目录中文件的个数较多,du的速度就会很慢了。
2.2 df 工作原理
df使用的是statfs这个系统调用,直接读取分区的超级块信息获取分区使用事情,它的数据是基于分区元数据的,所以只能针对整个分区。
正因为df读取的是超级块,所以运行速度不受文件数量的影响。
3.du和df不一致情况模拟
常见的df和du不一致就是文件删除的问题。当一个文件被删除后,在文件系统目录中已经不存在了,所以du就不再统计该文件。但是如果
此时还有运行的程序持有这个已经被删除的文件的句柄,那么这个文件就不会真正的在磁盘中被删除,分区的超级块中信息也就不会更改,所以
df还会统计这个已经被删除了的文件。
(1)当前根分区的使用情况
[root@vrh1 ~]# df -h /Filesystem Size Used Avail Use% Mounted on/dev/mapper/VolGroup00-LogVol00 28G 14G 12G 54% /
(2)创建一个1G的文件
[root@vrh1 ~]# dd if=/dev/zero of=test.log bs=1024k count=10241024+0 records in1024+0 records out1073741824 bytes (1.1 GB) copied, 14.2389 seconds, 75.4 MB/s
(3)此时根分区的使用情况
df查询结果
[root@vrh1 ~]# df -hFilesystem Size Used Avail Use% Mounted on/dev/mapper/VolGroup00-LogVol00 28G 15G 11G 58% //dev/sda1 99M 13M 82M 14% /boottmpfs 1006M 0 1006M 0% /dev/shm
du查询结果
[root@vrh1 ~]# pwd/root[root@vrh1 ~]# du -sh1.1G .
此时的二者的查询结果基本相同
(4)模拟一个进程打开这个文件,然后删除这个文件
[root@vrh1 ~]# tail -f test.log &[1] 2880[root@vrh1 ~]# [root@vrh1 ~]# rm -fr test.log
(5)再次对比du和df 的结果
首先确认有进程持有test.log的句柄
[root@vrh1 ~]# lsof | grep test.logtail 2880 root 3r REG 253,0 1073741824 2254399 /root/test.log (deleted) #注意在这里可以看到这个文件已经被删除了
[root@vrh1 ~]# df -hFilesystem Size Used Avail Use% Mounted on/dev/mapper/VolGroup00-LogVol00 28G 15G 11G 58% //dev/sda1 99M 13M 82M 14% /boottmpfs 1006M 0 1006M 0% /dev/shm[root@vrh1 ~]# du -sh888K .
可以看到df没有发生变化,而du则不再统计这个被删除了的文件
(6)停止模拟进程,再次对比du和df结果
[root@vrh1 ~]# kill -9 2880[root@vrh1 ~]# [1]+ Killed tail -f test.log[root@vrh1 ~]# lsof | grep test.log[root@vrh1 ~]#
[root@vrh1 ~]# df -hFilesystem Size Used Avail Use% Mounted on/dev/mapper/VolGroup00-LogVol00 28G 14G 12G 54% //dev/sda1 99M 13M 82M 14% /boottmpfs 1006M 0 1006M 0% /dev/shm[root@vrh1 ~]# du -sh888K
此时test.log文件已经没有进程占有它了,也就从磁盘上删除了,分区的超级块信息已经更改,df也就显示正常了
4.日常使用中需要注意的地方
(1)当出现du和df有很大差距的时候,考虑是否有删除文件未完成造成的,方法是lsof命令,然后停止相关进程即可(即使用lsof中文件末尾标明deleted的)
(2)可以使用清空文件的方式来替代删除文件,方式是:echo > test.log
(3)对于经常发生删除问题的日志文件,以改名、清空、删除的顺序来操作
(4)除了 rm 外,有些命令会间接的删除文件,如gzip命令完成后会删除原来的文件,为了避免删除问题,压缩前先确认没有进程打开该文件
(5)查看已经被 rm 掉,但是仍然被进程占用的文件的方法 :lsof | grep deleted
参考链接:http://blog.csdn.net/smstong/article/details/8715650
注:虽然基本照搬原链接内容,但是自己在实际测试中,还是有些额外的收获和体会的。
du与df区别以及出现较大差距时解决方法