Lions' 本読み (143)

下方面でノドが渇いてたのでリハビリ兼ねて復習。

とりあえず

ディスクドライバからバッファ云々、なあたり。バッファ (4720) とかバッファヘッダ (4535) て何かというとカーネルの静的領域に確保されたディスクキャッシュである、という認識なんですが大丈夫かな。
いっちゃんイメージし易いのは bread() 手続きなのかどうか。

4754 bread(dev, blkno)
4755 {
4756     register struct buf *rbp;
4757
4758     rbp = getblk(dev, blkno);
4759     if (rbp->b_flags&B_DONE)
4760             return(rbp);
4761     rbp->b_flags =| B_READ;
4762     rbp->b_wcount = -256;
4763     (*bdevsw[dev.d_major].d_strategy)(rbp);
4764     iowait(rbp);
4765     return(rbp);

getblk で dev と blkno なセットのバッファを取得して、バッファの状態 (?) が B_DONE であればそのまま戻してます。そうでなければ入力なリクエストを出して処理終了まで wait してバッファヘッダを戻しています。

getblk 手続き

以下な記述があります。

4931     if (dev < 0)
4932             dp = &bfreelist;
4933     else {
4934             dp = bdevsw[dev.d_major].d_tab;

ええと、初期値としては以下のはず。

4656 int (*bdevsw[])()
4657 {
4678  &nulldev, &nulldev, &rkstrategy, &rktab, /* rk */

rktab は rk.c で定義されてて以下。

5386 struct devtab rktab;

struct devtab 型は buf.h で定義されてて以下ですね。

4551 struct devtab
4552 {
4553    char    d_active;
4554    char    d_errcnt;
4555    struct  buf *b_forw;
4556    struct  buf *b_back;
4557    struct  buf *d_actf;
4558    struct  buf *d_actl;

d_tab な xref 手繰ってみます。みたんですがここに代入してない、って思っていたら getblk で云々してましたね。そしてやはり基本的にはこのリストからは外されてませんね。これがディスクキャッシュの所以か。

一旦終わり

晩メシ作成に着手の方向。18 章は inode 云々で 19 章がディレクトリ云々で 20 章がファイルシステムになっているのかどうか。

もう少し

キャッシュの所以、という意味では

  • いちばん最近に release されたバッファは bfreelist の末端に追加される
  • getblk で新規にアサインされるバッファは bfreelist の先頭から取り出す

という仕様に沿っていることと、ブロック番号でアサインされたことのあるバッファがあった場合にはそれが使われる、という事から、いっちゃん使われてないバッファが bfreelist の先頭にある、ということが保証されているのかどうか。