libspe 解析 take.1-CELLプロセッサ
やっと解析開始ということで、第一回は libspe から始めます。 まずは...
やっと解析開始ということで、第一回は libspe から始めます。
まずはマニュアルということで、SPE Runtime Management Library, Version 1.1 (libspe_v1.1.pdf) を読んで、解析に必要な情報を洗い出してみます。
- SPE thread と SPE group という管理単位がある
- SPE thread は 処理単位 (spe で実行されるプログラム) 毎に生成される
- SPE thread は SPE group に属する
- SPE thread の属性 (policy, priority) は 所属する SPE group によって決まる
- (当然だが) SPE thread と SPE group は複数生成可能
ということで、これらを管理しているデータ構造と制御関数を探してみます。
データ構造
spe.h を見てみると以下の構造体があります。
| struct group_list | SPE group リストの先頭データ |
| struct grpsElem | SPE group リストデータ |
| struct group_store | SPE group 管理データ |
| struct grpListElem | SPE thread リストデータ |
| struct thread_store | SPE thread 管理データ |
図で表すとこんな感じです。
+----------+ +--------+ +--------+
|group_list| -> |grpsElem| ----------------------> |grpsElem| -
+----------+ +--------+ +--------+
| |
V V
+-------------+ +-------------+
| group_store | | group_store |
| | | |
|+-----------+| |+-----------+|
||grpListElem|| ||grpListElem||
++-----------++ ++-----------++
| |
V
+-----------+ +--------------+
|grpListElem| -> | thread_store |
+-----------+ +--------------+
|
V
+-----------+ +--------------+
|grpListElem| -> | thread_store |
+-----------+ +--------------+
|
制御関数
次にこれらのデータを制御する関数にどんなものがあるのか見てみると、spe.c に以下の関数がありました。
| srch_thread() | SPE thread 識別子 (speid) の検査 |
| srch_group() | SPE group 識別子 (gid) の検査 |
| add_group_to_groups() | SPE group を group list に追加 |
| add_group_to_groups() | SPE thread を SPE group に追加 |
| remove_thread_from_group() | SPE thread を SPE group から削除 |
となっており、一旦作成した SPE group は削除できないみたいです。
実際の使用方法
実際の使用方法に関しては、SPE thread のライフサイクル (生成、実行、終了) に関わる libspe の 3 API と SPE thread のスタート関数を見てみます。また、libspe はスレッドの管理に pthread を使用し、spe の制御は syscall を使用していますので、これらの関数を適当に抜き出しました。
なお、これらの関数は全て spe.c 内に書かれています。
SPE group 生成関数
spe_create_group()
-> spe_gid_setup() // SPE group 管理データ生成
-> calloc() // SPE group 識別子を生成
-> add_group_to_groups() // SPE group を group list に追加
SPE thread 生成関数
spe_create_thread()
-> srch_group() // SPE group 識別子を検査
-> spe_setup() // SPE thread 管理データ生成
-> spe_gid_setup() // SPE group が指定されていない場合
-> calloc() // SPE group 識別子を生成
-> add_group_to_groups() // SPE group を group list に追加
-> calloc() // SPE thread 識別子を生成
-> spe_create()
-> syscall(spe_create) // spu context の生成
-> add_thread_to_group()
-> pthread_create(,,spe_thread,) // SPE thread の生成 (spe_thread() を実行)
SPE thread スタート関数
spe_thread()
-> do_spe_run()
-> spe_run()
-> syscall(spe_run) // spu context の実行
// return すると終了
SPE thread の状態変化 (終了) を待つ関数
spe_wait()
-> srch_thread() // SPE thread 識別子を検査
-> pthread_join() // SPE thread の終了待ち
-> spe_cleanup() // SPE thread 管理データ削除
-> remove_thread_from_group() // SPE thread を SPE group から削除
わかったこと
- spe_{get,set}_priority() より pthread_setschedparam がコメントになっているので priority 操作は未対応?
- spe_{get,set}_affinity() より affinity 操作は未対応
- spe_{get,set}_context() より context 操作は未対応



