R.A. Epigonos et al.

[debian] ファイル群に対して同一ファイルのハードリンク化を行うソフトウェアの比較(rdfind,hardlink)

すでにハードリンクが含まれるディレクトリの中にハードリンクでない同じ内容を持つファイルが複数含まれる。この時、すべての同じ内容のファイルはハードリンク化されるかテスト

テスト環境の作成

テストパーティションを作成してマウントして、以降のテストを行うユーザで書き込み可能にしておく。

# dd if=/dev/zero of=./vdz0 bs=1024 count=10K
# dd if=/dev/zero of=./vdz1 bs=1024 count=10K
# mkfs.ext4 ./vdz0
# mkfs.ext4 ./vdz1
# mkdir -p /mnt/hardlink_test/vdz0
# mkdir -p /mnt/hardlink_test/vdz1
# mount ./vdz0 /mnt/hardlink_test/vdz0
# mount ./vdz1 /mnt/hardlink_test/vdz1
# chown ****:**** /mnt/hardlink_test/vdz0
# chown ****:**** /mnt/hardlink_test/vdz1

テストを実行するユーザでテストファイルを作成。以下のファイルを作成。相対ファイルパスにcon0が含まれるファイルの内容は同じ。ino0が含まれるファイルのinodeは同じ。

$ find /mnt/hardlink_test/vdz0/hardlink_test_dir /mnt/hardlink_test/vdz1/hardlink_test_dir -type f -printf '%D %i %n %P\n' | sort -k1,1n -k4,4
1792 13 2 con0/dev0/ino0/name0
1792 13 2 con0/dev0/ino0/name1
1792 15 2 con0/dev0/ino2/name0
1792 15 2 con0/dev0/ino2/name1
1792 14 2 con1/dev0/ino1/name0
1792 14 2 con1/dev0/ino1/name1
1792 16 2 con1/dev0/ino3/name0
1792 16 2 con1/dev0/ino3/name1
1793 13 2 con0/dev1/ino0/name0
1793 13 2 con0/dev1/ino0/name1
1793 15 2 con0/dev1/ino2/name0
1793 15 2 con0/dev1/ino2/name1
1793 14 2 con1/dev1/ino1/name0
1793 14 2 con1/dev1/ino1/name1
1793 16 2 con1/dev1/ino3/name0
1793 16 2 con1/dev1/ino3/name1

hardlink

hardlink を使うと期待通りの結果が得られる。すなわち、同じデバイスに含まれる同一内容を持つファイルは全て一つのiノード番号を持つようになった。

$ find /mnt/hardlink_test/vdz0/hardlink_test_dir /mnt/hardlink_test/vdz1/hardlink_test_dir -type f -printf '%D %i %n %P\n' | sort -k1,1n -k4,4
1792 13 2 con0/dev0/ino0/name0
1792 13 2 con0/dev0/ino0/name1
1792 15 2 con0/dev0/ino2/name0
1792 15 2 con0/dev0/ino2/name1
1792 14 2 con1/dev0/ino1/name0
1792 14 2 con1/dev0/ino1/name1
1792 16 2 con1/dev0/ino3/name0
1792 16 2 con1/dev0/ino3/name1
1793 13 2 con0/dev1/ino0/name0
1793 13 2 con0/dev1/ino0/name1
1793 15 2 con0/dev1/ino2/name0
1793 15 2 con0/dev1/ino2/name1
1793 14 2 con1/dev1/ino1/name0
1793 14 2 con1/dev1/ino1/name1
1793 16 2 con1/dev1/ino3/name0
1793 16 2 con1/dev1/ino3/name1
$ hardlink --ignore-time /mnt/hardlink_test
Mode:     real
Files:    16
Linked:   8 files
Compared: 0 xattrs
Compared: 8 files
Saved:    20 bytes
Duration: 0.00 seconds
$ echo $?
0
$ find /mnt/hardlink_test/vdz0/hardlink_test_dir /mnt/hardlink_test/vdz1/hardlink_test_dir -type f -printf '%D %i %n %P\n' | sort -k1,1n -k4,4
1792 13 4 con0/dev0/ino0/name0
1792 13 4 con0/dev0/ino0/name1
1792 13 4 con0/dev0/ino2/name0
1792 13 4 con0/dev0/ino2/name1
1792 14 4 con1/dev0/ino1/name0
1792 14 4 con1/dev0/ino1/name1
1792 14 4 con1/dev0/ino3/name0
1792 14 4 con1/dev0/ino3/name1
1793 13 4 con0/dev1/ino0/name0
1793 13 4 con0/dev1/ino0/name1
1793 13 4 con0/dev1/ino2/name0
1793 13 4 con0/dev1/ino2/name1
1793 14 4 con1/dev1/ino1/name0
1793 14 4 con1/dev1/ino1/name1
1793 14 4 con1/dev1/ino3/name0
1793 14 4 con1/dev1/ino3/name1

rdfind

rdfind を使うと期待通りの結果が得られない。rdfind の出力はハードリンクの作成に失敗したことを伝えているが、戻り値はゼロで失敗を判断しづらい。また、ハードリンクの作成に失敗したファイルは結果的に削除される事になる。さらに、rdfind の出力には現れないものの、同一の内容を持つファイルがハードリンクになっていない場合がある。

$ find /mnt/hardlink_test/vdz0/hardlink_test_dir /mnt/hardlink_test/vdz1/hardlink_test_dir -type f -printf '%D %i %n %P\n' | sort -k1,1n -k4,4
1792 13 2 con0/dev0/ino0/name0
1792 13 2 con0/dev0/ino0/name1
1792 15 2 con0/dev0/ino2/name0
1792 15 2 con0/dev0/ino2/name1
1792 14 2 con1/dev0/ino1/name0
1792 14 2 con1/dev0/ino1/name1
1792 16 2 con1/dev0/ino3/name0
1792 16 2 con1/dev0/ino3/name1
1793 13 2 con0/dev1/ino0/name0
1793 13 2 con0/dev1/ino0/name1
1793 15 2 con0/dev1/ino2/name0
1793 15 2 con0/dev1/ino2/name1
1793 14 2 con1/dev1/ino1/name0
1793 14 2 con1/dev1/ino1/name1
1793 16 2 con1/dev1/ino3/name0
1793 16 2 con1/dev1/ino3/name1
$ rdfind -makehardlinks true /mnt/hardlink_test
Now scanning "/mnt/hardlink_test", found 16 files.
Now have 16 files in total.
Removed 8 files due to nonunique device and inode.
Now removing files with zero size from list...removed 0 files
Total size is 40 bytes or 40 b
Now sorting on size:removed 0 files due to unique sizes from list.8 files left.
Now eliminating candidates based on first bytes:removed 0 files from list.8 files left.
Now eliminating candidates based on last bytes:removed 0 files from list.8 files left.
Now eliminating candidates based on md5 checksum:removed 0 files from list.8 files left.
It seems like you have 8 files that are not unique
Totally, 30 b can be reduced.
Now making results file results.txt
Now making hard links.
failed to make hardlink /mnt/hardlink_test/vdz1/hardlink_test_dir/con0/dev1/ino2/name0 to /mnt/hardlink_test/vdz0/hardlink_test_dir/con0/dev0/ino2/name0
Rdutil.cc: Failed to apply function f on it.
failed to make hardlink /mnt/hardlink_test/vdz1/hardlink_test_dir/con0/dev1/ino0/name0 to /mnt/hardlink_test/vdz0/hardlink_test_dir/con0/dev0/ino2/name0
Rdutil.cc: Failed to apply function f on it.
failed to make hardlink /mnt/hardlink_test/vdz1/hardlink_test_dir/con1/dev1/ino3/name0 to /mnt/hardlink_test/vdz0/hardlink_test_dir/con1/dev0/ino3/name0
Rdutil.cc: Failed to apply function f on it.
failed to make hardlink /mnt/hardlink_test/vdz1/hardlink_test_dir/con1/dev1/ino1/name0 to /mnt/hardlink_test/vdz0/hardlink_test_dir/con1/dev0/ino3/name0
Rdutil.cc: Failed to apply function f on it.
Making 2 links.
+ echo $?
0
$ find /mnt/hardlink_test/vdz0/hardlink_test_dir /mnt/hardlink_test/vdz1/hardlink_test_dir -type f -printf '%D %i %n %P\n' | sort -k1,1n -k4,4
1792 15 3 con0/dev0/ino0/name0
1792 13 1 con0/dev0/ino0/name1
1792 15 3 con0/dev0/ino2/name0
1792 15 3 con0/dev0/ino2/name1
1792 16 3 con1/dev0/ino1/name0
1792 14 1 con1/dev0/ino1/name1
1792 16 3 con1/dev0/ino3/name0
1792 16 3 con1/dev0/ino3/name1
1793 13 1 con0/dev1/ino0/name1
1793 15 1 con0/dev1/ino2/name1
1793 14 1 con1/dev1/ino1/name1
1793 16 1 con1/dev1/ino3/name1

リファレンス

  1. Debian -- sid の hardlink パッケージに関する詳細
  2. Debian -- sid の rdfind パッケージに関する詳細

ソーシャルブックマーク

  1. はてなブックマーク
  2. Google Bookmarks
  3. del.icio.us

ChangeLog

  1. Posted: 2008-04-18T12:27:29+09:00
  2. Modified: 2008-04-18T12:27:29+09:00
  3. Generated: 2023-08-27T23:09:14+09:00