syncシステムコールの仕組みを調べた。
カーネルバージョン
v4.7-rc
syncシステムコール
システムコールの呼び出し元はこんな感じなので、補助関数の分け方はあまり変わっていなさそうだ。
/*
* Sync everything. We start by waking flusher threads so that most of
* writeback runs on all devices in parallel. Then we sync all inodes reliably
* which effectively also waits for all flusher threads to finish doing
* writeback. At this point all data is on disk so metadata should be stable
* and we tell filesystems to sync their metadata via ->sync_fs() calls.
* Finally, we writeout all block devices because some filesystems (e.g. ext2)
* just write metadata (such as inodes or bitmaps) to block device page cache
* and do not sync it on their own in ->sync_fs().
*/
SYSCALL_DEFINE0(sync)
{
int nowait = 0, wait = 1;1
wakeup_flusher_threads(0, WB_REASON_SYNC);
iterate_supers(sync_inodes_one_sb, NULL);
iterate_supers(sync_fs_one_sb, &nowait);
iterate_supers(sync_fs_one_sb, &wait);
iterate_bdevs(fdatawrite_one_bdev, NULL);
iterate_bdevs(fdatawait_one_bdev, NULL);
if (unlikely(laptop_mode))
laptop_sync_completion();
return 0;
}
flusherスレッド
fs-writeback.cにあるwb_*の関数で非同期でライトバックを行うためのスレッドである。もうpdflushではなくて、writebackというそのまんまの名前のワークキューになっている。全部のブロックデバイスのbdi_writebackに対して、ダーティーを吐き出すワークキューを積む。
これで、すべてのブロックデバイスに対して、ページキャッシュがディスクまで書かれる。
この辺はcgroup_writebackというのが関連していて、構造が複雑になっているようだ。メモリのリソースを分割した時のために、ブロックデバイスごとに複数のwriteback用スレッドが存在している?
iterate_supers
すべてのsuper_blocksのアイテムに対して第一引数の関数を実行する。super_blocksへはsget()で追加されている、sget()はフィアルシステムからマウント時に呼ばれる。
削除は__put_super()で、おそらくアンマウント時に呼ばれる。
sync_inode_one_sb
第一引数のsuper_blockに含まれるinodeから、__filemap_fdatawait_range()にmappingを渡してdirtyなファイルを書き出す。
sync_fs_one_sb
各ファイルシステムのスーパーブロックに対するsync_fsオペレーションを呼び出す。
iterate_bdevs
blockdev_superblockなるリストに対して、第一引数の関数を実行する。iterate_supersのブロックデバイスバージョン。
fdata*_one_dev
__filemap_fdatawrite_range()で、メモリマップされているファイルをライトバックする。これはブロックデバイスのinodeのマッピングなので、バッファキャッシュということになる。
まとめ
syncの動作を見ることで、どんなページキャッシュが作られるかイメージがつきやすい。writebackのスレッドがやっている書き出しと、inode,blockデバイスごとに走査して書き出す内容の違いがあまり調べられていない。もう一段キャッシュがある?
cgroupに関連して新たな仕組みが作られている。cgroupのような新し目の話題は書籍には無いので、どこかのタイミングでまとめて調査してみたい。