概要
dfとduコマンドのディスク使用量が一致しない
問題1:
ディスク容量の空きがなく、ディレクトリが作成できない。
mkdir: cannot create directory ‘{PATH}’: No space left on device
script returned exit code 1
状況把握
df コマンドでファイルシステムのディスク容量の使用状況を表示する / Use the df command to display the disk space usage of the file system
$ df -h
Filesystem Size Used Avail Use% Mounted on
/dev/mapper/{root_name} 26G 25G 0 100% /
devtmpfs 3.9G 0 3.9G 0% /dev
tmpfs 3.9G 0 3.9G 0% /dev/shm
tmpfs 3.9G 388M 3.5G 10% /run
tmpfs 3.9G 0 3.9G 0% /sys/fs/cgroup
/dev/sda1 302M 146M 137M 52% /boot
none 3.9G 1.1G 2.8G 28% /tmp
tmpfs 782M 0 782M 0% /run/user/21223
tmpfs 782M 0 782M 0% /run/user/15923
tmpfs 782M 0 782M 0% /run/user/13365
tmpfs 782M 0 782M 0% /run/user/0
used > 25GB
du コマンドでファイルのディスク使用量を調べる。 / Use the du command to check the disk usage of the file.
$ du -shx / 2>/dev/null
18G /
> df とdu の結果に大きな差分が生じている。
df: 25GB
du: 18GB
"/" 配下の実ファイルの容量は計18GBのはずなのに、ファイルシステムでは、計25GBの容量を割り当てている状態と言える。
lsof で開いているファイルのサイズを調べる。/ Find out the size of the file you are opening with lsof.
$ lsof / | head -3
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
lsof 4705 {username} cwd DIR 253,0 4096 524879 /home/{username}
lsof 4705 {username} rtd DIR 253,0 4096 2 /
SIZE/OFF のカラム(左から7番目)が開いているファイルのサイズを表す。上記であれば、約4GB.
lsofの結果をソートして一番サイズが大きい順に表示する。/ Sort the lsof results and display them in order of the largest size.
$ lsof / | sort -k7 -nr | head -1
java 35416 {username} 2w REG 253,0 6668955648 1471501
{filepath}/stdout (deleted)
およそ6.6GBの容量が削除されているはずのstdoutファイルに割り当てられていたようだ。これは、df - du の差の値(25GB - 18GB = 7GB) ともほぼ一致する。
ファイルを消したがrsyslogdが掴んでいて、ディスク容量を圧迫していたようである。
ファイルが存在しない確認と、プロセスIDを調べる。/ Confirm that the file does not exist and check the process ID.
$ ls
{filepath}/stdout
ls: cannot access
{filepath}/stdout: No such file or directory
$ ps -aux | grep extend
{username} 5874 0.0 0.0 112704 968 pts/0 S+ 11:04 0:00 grep --color=auto extend
{username} 35416 1.3 12.8 5971960 1031064 ? Sl Feb22 569:20 /usr/bin/java -Dsun.misc.URLClassPath.disableJarChecking=true -jar {filepath}/receiver/sample.jar
対処法 / How to deal
そのプロセスをkillする。
$ kill -9 35416
結果 / Result
$ df -h
Filesystem Size Used Avail Use% Mounted on
/dev/mapper/{root_name} 26G 18G 6.3G 74% /
devtmpfs 3.9G 0 3.9G 0% /dev
tmpfs 3.9G 0 3.9G 0% /dev/shm
tmpfs 3.9G 388M 3.5G 10% /run
tmpfs 3.9G 0 3.9G 0% /sys/fs/cgroup
/dev/sda1 302M 146M 137M 52% /boot
none 3.9G 1.1G 2.8G 28% /tmp
tmpfs 782M 0 782M 0% /run/user/21223
tmpfs 782M 0 782M 0% /run/user/15923
tmpfs 782M 0 782M 0% /run/user/13365
ディスクの空き容量が増えた。めでたしめでたし。
参考:
https://www.greptips.com/posts/1158/
https://www.unknownengineer.net/entry/2017/06/11/231301
問題2
と思ったらまだ別のエラーにより、mkdir ができない。
mkdir: cannot create directory
‘{file_path}/backup’: No space left on device
script returned exit code 1
ディスク容量に空きはある。
$ df -h
Filesystem Size Used Avail Use% Mounted on
/dev/mapper/{root_name} 26G 18G 6.2G 75% /
devtmpfs 3.9G 0 3.9G 0% /dev
tmpfs 3.9G 0 3.9G 0% /dev/shm
tmpfs 3.9G 396M 3.5G 11% /run
tmpfs 3.9G 0 3.9G 0% /sys/fs/cgroup
/dev/sda1 302M 146M 137M 52% /boot
none 3.9G 1.1G 2.8G 28% /tmp
tmpfs 782M 0 782M 0% /run/user/21223
tmpfs 782M 0 782M 0% /run/user/13365
tmpfs 782M 0 782M 0% /run/user/15923
しかし、inodeの容量が埋まっているみたい
※inode: ファイルやディレクトリの、所有者や更新日時、ファイルサイズなどの属性情報が書かれているデータ
$ df -i
Filesystem Inodes IUsed IFree IUse% Mounted on
/dev/mapper/{root_name} 1671072 1671072 0 100% /
devtmpfs 997144 362 996782 1% /dev
tmpfs 1000169 1 1000168 1% /dev/shm
tmpfs 1000169 1363 998806 1% /run
tmpfs 1000169 16 1000153 1% /sys/fs/cgroup
/dev/sda1 81920 341 81579 1% /boot
none 1000169 87 1000082 1% /tmp
tmpfs 1000169 1 1000168 1% /run/user/21223
tmpfs 1000169 1 1000168 1% /run/user/13365
解決法
下記のコマンドで、大量の小さいファイルがどこかに存在していないか1階層ずつ調べる。 > ファイルを削除する
今回の場合、/var/log/td-agent/buffer 配下に140万の空ファイルが存在していた。
echo c"==== `pwd` ====" ; for i in `ls -1`;do echo -n "## $i ### " ; echo "(`find /var/log/td-agent/$i -type f |wc -l`)" ;done | sort -r 2>/dev/null