- 並列信頼研
- 桃原 優
# 概要
- OS の信頼性を上げたい
- CbCという言語を使って xv6 という OS を書き換える
- Paging の書き換えを行った
- まだ実装中
- 将来はコンテナやVMを実装できるはず
# OS の信頼性を上げたい
- OS自体が複雑で検証が困難。
- バグの原因に
- OSの仕様を定義してそれを満たすことを証明する
- 証明しやすい形の記述を作る
- CbCの goto で書く
- 状態遷移系に近い形で記述できる(証明しやすい)
- 関数型の記述
- 入力に対しての出力を検証する
- 記述のモジュール化
- CbCのインターフェースで書く
- 煩雑な記述の解消
- 入力の切り替えによる機能の入れ替え
# ノーマルレベルとメタレベル
- ノーマルレベル
- CbCで記述される部分
- メタレベル
- Paging などのメモリやCPU自体の操作
- (ノーマルレベルの)プログラムの正しさの証明
- cmake で生成している
# Continuation based C
- 状態遷移ベースで記述できる言語(以下CbC)
- cmake で CbC からメタレベルの記述を生成する
- Code Gear
- 基本的な処理の単位
- goto 文で遷移する
- Data Gear
- Code Gear からアクセスできるデータの単位
- 引数など
- Meta Code Gear
- Code Gear の間に挟まれるメタレベルの処理
- Meta Data Gear
- Code Gearの間の接続などの情報
- Context(後ほど説明)
# ノーマルレベル
# Code Gear による継続
- Code Gear の処理の間を goto によって遷移していく
- __code CodeGear名 で定義
# Data Gear の継続
- Code Gear からアクセスできるデータ
- input Data Gear と Output Data Gear で証明する
# メタレベル
# Meta Code Gear
- メタレベルで見ると Code Gear の間にメタレベルの処理が挟まっている
- cmake で __code CodeGear名_stub が生成される
# Meta Data Gear
- ノーマルレベルでの書き換えやアクセスを防ぐために存在
- CbC の 接続可能な Code Gear, Data Gear のリスト
- Data Gear を確保するメモリ空間
- Context
# Context
- Meta Data Gear
- Contextには全てのData Gear と Code Gear が登録されている
- ユーザープロセスに対応して1つのcontextが存在する
- 将来的なVMやコンテナの実装はContextの切り替えるによる実装を目指している
- Code Gear は Context 内の Data Gear の関数ポインタを持っていてそこにアクセスする
- stub Code Gear でOutput Data Gear のポインタを参照してそこに書き出す
# Xv6
- MIT の講義用教材として作られたOS
- 規格化される前のCで書かれたUNIX V6 を書き換えた
- 1万行程の軽量なOS
- Linuxだと数千万行
- Xv6 をCbCで書き換える
# Xv6の構成
- system call
- カーネル空間の処理の呼び出し
- VM(仮想メモリ)
- Paging
- File System
- I/O, Read, Write
- Scheduler など
# カーネル空間
- OS の中核となるプログラムで Meta Level に相当する
- Xv6 ではカーネルとユーザープログラムは分離されている
- ユーザープログラムはカーネルに直接アクセスできない。
- ユーザープログラムによる書き換えやアクセスを防ぐため
- 呼び出す場合は system call
# Paging
- Page と呼ばれる固定長のブロックに分割して、メモリとスワップ領域で Page を入れ替えて管理
- 仮想メモリとして扱うことでフラグメンテーションの解消と空き番地を探す必要がなくなる
# Xv6の書き換え方針
-
メタレベルからノーマルレベルを保証するOSを作りたい
-
段階的に書き換えていきたい
-
Paging を書き換える理由
- OS の信頼性を保証する上で重要なメモリ管理部分
-
__code で書き直していく
# インターフェースの導入
- ノーマルレベルからメタレベルの記述が記述が煩雑になるためインターフェースを導入
- インターフェースによるメリット
- 煩雑な記述の解消
- 入力の切り替えによる実装の入れ替え
- 実装は別で定義し、呼び出す
- 後ほど説明
# CbCインターフェース
- Data Gear と Data Gear に対して操作を行う Code Gear の集合を表現する Meta Data Gear
- インターフェースを定義してそこから呼び出す
# インターフェースの定義
- Xv6 の Virtual Memory の API 部分のインターフェース
- 以下のコードについて説明していく
|
|
# インターフェースの命名(1行目)
- typedef struct の直後にインターフェース名(vm)を書く
|
|
# インターフェースの Code Gear(2行目~)
- vm で使う Code Gear を登録する
- Code Gear は __code CodeGear名(引数); で記述する
- 引数が Data Gear に相当する
- 第1引数の Impl* vm がインターフェースの実装の型になる
|
|
# next(…)
- __code next(…) は次の Code Gear の継続先
- それぞれの Code Gear の引数の1つに設定する
|
|
- 例) goto vm->kpt_freerange の引数に exit を設定すると Code Gear である exit に遷移する
|
|
# Interface の実装の型
- 実装側のヘッダーファイルも vm_impl と同じように用意する
|
|
# インターフェースの実装
- 実装は型と実装をそれぞれ別ファイルで定義する(vm_impl.h と vm_impl.cbc)
- 実装するインターフェースは #interface で宣言する
|
|
# vmインターフェースの実装の初期化
- 定義が終わったのでインターフェースを使用したい
- メモリ上にインターフェースの置き場所と実装を確保
- struct vm* vm = new vm();
- インターフェースと実装の紐付け
- vm->void_ret = C_vm_void_ret;
- Code Gear の enum の設定
- インターフェースのAPIと enum の番号を紐付けている
- vm->void_ret = C_vm_void_ret;
|
|
- APIの実装の例(init_vmm)
- C_init_vmmvm_impl が メタレベルでinit_vmmvm_impl と対応する
|
|
# インターフェース実装内の CbC
- for文やif文がある場合はさらに実装を分ける
- 状態遷移ベースで記述したい
- インターフェースは外から呼び出されるAPI
- それに対してインターフェースの実装の Code Gearから明示的に呼び出される Code Gearは、Java の private メソッドのように扱われる。
- 実際に vm.c の loaduvm の実装を分けた記述を説明する
# 実装内の明示的な遷移の処理
- vm と同じ create_impl 内で vm_impl を定義し、private で実装する Code Gear を定義する
- loaduvmvm_impl で goto によって private に遷移する
|
|
- vm のインターフェースの実装を vm_impl に設定している
- vm の実装内で使用する Code Gear も enum の番号で指定する
- vm_impl->loaduvm_ptesize_check = C_loaduvm_ptesize_checkvm_impl;
|
|
# loaduvmの CbCによる書き換え
-
loaduvmは
- swapから呼び出す
- kernelの中をloopしてreadiに入る
- 入った場合は待ちになる
- user proc側が待ちになる
-
vm.cのloaduvmの処理をCbC で書き換える
|
|
- loaduvm_impl がインターフェースから呼ばれる実装
|
|
- loaduvm_impl から private な Code Gear が呼ばれる
|
|
- vm.c のloaduvm の実装を CbC で書き直す
|
|
- vm.cではここから for だが CbC は if文の中と外にgoto を用意して実装する
|
|
# C を CbC に部分的に書き直す手法
- CbC の場合 goto による 遷移を行うので、関数呼び出しのように goto 以降のコードを実行できない
- 例) goto すると戻ってこれないため それ以降が実行されなくなる。
# CbC から C への遷移
- 最初の命令は next で戻ってこれるので、dummy の関数を用意してそこで実行する
|
|
# まとめ
- OS 内部で CbC インターフェースを扱えるようになった
- CbC の書 き換えが完了すれば、継続の入力と出力を検査することで OS の信頼性を保証したり、インターフェースの実装の入れ替えが可能になる。
- Context による複数環境の入れ替えや同時実行を可能にすることで CbCXv6 に おいて コンテナと VM を実装ができると予想される。