next up previous contents index
Next: コンパイルドコード Up: KLICの基本的な動作 Previous: 動作モデル

トップレベルループ

 

先に説明した動作モデルをごく単純化すると、「ゴールの選択」 $\Rightarrow$ 「実行」 $\Rightarrow$ 「ゴールの選択」... という「ループ」であることがわかる。これをKLICのトップレベルループと 呼ぶ。このループは runtime/kmain.c内のtoploop関数により実現されている。

もう少し正確、詳細に解説すると、 モジュールはmodule型関数で実装されるが、この関数は以下のように動作する。 このモジュール型の関数はKLICのコンパイラで出力されるものであり、 ユーザが定義したモジュール、システムで定義されているモジュール各々に 一関数ずつある。

この関数が終了した後には、大域変数current_queueにその時の 実行可能queueの先頭がセットされているので、それをqpに戻し、 次のモジュールの実行を行う。

以下がmodule型関数を呼び出す toploop関数の全てである。

static void toploop()
{
  declare_globals;
  struct goalrec *qp = current_queue;
  Const struct predicate *toppred = qp->pred;
  module func = (module)toppred->func;
  while (1) {
    func = ((module (*)())func)(glbl, qp, heapp, toppred);
    qp = current_queue;
    toppred = qp->pred;
  }
}

 

current_queueとあるのが(現在実行中の優先度の)実行可能ゴールスタックであり、 struct goalrecの線型リストとなっている。先頭をqpにとりだし、 述語レコード(struct predicate)をとりだし、モジュールを実現する関数 (func)をさらに取りだしている。そして、 その関数を呼びだすことを繰り返すwhileループに突入する。

ここで、module型関数の引数は以下のようになっている。

glbl:
大域データ構造へのポインタ(第2.4.1章 ([*]ページ)参照)

qp:
現在の実行優先度の実行可能キュー

heapp:
ヒープ割付点

toppred:
(この文脈で判明するように)これから実行する 述語のレコード



Sekita Daigo
1998-05-18