検索
連載

動画・写真などのデータを仮想化する仕組みとは? = Linuxカーネルinodeの仕組み =作りながら理解するファイルシステムの仕組み(9)(2/2 ページ)

今回は、前回紹介した「dentry」が参照している、ファイルの実体「inode」について詳しく解説する!

PC用表示 関連情報
Share
Tweet
LINE
Hatena
前のページへ |       

共通データ

 inodeのメンバには、共通データが入っています。具体的には、ファイルサイズやモード情報などが設定されており、ファイル情報を参照するstat(2)システムコールで返すデータが一通りそろっています(注5)。

 通常は、これらのデータでファイル情報をカバーできるのですが、LFS固有のデータもどこかに記録しておき、必要に応じて参照できるようにしておく必要があります。そのためのメンバが「i_private」というメンバです。


※注5:stat(2)で返すデータの内容については、「素晴らしきファイルシステムのデータ管理」で紹介しています。


 ただし、ファイルシステムによってはi_privateを使わずに、LFS固有データがinodeを包含するようなデータ構造を採用しているものもあります(注6)(図4)。

inodeの構造(2)
図4 inodeの構造(2)
※注6:「ext2」「ext3」「ext4」「reiserfs」「jffs2」など。


 このような構造を採用するメリットとしては、LFS固有データとinodeデータのメモリが連続しているため、メモリフラグメント(注7)の抑止効果が挙げられます。

 筆者が仕事でLinuxファイルシステムを開発していたのは、Linux 2.4系と古いのですが、その当時の記憶ではLinux標準でないファイルシステムの固有データはi_privateに登録することが普通だったと思います。しかし、Linux 2.6系ではVFS層のサポートもあり、全体的にinode包含型の採用率が高いようです。Linuxは、日々進歩していますね。ちなみに現時点でのtarfsは、inode包含型ではないので、いずれ改善させたいと思います。

※注7:メモリフラグメントとは、メモリの獲得解放を繰り返すと使用できない領域ができてしまう現象です。


共通オペレーション

 inodeのオペレーションとしては、大きく分けて2つあります。

  1. ファイルの検索/作成/削除などを行うためのオペレーション(inode_operations)
  2. ファイルデータのI/Oを行うためのオペレーション(file_operations)

 まず、inode_operationsの主要な関数を表3にまとめました。

関数名 REG DIR SYM オペレーション内容
create × × 通常ファイルを作成する
lookup × × ファイルを検索する
unlink × × ファイルを削除する
symlink × × シンボリックリンクを作成する
mkdir × × ディレクトリを作成する
rmdir × × ディレクトリを削除する
mknod × × デバイスファイルを作成する
rename × × ファイル名を変更する
readlink × × シンボリックリンクのパス名を参照する
follow_link × × シンボリックリンクのリンク先をたどる
put_link × × リンク先のパス格納バッファを解放する
truncate × × ファイルサイズを変更する
permission ファイルアクセス権をチェックする
setattr ファイルの時刻/モード/UID/GIDを変更する
表3 inode_operations

 ご覧のとおり多数の関数(オペレーション)があります(注8)。ローカルファイルシステムを新たに追加する場合は、これらの関数を登録する必要があります。登録する関数は、ファイル種別ごとに異なります。通常ファイルの場合は、inode情報に関するデータの参照・変更操作だけです。シンボリックリンクは、inode情報操作に加えてリンク先パス名に対するオペレーション関数の登録が必要になります。そして、登録関数が一番多いディレクトリについては、inode操作およびファイルの検索・作成・削除・変名などのオペレーションを登録する必要があります。

※注8:○は登録すべき関数で、×は登録不要な関数です。ただし、登録すべき関数であっても、あえて未登録にしておくことでVFS層のデフォルト処理が実行されるような場合は登録不要です。


 file_operationsの主要な関数は、表4のとおりです。

関数名 REG DIR SYM オペレーション内容
llseek × ファイルオフセット位置を変更する
read × × ファイルデータを読み込む
write × × ファイルデータを書き込む
readdir × × ディレクトリ内のファイル名一覧を取得する
mmap × × ファイルのメモリマップを作成する
open × ファイルをオープンする
release × ファイルをクローズする
fsync × × ファイルの変更データを永続化する
表4 file_operations

 ファイルI/O用の関数なので、シンボリックリンクは関数の登録は不要です。一方、通常ファイルについては、動画や写真のデータを読み書きするための関数readやwriteを登録しなければなりません。最後にディレクトリについては、ファイル名一覧を参照する専用関数としてreaddirの登録が必要となります。

 これらの登録関数ですが、ローカルファイルシステムを作る場合には、どうやったらよいか戸惑ってしまうのではないかと思います。筆者が経験的にやってきたこととしては、Linux標準のファイルシステムであるext3やVFS層からローカルファイルシステムの処理を呼び出すソースを読み、紙と鉛筆でデータ構造や関数呼び出し関係を図示しながら……、「あー、ここはこうすればよいのか!」といった風に設計・実装を進めていきました(注9)。

※注9:詳しくは、tarfsをLinuxカーネルに導入する方法にて紹介する予定です。




 さて、次回は、ファイルデータのI/O処理を理解するうえで欠かせない「page」と「buffer_head」の構造について解説します。これが分かれば、Linuxカーネル内で自分のデータがどうやって管理されているかがよく分かります。お楽しみに! (次回に続く)


Copyright © ITmedia, Inc. All Rights Reserved.

前のページへ |       
ページトップに戻る