これは CVF-FAT ファイルシステム拡張の主要な資料です。   1998年11月18日


目次：

1. CVF-FAT の概念
2. 制限
3. マウントオプション
4. CVF-FAT インターフェースの概要
5. CVF モジュール

---------------------------------------------------------------------

1. CVF-FAT の概念
---------------------------------------------------------------------

CVF-FAT は FAT ファイルシステムの拡張で、FAT パーティションにおける
Compressed Volume Files の汎用的なインターフェースを提供します。一般的
な CVF ソフトウェアは、例えば、Microsoft の Doublespace/Drivespace や
Stac の Stacker です。CVF-FATインターフェースの使用は、圧縮および展開
を動的に行う低レベルディスクアクセスを扱うモジュールをロードすることで
できます。FAT ファイルシステムにある CVF-FAT 以外のファイルへのアクセ
スは、今までどおり FAT, MSDOS, VFAT あるいは UMSDOS ドライバが行います。

CVF アクセスは、FAT ドライバからロード可能な CVF フォーマット固有のモ
ジュールへ特定の低レベルルーチンをリダイレクトすることで行えます。この
モジュールは CVF に対して圧縮や展開のような特殊な処理を暗黙裡に行い、
FAT ドライバからは CVF が通常の FAT ファイルシステムであるかのように見
えないといけません。


2. 制限
---------------------------------------------------------------------

- BMAP の不具合

  CVF ファイルシステムは bmap することができません。原理的にできませ
  ん。したがって、bmap を要するすべてのアクションは動作しません (swap
  や書き込み可能な mmap)。読み出し専用の mmap は、FAT ドライバがこの状
  況を考慮して作られているので動作します :) また、書き込み可能な mmap
  は、CVF-FAT 向けに FAT ドライバの中をいじったので、readpage のインター
  フェース機能を用いれば、動作します :)
  
- DOSEmu ユーザへの注意

  DOSEmu の設定によっては DOSEmu を実行する前に CVF パーティションをす
  べて umount しなければならないかもしれません。ディスク全体もしくはパー
  ティションアクセス (これは、時々 DOSEmu に圧縮されたパーティションを
  アクセスさせる場合です) を使用する設定を DOSEmu にしたなら、ドライバ
  が混乱し、圧縮されたパーティションの破壊やシステムがクラッシュする危
  険があります。
  
  lredir または emufs.sys と一緒に圧縮されたパーティションをリダイレク
  トすることは常に安全であることを覚えておいてください。詳しくは
  DOSEmu の資料を参照してください。


3. マウントオプション
---------------------------------------------------------------------

CVF-FAT 拡張は、現在 FAT ドライバの標準のオプションに加え、次のオプショ
ンがあります。

  cvf_format=xxx
    自動検知の代わりに CVF モジュール "xxx" を使用することをドライバに
    強制します。このオプションがない場合、CVF-FAT インターフェースは現
    在ロードされているすべての CVF モジュールに CVF を認識したかどうか
    訊ねます。したがって、CVF モジュールのバグや非互換性のために CVF
    フォーマットを正しく認識できない場合のみ、このオプションが必要にな
    ります (detect_cvf コールを行いません)。"xxx" を文字列 "none" ("は
    除く) とした場合、ロードされた CVF モジュールのいずれの使用も禁止
    します。これは、CVF モジュールが誤解し 純粋な FAT ファイルシステム
    をマウントしてしまうことを防ぎます。また、"xxx" は文字列
    "autoload" でもよく、モジュールローダ用の特別な意味がありますが、
    自動検知は行われます。

    カーネルが kmod をサポートする場合、cvf_format=xxx オプションは
    CVF モジュールのオンデマンドでのロードも制御します。このオプション
    がない場合、オンデマンドでロードされるものはありません。
    cvf_format=xxx を指定すると ("xxx" が "none" でなければ)、圧縮され
    たファイルシステムをマウントする前に自動的にモジュール "xxx" が要
    求されます。CVF フォーマット名とモジュール名とが異なる場合に備えて、
    モジュール設定で別名を定義してください。文字の部分の "xxx" が
    "autoload" の場合、二つ以上の CVF モジュールをロードするために特別
    なモジュール設定 (alias および pre-install 命令) を組むことで、実
    際には存在しないモジュール "cvf_autoload" を要求させて、自動的にマ
    ウントする CVF の種類を検知させ、メモリに適切なモジュールのみを保
    持します。例題は、dmsdos の資料に載っています (ftp および http の
    アドレスを後で示します)。

  cvf_options=yyy
    オプションの文字列を CVF モジュールに渡します。つまり、"yyy" だけ
    が渡されます ("は除く)。それは各 CVF モジュールでのみ解釈されるも
    のなので、その説明は各 CVF モジュール用の資料でされているはずです。
    文字列はカンマ (",") を含んではならないことに注意してください -
    FAT ドライバが、カンマの後の文字列を FAT ドライバのオプションとし
    て認識するという誤った解釈をし、混乱するか奇妙なエラーメッセージを
    吐くかもしれません。CVF モジュール用の文書は (カンマとは) 異なった
    分離記号を提示しているはずで、例えば、ドット "." やプラス記号 "+"
    で、これは文字列 "yyy" の中だけで有効です。


4. CVF-FAT インターフェースの概要
---------------------------------------------------------------------

あなたが自分の CVF モジュールを書こうとした場合、多くのインターフェー
ス機能を書かなければなりません。大部分はネット上で探せるカーネル文書の
中に網羅されているので、それらについては記述しません。それらは "[...]"
と表記しています :-) include/linux/fat_cvf.h を見てください。

struct cvf_format
{ int cvf_version;
  char* cvf_version_text;
  unsigned long int flags;
  int (*detect_cvf) (struct super_block*sb);
  int (*mount_cvf) (struct super_block*sb,char*options);
  int (*unmount_cvf) (struct super_block*sb);
  [...]
  void (*cvf_zero_cluster) (struct inode*inode,int clusternr);
}

この構造体は、CVF モジュールの能力を定義します。CVF モジュールはすべて
を記入しなければなりません。FAT/CVF-FAT ドライバにモジュールを導入する
ために使われる一形式とみなしてください。

次のものが含まれます。
  - cvf_version:
      バージョン識別子でユニークでなければなりません。何か選んでくださ
      い。
  - cvf_version_text:
      人が判読可能なバージョンの文字列で、モジュールが実装する CVF フォー
      マットについて記述する短い単語です。この文字列は cvf_format オプ
      ションで使用されます。この名前もユニークでなければなりません。
  - flags:
      ビットをフラグに割り当てたもので、ビットは mmap と readpage の両
      方の機能性を提供し readpage/mmap の考慮のためだけに現状使われて
      います。CVF_USE_READPAGE がセットする場合、mmap は
      generic_file_mmap に設定され、readpage は捕捉され cvf_readpage
      関数にリダイレクトされます。セットされない場合、readpage は
      generic_readpage に設定され、mmap は捕捉され cvf_mmap にリダイレ
      クトされます (書き込み可能な mmap を望まない場合、readpage イン
      ターフェースを使用してください)。
  - detect_cvf:
      ファイルシステムがモジュールにサポートされている種類の CVF かど
      うか決定するために呼ばれる関数です。detect_cvf 関数はその種類の
      CVF をサポートしていない (NO, I DON'T KNOW THIS GARBAGE) なら 0
      を返し、サポートしている (YES, THIS IS THE KIND OF CVF I
      SUPPORT) なら 1 以上を返さなければなりません。この関数は安全のた
      めにモジュールの使用カウンタも管理しなければなりません。つまり、
      始まりで MOD_INC_USE_COUNT を、終わりで MOD_DEC_USE_COUNT を行い
      ます。関数は、認識が成功した後 mount_cvf 関数を呼び出すことを想
      定する必要はありません。
  - mount_cvf:
      CVF がマウントされる時、いくつかの値の設定やその時に追加で行わな
      ければならない初期化をする関数です。これは fat_read_suser の終わ
      りで呼ばれ、成功時には 0 を返さなければなりません。必ず、この関
      数は MOD_INC_USE_COUNT によりモジュールの使用カウンタを増やさな
      ければなりません。さらに、この mount_cvf 関数は CVF モジュール固
      有のオプション文字列 (FAT のマウントオプション "cvf_options=yyy"
      中の "yyy") の解釈も行います。文字列はカンマを含むことができませ
      ん (分離記号として例えばドット "." を使ってください)。
  - unmount_cvf:
      ファイルシステムが umount される時、呼ばれる関数です。たぶん、い
      くつかのメモリを解放し MOD_DEC_USE_COUNT を呼び出します。返り値
      は関係ありません (現在無視されます)。
  - [...]:
      他のすべてのインターフェース機能は FAT ドライバ関数に捕捉されま
      す。つまり、オリジナルの FAT ドライバ関数の *代わりに* FAT ドラ
      イバにより実行されます。NULL はオリジナルの FAT ドライバ関数を用
      いることを意味します。本当に "何もしない" を望む場合、何もしない
      関数を書いて代わりにそれを置いてください。
  - cvf_zero_cluster:
      FAT ドライバが 0 埋めした (新しい) クラスタを欲しい場合、
      cvf_zero_cluster 関数が呼ばれます。ディレクトリ (mkdir) にとって
      重要です。このポインタが NULL の場合、渡されたinode のクラスタ全
      体が 0 で上書きされます。引き数の clusternr は絶対値であり、渡さ
      れた inode に対する相対値でないことに注意してください。

注記：
  1. cvf_bmap 関数は無視されるはずです。実際に、どこからも決して呼ばれ
     ていないはずです。すぐにバグが判明するように、私はそれをパニック
     か致命的なエラーメッセージにリダイレクトすることを薦めます。
  2. cvf_writepage 関数は無視されます。FAT ドライバがサポートしていな
     いためです。これは今後変わるかもしれません。私はそこに NULL を設
     定することを薦めます (つまり、既定値を使ってください)。

int register_cvf_format(struct cvf_format*cvf_format);
  上記の構造体に含まれる変数を設定したなら、FAT/CVF-FAT ドライバにあな
  たの CVF フォーマットを導入するためにこの関数を呼んでください。これ
  は、通常 init_module で行われます。必ず返り値を確認してください。ゼ
  ロは成功を意味し、他の場合は、起きたエラーの詳細が syslog の中にカー
  ネルメッセージとして出力されます。典型的なエラーは、
    - 同じバージョン識別子を持つモジュールがすでに登録されている。
    - CVF フォーマットが多すぎる。必要なら fs/fat/cvf.c を調整する。
  です。

int unregister_cvf_format(struct cvf_format*cvf_format);
  通常 cleanup_module の中で呼ばれます。返り値 0 は成功を意味します。
  以前に登録されていない CVF フォーマットを unregister しようとした時
  だけ、エラーが起こります。コードはモジュールの識別のためにバージョン
  識別子を使用しますので、必ずユニークにしておいてください。


5. CVF モジュール
---------------------------------------------------------------------

実装例として dmsdos モジュール (dmsdos ファイルシステムの後継) を参照
してください。現在次のところにあります。

  ftp://fb9nt.uni-duisburg.de/pub/linux/dmsdos/dmsdos-x.y.z.tgz
  ftp://sunsite.unc.edu/pub/Linux/system/Filesystems/dosfs/dmsdos-x.y.z.tgz
  ftp://ftp.uni-stuttgart.de/pub/systems/linux/local/system/dmsdos-x.y.z.tgz

(x.y.z は実際のバージョン番号とおきかわります)。dmsdos のすべての資料
は dmsdos パッケージに含まれていますが、さらに次のところにもあります。

  http://fb9nt.uni-duisburg.de/mitarbeiter/gockel/software/dmsdos/index.html
  http://www.yk.rim.or.jp/~takafumi/dmsdos/index.html (in Japanese).
======================================================================
日本語訳：野本浩一 <hng@ps.ksky.ne.jp>
    校正：早川仁さん <cz@hykw.tv>
          武井伸光さん <takei@webmasters.gr.jp>
          Akihiro KODAさん <coda@post.kek.jp>
