FUSEとarchivemountでアーカイブをマウントする

 archivemountというFUSEファイルシステムを利用すると、圧縮したままのtarballをファイルシステムとしてマウントすることができる。FUSEファイルシステムにはLinuxカーネルを介してアクセスするので、この方法でマウントすれば、どのアプリケーションからでもアーカイブのファイルを取り込んだり保存したりできることになる。つまり、ファイルをアーカイブに置いたまま、いつも使っているテキスト・エディターで開いたりイメージ・ビューアーで表示したり音楽プレーヤーで再生したりできるというわけだ。しかも、一部のアーカイブ形式については書き込みもでき、アーカイブにあるファイルを直接編集することも可能だ。

 archivemountはソースファイルとMakefileを1つずつ含むtarballの形で配布されている。主要なディストリビューション向けに簡単にインストールできるパッケージはないかと探してみたが、見当たらなかった。

 archivemountは実作業をlibarchiveに頼っているので、このライブラリーをインストールしておく必要がある。libarchiveのパッケージはUbuntu Gutsy用openSUSE用はあるが、Fedora用はない。コンパイルする場合は、あらかじめuudecodeをインストールしておく必要がある。今回の試用では、Fedora 8のsharutilsパッケージに含まれているものを使った。uudecodeをインストールしたら、libarchiveをビルドする。手順は標準的な「./configure; make; sudo make install」だ。

 ソースまたはパッケージからlibarchiveをインストールしたら、最後にarchivemountをビルドする。makeを実行するだけだ。できあがったバイナリーを/usr/local/binにコピーし、適切なアクセス許可を設定すればインストールは完了する。FUSEファイルシステムをマウントするユーザーは、どのLinuxディストリビューションでも、グループfuseに属していなければならない。そこで、archivemountコマンドのグループもfuseにしておくとよい。こうしておけば、このツールの利用には適切なアクセス許可が必要であることを思い出すだろう。手順は、以下のようになる。

# cp -av archivemount /usr/local/bin/
# chown root:fuse /usr/local/bin/archivemount
# chmod 550 /usr/local/bin/archivemount

 それでは、archivemountの使い方を説明しよう。まず、簡単なtarballを作って圧縮し、archivemountでマウントする。そして、lsコマンドでtarballに含まれているファイルのディレクトリー構造を表示し、catコマンドでアーカイブのファイルに直接アクセスしてみよう。

$ mkdir -p /tmp/archivetest
$ cd /tmp/archivetest
$ date >datefile1
$ date >datefile2
$ mkdir subA
$ date >subA/foobar
$ cd /tmp
$ tar czvf archivetest.tar.gz archivetest
$ mkdir testing
$ archivemount archivetest.tar.gz  testing
$ ls -l testing/archivetest/
-rw-r--r-- 0 root root 29 2008-04-02 21:04 datefile1
-rw-r--r-- 0 root root 29 2008-04-02 21:04 datefile2
drwxr-xr-x 0 root root  0 2008-04-02 21:04 subA
$ cat testing/archivetest/datefile2
Wed Apr  2 21:04:08 EST 2008

 次に、アーカイブにファイルを新規作成してから、アーカイブにあるファイルの一覧を表示してみた。下に示したのは、そのときの様子だ。ファイルを作成した直後に直接tarballに対して実行したtarコマンドでは、アーカイブに新しいファイルはできていない。実際の書き込みは、アーカイブがアンマウントされるときに行われるからだ。実際、「fusermount -u」コマンドのあとのtarコマンドでは、新しいファイルがアーカイブに追加されている。

$ date > testing/archivetest/new-file1
$ cat testing/archivetest/new-file1
Wed Apr  2 21:12:07 EST 2008
$ tar tzvf archivetest.tar.gz
drwxr-xr-x root/root         0 2008-04-02 21:04 archivetest/
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/datefile2
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/datefile1
drwxr-xr-x root/root         0 2008-04-02 21:04 archivetest/subA/
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/subA/foobar

$ fusermount -u testing
$ tar tzvf archivetest.tar.gz
drwxr-xr-x root/root         0 2008-04-02 21:04 archivetest/
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/datefile2
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/datefile1
drwxr-xr-x root/root         0 2008-04-02 21:04 archivetest/subA/
-rw-r--r-- root/root        29 2008-04-02 21:04 archivetest/subA/foobar
-rw-rw-r-- ben/ben          29 2008-04-02 21:12 archivetest/new-file1

 FUSEファイルシステムのアンマウントでは、処理が完了する前にプロンプトに戻ってしまうことがある。その場合、FUSEファイルシステムの処理に異常が発生しても、その異常を報告する場がないことになる。archivemountの解説書にアンマウント中にアーカイブへの書き込みで異常が発生してもarchivemount側でデータ喪失の対策をとることはできないという警告があるのは、そのためだ。しかし、これはその文言ほどには深刻な問題ではない。というのは、読み込みしかできないtar.bzアーカイブをマウントし、このアーカイブにファイルを新規作成したり既存ファイルに書き込んだりしてみたが、いずれも"Read-only filesystem"というメッセージを表示して直ちにエラー終了したからだ。

 そこで、データ喪失を引き起こすため、libarchiveが読み込みしかサポートしていない形式のアーカイブを作って実験してみた。まず、archivetestディレクトリーを圧縮してarchivetest.zipを作りマウントし、ファイルを新規作成し読み込んでみた。ここまでは問題はない。次に、zipファイルをアンマウントすると、archivemountのREADMEファイルで警告されているように、エラー・メッセージは表示されなかった。しかし、「unzip -l」でzipファイルの一覧を見ることはできない。archivetest.zipが非圧縮のPOSIX tarアーカイブになっているからだ。実際、「tar tvf」で一覧を表示すると、archivetest.zip tarアーカイブには先ほど作成した新規ファイルも含まれていた。さらに、archivetest.zip.origというファイルもあり、これはzip形式で、archivemountでマウントしたときの状態と同じだった。

 このように、archivemountの使用でデータを失うケースは稀だ。読み込み専用のアーカイブ・ファイルをマウントしても問題なし。libarchiveが読み込みしかできないアーカイブ形式にしても問題は発生しなかった。もっとも、この場合、アーカイブの形式が勝手に変更されてしまうが。留意すべき状況はもう一つある。archivemountはアンマウントの際に新しいアーカイブを作るため、アーカイブを保存する際にディスク領域が不足するとデータが失われる可能性があるのだ。したがって、十分な領域を確保しておく必要がある

 次に、archivemountのパフォーマンスを見てみよう。使ったのは、bonnie++ファイルシステム・ベンチマークでバージョンは1.03。archivemountはファイルシステムをアンマウントするときまで実際のアーカイブを更新しないため、マウントしたアーカイブへのアクセスと書き込みのパフォーマンスは高いはずだ。下に、archivemountを介して/tmpに置いたアーカイブ・ファイルにアクセスした場合と/tmpのサブディレクトリーに直接アクセスした場合の結果を示す。archivemountの場合のシークの数字は、平均して直接アクセスの場合の半分だった。また、書き換えのパフォーマンスは直接アクセスの70%程度と見られる。bonnie++の解説書には書き換えテストでは一群のデータを読み込んで変更し書き込むとあり、これにはシークが必要なため、シーク・パフォーマンスの低いarchivemountの数字が低く出るのだろう。

$ cd /tmp
$ mkdir empty
$ ls -d empty | cpio -ov > empty.cpio
$ mkdir empty-mounted
$ archivemount empty.cpio empty-mounted
$ mkdir bonnie-test
$ /usr/sbin/bonnie++ -d /tmp/bonnie-test
Version  1.03       ------Sequential Output------ --Sequential Input- --Random-
                    -Per Chr- --Block-- -Rewrite- -Per Chr- --Block-- --Seeks--
Machine        Size K/sec %CP K/sec %CP K/sec %CP K/sec %CP K/sec %CP  /sec %CP
v8tsrv           2G 14424  25 14726   4 13930   6 28502  49 52581  17  8322 123

$ /usr/sbin/bonnie++ -d /tmp/empty-mounted
Version  1.03       ------Sequential Output------ --Sequential Input- --Random-
                    -Per Chr- --Block-- -Rewrite- -Per Chr- --Block-- --Seeks--
Machine        Size K/sec %CP K/sec %CP K/sec %CP K/sec %CP K/sec %CP  /sec %CP
v8tsrv           2G 12016  19 12918   7  9766   6 27543  40 52937   6  4457  24

 tarballにあるファイルを使うときも、archivemountを利用すれば、通常どおりの操作を実行するだけで済む。たとえば、tarball中のファイルをEmacsに読み込むには、tarballをマウントして、そのファイルシステム上でEmacsを通常どおりに実行すればよい。アーカイブを/tmpに展開する必要はない。上に示したbonnie++ベンチマークによると、archivemountファイルシステムを利用しても、アプリケーションのパフォーマンスはさほどには低下しない。

Ben Martin 10年以上にわたってファイルシステムに携わっている。博士課程を修了し、現在、libferris、ファイルシステム、検索ソリューションを中心にコンサルティングをしている。

Linux.com 原文(2008年4月16日)