iRender : Global Illumination with iPhone.

by syoyo

irender.png

I’ve ported ambient occlusion renderer to iPhone as a OpenGL ES application.

http://lucille.svn.sourceforge.net/svnroot/lucille/angelina/irender

irender.tar.gz (project files)

The renderer core itself is simple and I already ported it to many platforms.

Proce55ing
Flash10
JavaScript
Performance comparison

Unfortunately I haven’t real iPhone, so I just tested that the renderer runs correctly in the simulator.
I don’t know how much the rendering time is in real iPhone device.

[Ja]

iPhone にアンビエントオクルージョンレンダラをポーティングしてみた.
とりあえず OpenGL ES が使えるということで、iPhone の開発環境(Cocoa?)も ObjC もまったくわからない状態で,
レンダラ部分を無理矢理 C + GL だけ使って組み込むことで実現してます.
2 時間くらいで作ったのでやっつけです. ソースもいいかげん.

残念ながら実機がないので速度がどれくらいかは分かりません.
シミュレータだと結構早いです. Core2 2.15GHz で、ネイティブ C が 2.5 秒なのに, iPhone simulator だと 5 秒ほど.

あ、ちなみにレンダリングは一回やるだけで、あとはテクスチャにして回転させているだけです.
毎回回転するたびにレンダリングを行っているわけではありません.

iPhone は 1,000 万台も普及しているとのことなので、
分散レンダリングを iPhone でやるのも面白いんじゃないかなぁと思っています.

iPhone で画像テクスチャを貼付ける

GLES では glDrawPixels が無いということが分かったので、
今回レンダリング結果の画像表示はテクスチャ経由で行っています.

参考までに、 iPhone で OpenGL ES を使ってテクスチャを貼付けて表示する部分はこうなってます.
(タブの設定のせいでインデントがずれているところがあります)

テクスチャを使う手順はこんな感じ.

– テクスチャになるデータを配列で用意
– (最初だけ)テクスチャオブジェクトを作成 (glGenTextures)
– テクスチャオブジェクトをバインド (glBindTexture)
– (最初だけ)テクスチャ拡縮フィルタを設定 (glTexParameterf)
– (更新するときだけ)テクスチャになるデータをテクスチャメモリに転送 (glTexImage2D)
– テクスチャマッピングを有効にする (glEnable(GL_TEXTURE_2D))
– テクスチャ座標アレイを有効にする (glEnableClientState(GL_TEXTURE_COORD_ARRAY))
– テクスチャ座標ポインタを設定 (glTexCoordPointer)
– ポリゴン描画

矩形ポリゴンに矩形テクスチャを貼付けています. テクスチャ座標は texCoords で与えています.
テクスチャデータは width*height*4 bytes の GLubyte 型の配列で用意すれば OK.
よって配列をあとは自由にいじればピクセル処理を行い、それを GLES を通して表示することができます.

GLES だとテクスチャデータの更新は glTexImage2D でやるしかないのかな?
それだと更新コストが高いと思うので、あまり毎フレーム画像をアニメーションさせるというのには向かないかもしれません.

それにしても、しばらくぶりに OpenGL を使いました(SW raytracing に移行しつつあるので OpenGL を使う理由がなくなってきている).
以外と API やら中身の動作様式を覚えているものです.

[追記]

早速実機を持っているひとに試してもらいました.

iPhone3G -> 130 秒 

う、遅すぎ…

でも実は、こんなのが原因のようです.

浮動小数点演算の高速化
http://d.hatena.ne.jp/kstn/20081031/1225458244

というわけで、-mthumb オプションを無効にして再度計測してもらいました.

130 秒(-mthumb あり. デフォルト) -> 38 秒(-mthumb オフ)

結構早くなりました.

ただ、-mthumb を付けると(デフォルトの動作)、コードサイズは小さくなるという効果があるとのこと.
多くのアプリは浮動小数点演算は多用しないので、このオプションがデフォルトで有効になっているようです.

やはりパフォーマンスについて調べるときにはアセンブラレベルでちゃんと確認したいですね.
残念ながら実機がないと、実機向けコンパイル(armv6 ターゲット)の段階でライセンスが何たらと出てコンパイルがまず走らないので、アセンブラ出力が確認できません… 実機を手に入れるしかないのか…

ちなみに CPU(armv6) 自体には VFP と呼ばれる SIMD 命令があるので、これを使えるようになるともっと早くなるかも.
でも iPhone SDK 経由で使えるのかな?(たとえば、インラインアセンブラを使ってとか).

VFP 向けの SIMD 数学ライブラリはありました.
http://code.google.com/p/vfpmathlibrary

インラインアセンブラを使っています.なのでたぶんユーザ側でもきっと VFP を使えるはず.

MUDA の VFP バックエンドをちょっと書きたくなってきた.
でも今は MUDA は C コードを吐くので、 gcc 側でイントリンジックスなりで VFP に対応してくれていないとダメなんですよね.
AVX の時も思ったけど、やはり gcc とかのコンパイラの対応度に依存しないように、
いずれは直接最適化されたアセンブラを吐く、自作の SIMD 命令むけコンパイラを書いたほうがいいんだろうな.

Advertisements