Next: Up: Previous:

制限と議論

 

StackThreads は C でのプログラミングの実際をできるだけ多く サポートすることを目指している一方で, ある制限も存在する.

まず, StackThreads は基本的にスタックフレームが移動可能で ある事実, より正確に言えば, スタックに確保されたデータは FP および SP に相対的にアクセス可能であることに依存している. この性質はもちろんすべての C プログラムとコンパイラが満たして いるわけではない. StackThreads は, スタックに確保された オブジェクトのアドレスを取りだすこと, アドレスがコンテキストスイッチをまたがって有効なデータを キープすることを仮定することをを禁止している. さらに悪いことに, たとえ手続きが明示的にスタックデータの アドレスを取り出さなくても, オプティマイザが汎用レジスタに そのアドレスをキャッシュし, 手続き全体に渡ってその アドレスを使用することがありうる. これは集合データ(配列 もしくはスタックに確保された構造体)に対して行なわれる. 総合すると, StackThreads はスタック上にどんな集合型データを 確保することも奨励していない. 我々は Garbage-collected 言語に ついては, これが致命的な制限でないことを信じている. 我々は StackThreads を garbage-collected heap をサポートする 並列オブジェクト指向言語 ABCL/f を実装するためにうまく使った.

二番目に, 読者はどのプリミティブを StackThreads がサポートするべきか については選択の余地があると気づいているかもしれない. それは現在一つのスタックフレームのコンテキストのセーブ をサポートしている (3.2.4 (3)節を思い出してほしい. スレッド fswitch_to_parent を 手続き呼びだしの鎖を通じて間接的に呼ぶとき, f のフレーム のみがセーブされ, 呼び出しの鎖の中の他のフレームは単純に 捨てられる). 結果として, ブロックの可能性がある手続きの逐次呼びだしは, 手続きがリターンしたあとのフラグのチェック, および, もし返り値がない場合は連なった巻き戻しの操作, によって実現されなければならない. 我々は逐次呼び出しをサポートする可能性について調査した. 逐次呼びだしにおいては, caller への制御の移動は 返り値の存在を意味する. 最終的に 我々はいくつかの呼びだし慣例においてはこの実装は難しい という結論に至った. 上の逐次呼びだしのセマンティクスを サポートするためには, ライブラリは一つのライブラリ呼びだしで 複数のスタックフレームを巻き戻し, 後にそれを, フレーム間の 呼びだしの鎖を維持したまま, 他の場所に移動しなければならない. 複数のフレームを一緒に移動させることは, もしスタックフレームが 相対アドレスによってのみつながっている場合は単純であろう. しかし, 不運にも, これは Sparc を含むいくつかの手続き結合慣例では 当てはまらない. 各フレームスロットは caller のフレームポインタの 絶対アドレスを格納する. そのような慣例のもとで 呼びだしの鎖を再構築するためには, 各フレームは逐次呼び出しの 前にフレームについての情報を提供しなければならない. Sparc では, これは1フレーム当たり10インストラクションを要し, 値があるかどうかのチェックを省いた利点を帳消しにする. 我々の現在の実装は, 呼び出しの前には全くオーバヘッドを 課さず, 代わりに, オーバヘッドは呼び出しの後にフラグをチェック すること, および, 必要ならば連なった巻き戻しをすることで払われている.

最後に, StackThreads は, コンテキストスイッチのコストを 小さくするために生きている変数の情報を利用できない. 手続きのすべての局所変数を保持している領域全体を保存/回復している. これは潜在的には問題であるが, 3.2.6節の 性能評価は他の要素が支配的であることを示している.



Mitsubishi Research Institute,Inc.
Mon Feb 24 19:27:36 JST 1997