Upload
koguchi-takahiro
View
2.233
Download
0
Embed Size (px)
DESCRIPTION
第2回レイトレーシング合宿で発表した資料です。 リアルタイムGPUフォトンマッピングについての論文の説明です。
Citation preview
フォトンマッピングGPU 実装最新手法
平成 26 年 9 月kgussan
GPU 実装~リアルタイム GI昨年度の合宿で、様々なレイトレのわかりやすい資料が発表されたと思います。今回次に話題になりそうな GPU 実装の論文について一つご紹介したいと思います。紹介するのはリアルタイム向けのアルゴリズムとして述べられた論文です。ですが GPU にとって効率の良いアルゴリズムを知るという意味において有用だと思います。
現行リアルタイム CG とレイトレーシングの照明の違いとして、リアルタイムCG で使う近似アルゴリズムは、環境テクスチャマッピングによる 2 次の反射光までが中心です。近年、ボクセルコーントレーシング、ライトプロパゲーションボリュームなど、いくつかの条件付きで反射回数の制限がなくなってきています。最近の GPU の性能向上から、リアルタイム CG に本格のグローバルイルミネーションが適用される日も近いのではないかと思います。
フォトンマッピングを使い、任意回数のフォトントレーシング反射結果を表現するいくつかの手法を紹介します。
レイトレーシング ラスタライズ
光学計算レイトレーシング演算スリックモデルなど
フォンライティングフォン・ブリンライティングなど
大域照明(反射が 2 回以上の光学計算) レイトレーシング演算
ライトプロパゲーションボリューム( LPV)事前計算放射輝度転送( PRT )ボクセルコーントレーシングなど
影 レイトレーシング演算
シャドウマッピングシャドウボリュームSSAO など
反射レイトレーシング演算(任意回数の反射)
キューブ環境マップ スフィア環境マップなど (一回の反射まで)
屈折レイトレーシング演算(任意回数の屈折)
キューブ環境マップ スフィア環境マップなど (一回の屈折まで)
集光現象(コースティクス) レイトレーシング演算テクスチャ焼き込みなど。トポロジに依存するため動的には厳しい
被写界深度( DOF ) レイトレーシング演算 深度バッファを使った 画像(後)処理
モーションブラー レイトレーシング演算 深度バッファを使った 画像(後)処理
プリミティブレイトレーシング演算(陰関数等の交差判定実装次第) 三角形
レイトレーシングとラスタライズアルゴリズムの比較レイトレーシング VS ラスタライズ(グラフィックス専用演算器群)代表的なグラフィックスアルゴリズム比較リアルタイムに動かすために様々な工夫、近似を使っている。
基本的に速度はレイトレーシングよりもラスタライズ方式のほうが格段に高速。前者は 1 フレームに数時間単位に対してラスタライズ方式は 16.7ms(1/60 秒 , 60fps)で処理することを前提にしている。ハードウェア化されている恩恵とともに、近似演算で高速化されていることで可能になっている。近似されているゆえに高速だが精度を捨てている。GPU 性能に合わせて性能と質のトレードオフを見ながらリアルタイム演算のアルゴリズムは選択され、新しいものが研究・開発されている。元ネタ: raytracing.jp
リアルタイムレイトレーシング真面目に計算理する方法でも , 実用的なリアルタイム処理が現実に近くなっています。
下記手法があれば解決?
・ Matt svoboda さんのリアルタイムレイトレデモ
http://www.youtube.com/watch?v=i8hSZGTXTx8#t=144
・ Matt さんのリアルタイムレイトレデモ解説( brick map )
http://d.hatena.ne.jp/hanecci/20140209/p1
http://graphics.cs.williams.edu/papers/PhotonI3D13/
Morgan さん:法線マップを使った SSAOなど有名論文著作多数。
反射・屈折のみならず、環境項、多数回の拡散反射、コースティクスを扱うためにはレイトレだけでは表現が難しいです。前頁のものだけでは不足です。フォトンマッピングなど、表現に適した手法があります。
レイトレーシングの GPU 実装の話題は多々ありますが、フォトンマッピングのフォトン収集パスとその GPU 実装について述べている論文は見当たらないので紹介したいと思います。
1st 著者 NVIDIA Michael さん今年は DeepGbuffer
リアルタイムフォトンマッピング処理
論文の概要フォトンマッピングの実装を取り上げてみます。計算には、フォトンのトレーシング計算に加えて、フォトン収集パスが必要になります。フォトン収集には大量のフォトンをサンプリングする必要があります。レイトレーシングはすでに様々な解法があります (NVIDIA には秒間数億レイが飛ばせるOptix システムがある ) 。そのためトレーシングは割愛し、今回はフォトンのサンプリング手法について調べます。高速に実行するために GPU を活用します。
今回試してみたところでは GeForce670 にて、 1frame 28ms ( 30fps )を達成した。演算能力 1344shader pipe,
915MHz : 2460FLOPs
メモリバンド幅 192GB/s GDDR5
計算解像度 960x540
実装手法
ここでは実装の可能性を思いつく手法を 4 つほど試してみました。3D Bounds / 2.5D Bounds / HashGrid / Tiled
それぞれの手法の分類を詳しく見てみる。
それぞれの手法の分類を詳しく見てみる。 メインのループをフォトンあたりにするか、ピクセルあたりにするか
射影するジオメトリをどう処理するか
どの空間で処理するか。
処理するシェーダステージ サンプリングを全部やるか、離散的に済ませるか
1)3 D Bounds 手法グラフィックスパイプラインのラスタライザを使って、インスタンシング等でフォトンを描画。フォトンの寄与範囲を 20 面体で表現し、干渉するオブジェクトに色を付ける。ラスタライザを使うことで高速に演算が可能になる。論文: http://graphics.cs.williams.edu/papers/PhotonHPG09/デモ: https://www.youtube.com/watch?v=GckOkpeJ3BY
2) 2.5D Bounds 手法スクリーンスペースで Z バッファを使い、フォトンを小さな球に外接するコーンとして計算。コーン形状はフォトン座標から Geometry Shader で生成する。スクリーンスペースで計算することから、3 D ではなく 2.5D と表現している。この状態では Z 方向のフォトンのバウンドは正確ではなくなる。(同じ量のフォトンを計算する場合に、3 D 方式よりも、 XY についての寄与は良くなるとのこと)
3) HashGrid Cellsセル上にフォトンを分配し、スクリーンのピクセル座標を3 D空間に投影し、その座標に近いフォトンを3D空間上で探索・収集する。セル内に hash6432shift アルゴリズムでコードテーブルを作成しフォトンを管理する。
高速化するために共有メモリ( LDS,GDS )を使いたいが、この手法では使いにくい。
4)タイルベース手法スクリーンスペースでタイル状にピクセルを区切り、そのタイルごとにフラスタムを生成。フラスタムにのりしろを付けてフォトンを分配する。Intel の tile based rendering のような手法。ここで扱うポイントライトやスポットライトの代わりにフォトンを扱う。demo https://www.youtube.com/watch?v=Aogk2r_HjjA
タイルベースの分割例( AMD Forward+)
サンプル手法
真面目に周辺フォトンを探った結果と、周辺フォトンを離散的に(たとえば 1 飛ばしで 1000 フォトン中、 500 フォトンしかサンプルしない。)バイラテラルフィルタを使ってノイズを減らした画像をみると、差はほとんどなくすことができる。
実行結果
2)“ 2.5D バウンド”と4)”タイルド”アルゴリズムの結果が良好。今回はフルの BRDF ではなく、リアルタイム向けにランバートのみの状態で良好な、タイルドアルゴリズムを詳しく見てみる。
リッチなフルのBRDF
リアルタイム向けのランバートのみ BRDF
タイルベースアルゴリズムフロー1. フォトン投射
a. 普通にフォトンを光源から投射してトレーシング2. 代表深度生成
a. 次に生成するフラスタムの深度を計算。分割されたタイル内のもっとも手前を near に、もっとも奥を far に設定
3. フォトンのタイルデータベースへの分配a. 上記投射されたデータをスクリーンスペース上でタイルに区切った
ピクセルからフラスタムの left right top bottom を指定。b. 2と合わせてフォトン収集半径分ののりしろを付けて、フラスタムカリングができる。これを使ってフォトンをタイルごとに分配。すべてのフォトンが対象。
4. フォトンのサンプリングa. 離散的フィルタ: N 飛ばしでフォトンをサンプルし、最後に飛ばし
た N倍エネルギーを増やす。5. 放射輝度の計算6. 必要に応じてバイラテラルフィルタなどノイズをごまかす
まとめアルゴリズムを CPU から GPU に移動して高速にすることができる。この際、データ構造によって性能が大きく異なる。
性能変化の傾向が CPU と GPU では違う。現状 GPU で、数百 K のフォトンをリアルタイムにサンプルして放射輝度を計算することができる。しかしながら、映画品質に向けてはまだ扱うフォトンの桁が 6ケタくらい違う。
今回の GPU 実装ネックはメモリ読み込みのレイテンシ。分割したフォトンはのりしろ分の重複があるので数が増える。フォトンのデータを読み込むのにメモリ読み込みのレイテンシの時間分毎時データ読み込みの待ちが入り、処理が進まない。
参考
参考: GPU 実装 TipsGPU のパイプラインは長い。流れが止まると後段は滞留する。→ 流れを止めない。ボトルネックになっている箇所を意識。ボトルネック解析ができたら当該箇所の負荷を緩和する。
GPU の構成に依存して強い箇所、弱い箇所があります。それぞれ、 GPU が持っているリソース・特性に合わせて調整します。
よくあるネック要因
● テクスチャネック
● 頂点アトリビュートネック
● シェーダネック
● CBDB(ROP) ネック
● メモリバンド幅ネック
● 命令ネック
● 同期ネック
● 頂点数ネック
参考文献・フォトンマッピング入門 林秀一さん
http://www.slideshare.net/ssuser2848d3/ss-25795852
・リアルタイム CG とフォトンマッピングのハイブリッドレンダリングhttp://game.watch.impress.co.jp/docs/series/3dcg/20091228_340280.html
・ intel / tile based rendering
https://software.intel.com/en-us/articles/deferred-rendering-for-current-and-future-rendering-pipelines/
・ AMD / Forward+
http://developer.amd.com/tools-and-sdks/graphics-development/
・ Fast Global Illumination Approximations on Deep G-buffers 2014http://graphics.cs.williams.edu/papers/DeepGBuffer14/#video
フォトン主軸アルゴリズム疑似コード(散布系)for (uint32_t p=0; p<photon_num; p++ ){ // フォトンループ photon[ p ].draw(); // グラフィックスパイプでメモリにフォトン位置を格納 for(uint32_t y=0; y<height; y++){ // スクリーン座標ループ for(uint32_t x=0; x<width; x++){ //pixel shader, compute shaderへ GPU化しやすい。 if( isVisible( photon[ p ].pos, x, y, eyePos ) ){ // スクリーン上でフォトンが見えるなら image[ y ][ x ] += contribution( p, x, y, z ); // 寄与をさせる。 } } }}
ピクセル主軸アルゴリズム疑似コード(収集系)for(uint32_t y=0; y<height; y++){ // スクリーン座標ループ for(uint32_t x=0; x<width; x++){ //pixel shader, compute shaderへ GPU化しやすい。 for (uint32_t p=0; p<photon_num; p++ ){ // フォトンループ if( isVisible( photon[ p ].pos, x, y, eyePos ) ){ // スクリーン上でフォトンが見えるなら image[ y ][ x ] += contribution( p, x, y, z ); // 寄与をさせる。 } } }}