GPUの勉強
GPUのアーキテクチャを調べています。ARMの「Mali T-658」やPowerVRなどを見る機会も多いのですが、ブロック図を見ても全然わからない…。
新しい機能の説明は目につくのですが、基礎的な知識が不足してますね。
GPUの処理の順番と、それに伴うメモリとのやり取りの図です。まずこれを見て思うのは
- 頂点シェーダって何?
- ジオメトリシェーダって何?
- ラスタライズって何?
- ピクセルシェーダって何?
- ラスター演算って何?
- Zバッファって何?
- テクスチャって何?
- インデックスバッファって何?
- ストリームバッファって何?
ということで全部わからないわけです。
そもそもプログラマブルシェーダって?
シェーダの名前が色々出てきますが、そもそもプログラマブルシェーダとはなんなの?
DirectX8の説明ではこのようにあります。
プログラマブル シェーダを使うと、トランスフォーム、ライティング、レンダリングの機能を実行時に修正することが可能になり、グラフィック パイプラインに新しい次元が追加される。シェーダは実行時に宣言されるが、ユーザーはこのときに、アクティブにするシェーダを変更したり、ストリーム データを使ってシェーダ データを動的に制御することができる。プログラマブル シェーダを使えば、ピクセルのレンダリング方法に新しいレベルの動的な柔軟性が生まれる。
2000年にプログラムシェーダが出てきたので過去の記事をさかのぼってみます。4Gamers辺りが詳しいですね。(参考:4Gamers ATI Radeon HD2000シリーズのGPUアーキテクチャ)
なぜプログラマブルで機能の切り替えをしなければならないのかは、シーンによって頂点シェーダとピクセルシェーダにかかる負荷は変わるのだそう。上の図の処理の順番でいうと、始めは頂点シェーダは動いているのだけど、ピクセルシェーダは動いていないってこと。
シェーダによる処理内容はそれほど変わらないので、負荷に合わせて演算器を切り替えればいいじゃないかという発想らしい。
上の図で入力アセンブラを入れるなら、それを解釈する機能が必要だなぁと思っていたのですが、サブCPU的なものが必要だそうだ。ARMのMaliでは「Inner-core Task Management」と呼ばれている部分が相当しそう。
それまでCPUがドライバソフトで実行していたのが、これでGPU側で処理が出来る。CPU負荷が下がるのはこれによるそうだ。GPU側にあることでGPUのステータスを知ることができ、コマンド発行タイミングを制御しやすいとのこと。
参考にした4Gamerの記事にあるATIのブロックでは、「頂点アセンブラ」「ジオメトリアセンブラ」「スキャンコンバータ/ラスタライザ」の3つをまとめて「セットアップエンジン」と呼んでいる。
頂点アセンブラ
頂点シェーダが必要とする頂点バッファやインデックスバッファのアドレスデータをまとめる。
ジオメトリアセンブラ
ジオメトリシェーダが必要とする複数頂点情報をまとめる。
スキャンコンバータ/ラスタライザ
ポリゴン情報からピクセルシェーダ単位の処理に分解する
ウルトラスレッド・ディスパッチ
汎用シェーダユニットの切り替えを行う。汎用シェーダは頂点シェーダ、ジオメトリシェーダ、ピクセルシェーダの3種類に切り替えられるが、この制御を行う。
まず命令が頂点/ジオメトリ/ピクセルの各処理キューに入る。汎用シェーダを実際に切り替えてるのはアービタのようだ。シーケンサによってプログラムカウンタの管理をする。メモリからテクスチャの読みこみも行う必要があり、読み込みに時間がかかるので、マルチスレッドのような処理を行いいかに効率的にハード資源を使うのかが性能に効いてきそう。
またテクスチャをメモリから読むのでは時間がかかるので、キャッシュも備えているようだ。
実行した結果は汎用レジスタに保持する。ウルトラスレッド・ディスパッチによって一時的に処理が止められた途中データも汎用レジスタに保持する。
座標系
レンダリングパイプラインの進行によって複数の座標系があるそうです。
- オブジェクト座標系(object coordinate system)
- 世界座標系(world coordinate system)
- 眼点座標系(eye coordinate system)
メモ
- トライアングルセットアップ … ポリゴンからピクセル単位のタスクに分解する