\chapter{CbCによるFileSystemの書き換え}
\section{書き換え方針}
FileSystem の処理は複雑である。FileSystem が記述されている fs.c で定義されている関数を CbC によって書き換えることにより処理の明確化と信頼性の保証をしたい。
そのために if 文の中に if文がある場合や for 文がある場合には処理を細かく分離してやり分かりやすくする。また、CbC の Interface を用いることにより仕様と実装を分離し拡張性を実現する。
%xv6 を CbC で書き換え、Gears OS の機能と置き換えることで Gears OS に OS の基本構造を持たせたい。
%このためには xv6 をモジュール化することで、xv6 の機能を明らかにする必要がある。
%xv6 の Interface を定義し、Gears OS の機能をこれに合わせることによって実現したい。

%\newpage
\section{FileSystem の Interface の定義}
Interface はある Data Gear の定義と、それに対する操作を行う Code Gear の 集合を表現する Meta Data Gear である。Context では全ての Code Gaer と Data Gear の集合を表現していることに対し、Interface は一部の Code Gear と一部の Data Gear の集合を表現する。
図\ref{fig:fsfilesystem}で表されている通り、FileSystem においても Interface で定義した CodeGear と実装側の CodeGear は対応している。

\begin{figure}[ht]
     \begin{center}
     \includegraphics[width=100mm]{fig/fsInterface.pdf}
     \end{center}
     \caption{xv6 FileSystem の Interface と実装}
    \label{fig:fsfilesystem}
\end{figure}

%\newpage
FileSystem の Interface を記述したコードをソースコード\ref{fs_interface}に示す。

\lstinputlisting[label=fs_interface,  caption=FileSystem の Interface (fs.dg一部抜粋)]{src/fs1.dg}

1行目で Interface名を定義している。typedef struct の後に Interface名 (今回は fs) を書く。
CodeGear は \_\_code CodeGear名 (引数) の形で記述する。第一引数である Impl* fs が CodeGear の型、第二引数以降は Interface の実装時に利用する CodeGear が必要とする引数が入る。
CodeGaer は 2 行目から 9 行目のように ”\_\_code [CodeGear 名]([引数])”で記述する。この引数が input Data Gear になる。

\section{FileSystem の Interface の実装}
Interface の実装はソースコード\ref{fs_interface_impl}で示すように Interfaceとは別に定義する。
\lstinputlisting[label=fs_interface_impl,  caption=FileSystem の Interface の実装(fs\_impl.cbc 一部抜粋)]{src/fs_impl1.cbc}

2 行目のようにインターフェースのヘッダーファイルは \#include ではなく \#interface で呼び出す。
4行目の create fs\_impl は Java などのコンストラクタに相当する。7行目から66行目で Interface と実装の紐付けしている。
CbC は1つ1つの CodeGear の信頼性を保障させるために細かくするべきであるため、 for 文や if 文がある場合はさらに実装を分ける。fs と同じように fs\_impl を定義し、遷移する関数名に対応させていく。分けた実装はさらに別で実装する (fs\_impl\_private.cbc)。

\section{FileSystem の Interface の private な実装}
インターフェースで定義した CodeGear 以外の CodeGaer も記述することができる。この Code Gear は基本的にインターフェースで指定された Code Gear 内からのみ継続されるため、Java の private メソッドのように扱われる。
インターフェースと同じようにヘッダーファイルをソースコード\ref{fs_impl}で定義する。

\lstinputlisting[label=fs_impl,  caption=fs private のヘッダーファイル(fs\_impl.h一部抜粋)]{src/fs_impl1.h}

private での CbC の記述について説明する。記述量が多いため、if 文と for 文を書き換えた ialloc\_impl という関数で説明する。書き換えコードは以下のソースコード\ref{ialloc}とソースコード\ref{alloc}に示す。

\lstinputlisting[label=ialloc,  caption=iallocfs\_impl の実装]{src/iallocfs_impl.cbc}
fs\_impl.cbc の中でCodeGear である iallocfs\_impl が処理されると goto で private な実装である fs\_impl\_private.cbc 側の allocinode という CodeGear へと遷移する。

\lstinputlisting[label=alloc,  caption=iallocfs\_impl の private 実装]{src/ialloc.cbc}
private 側では iallocfs\_impl からの受け皿としての allocinode、for 文のループ条件を確認する allocinode\_loopcheck、ループした際の処理をする allocinode\_loop、ループから抜けた際の処理をする allocinode\_noloop の4つの CodeGearから成り立っている。 ループの条件に当てはまらない際は panicへと処理が移り処理が停止する。static なものはまだ書き直していないが後々実装する。これらの CodeGearの一連の挙動を図\ref{fig:iallocloop}に示す。

\begin{figure}[ht]
     \begin{center}
     \includegraphics[width=100mm]{fig/iallocloop.pdf}
     \end{center}
     \caption{allocinode の ループによる遷移図}
    \label{fig:iallocloop}
\end{figure}

本稿では ialloc\_impl という関数を取り上げて説明したが、FileSystem が記述されている fs.c で定義されている関数に関しては全て CbCを用いることにより状態遷移ベースに書き変え挙動を明確化した。