OpenGL一覧

Ubuntu 15.05 on Proxmox

割と最近でたばかりの Ubuntu 15.05 を Proxmox の仮想マシンとしてインストールしてみました。しかしながら Ubuntu Desktop 日本語 Remix の iso をダウンロードしようとしたら、なぜか 15.04 という記載になってて混乱してます。
 単なる間違いだろうということであまり気にせず作業してみました。通常の Linux のインストールと同じように Proxmox の仮想マシンを構成してインストールを行いました。

そして起動後

普通に起動してきて問題はなさそうです。しかし環境の問題なのか非常に動作がもっさりとしています。top で見てみると、compizがおよそ 20% 常時持って行っていました。これについては初回なので様子見です。

openssh-server をインストールして ssh terminal で操作しているときには若干遅いかな、という程度でした。

OpenGL関連など

せっかく Ubuntu の新しいものをいれたので OpenGL に関係するところをちょっとだけ調べてみました。調査するのに必要なパッケージを以下のようにしてインストールしました。

この後に、Proxmox のコンソール上で es2_info を実行してみました。

このようになりました。インストールされた Mesa 3D は 10.5.9 であることがわかりました。またグラフィックスデバイスが使えないので、ソフトウェアレンダラーである llvmpipe が選択されています。ソフトウェアレンダラーでもこのくらいの GL拡張が使えているのは個人的に驚きでした。良い時代ですね.

そしてものは試しと es2gears を実行してみたところ以下のようにちゃんと動作しました。FPSとしては 160FPS 程度となってます。実際の見た目は Webブラウザ経由しているのでちょっとカクカクですが動作としては意外とまともに動いていると感じました。(N3150MのVM上であることも考慮して)。

その後

しばらくすると以下のように、 15.10 へのアップデートを促すダイアログが出てきました。今一番新しいのは 15.10 ということのようです。今現在の Ubuntu Desktop 日本語 Remix とのズレが多少あるということっぽいです。


OpenGL でデュアルディスプレイのフルスクリーン

なかなかやっている人も少ない OpenGL のフルスクリーンの話になります。さらにそれのデュアルディスプレイ版となるとほぼ皆無といっていい内容かと思います。ちなみに先日の Windows 10 では使えるのか?と試した話の延長です。

OpenGL では DirectX とは違い、それぞれの画面で OpenGL のコンテキストを作り、必要に応じてリソースを共有できるようにします。あとはコレを wglMakeCurrent で切り替えつつ描画を行う、といった感じで処理するので、別段難しいことはここにはないです。
フルスクリーン化するAPIは OpenGL にはないため、 Windows API で最前面で全画面をおおうウィンドウを作ります。

最大の問題点

OpenGL APIでフルスクリーン化する機能を備えていないため、 Windows API で何とかする感じになっています。つまりは OpenGL はフルスクリーンについて何も考慮をされていないといってもよいでしょう(言い過ぎかもしれませんが・・・)
試しに近年の Windows OS でこれらの挙動を確認してみました。以下に示すようにデバイスとOSと依存して使えない環境もあるようです。
(機材の関係で、環境をそろえることが出来なかったり、ばらばらだったりしますがご了承下さい)。

OS デバイス 判定
Windows7 Geforce650Ti OK
Windows8 Geforce750Ti NG
Windows8.1Update Geforce750Ti OK
Windows10(build10240) Geforce750Ti OK

ここでの使えないというのは、他方のウィンドウに描画される内容がとても低フレームレートになってしまい、なめらかな描画更新ができないという状況を意味しています。
そもそもそれぞれの画面内をクリックするような操作を行うと、一瞬おかしな映像が見えてしまったりするのですが・・・。
試したドライバは、現在の最新版 353.30 でした。NVIDIA というと OpenGL 対応を積極的に行っているメーカーのような印象があり、うまく動くと思っていただけに今回の件は残念でした。

続いて AMD (RADEON) で同じことを確認してみました。

OS デバイス 判定
Windows7 RADEON HD 7750 未チェック
Windows8 RADEON HD 7750(14.4) OK
Windows8.1Update RADEON HD 7750(14.4) OK
Windows10(build10240) RADEON HD 7750(15.7) OK

こちらの場合にはそれぞれの画面内をクリックするような操作を行っても、一瞬おかしな映像が見えたりしませんでした.

まとめ

OpenGL でデュアルディスプレイのフルスクリーン対応は Windows8 が例外的な動きをするようなので、難しそうです。もしかしたらいつか NVIDIA ドライバが更新されて正常に動くかもしれませんが、今となっては比較的古い Windows8 なので見込みは薄そうです。


Windows10 で OpenGL 使えるのか?

Windows10 の正式なリリースが間もなくとなってきました。この Windows10 で DirectX 12 が使えるようになるというのは、各所で語られていて有名な話ですが、それと対を成す OpenGL は生きてるんだろうかと思って、まずは軽く調べてみました。

opengl-capture-win10

軽くといいつつ、デュアルディスプレイでそれぞれにフルスクリーンとなる OpenGL アプリケーションを動かしてみました。上記の図は その時の様子を PrintScreen でキャプチャしたものです。本来は同じクリアカラーおよび同じような位置で三角形を書いているのですが、なんかおかしなことになっています。実際のモニターでは2つの画面でこのようなズレはないので、不思議なところです。
ちなみに、2つのディスプレイ解像度が違うため、アスペクト比がずれているので全く同じ絵にはなりません。

このときの OpenGL コンテキストの情報を出してみるとこんな感じでした。

今のドライバだと NVIDIA で OpenGL 4.5 が使用可能なようです。ドライバが入っていなくて、OpenGL のエミュレーションというかリファレンスドライバで動く、なんて状況ではなさそうです。

まとめ

とりあえず NVIDIA ドライバでは OpenGL はそのまま使えそうです。他の AMD や Intel のほうで DirectX12 & OpenGL が両方サポートされるかどうかは、徐々に調べてみようと思います。
それと、 PrintScreen ってこんな挙動だっけと不思議な部分があるので、Windows7, 8.1 あたりで同じだったかも調査してみたいと思います。

その他

OpenGL でフルスクリーンは調べるとよく出てくるのですが、そこ止まりで、複数ディスプレイで OpenGL をやっている例を見かけませんでした。相当マイナーな部分なのでしょうか。こうも事例が見つからないと、たまたま動いているだけ感を感じます。


BC7について段階的にデコードしてみた

BC7のCPUデコーダーを作っている過程でおもしろいものが確認できたので記事にしてみました。当たり前の話ではあるのですが、視覚化されたケースって無いようなので。
BC7 はいわゆる第2世代のテクスチャ圧縮技術で、各ブロックごとに最適なモードを選択してデータを圧縮しています。このブロックがどんな風に割り当てられているかを、ブロックごとの色分けで塗ってみたら以下のような結果を得られました。

image_partition

この段階でも各ブロックの特徴によってモード選択されているのが確認できます。そのためおおよその画像の検討が付く程度にはなっています。これらのブロック種別を順番に展開してみます。 続きを読む


ASTCの圧縮ノイズを調べてみた

今回は期待のASTC圧縮のノイズを調べてみました。

ASTCについて

詳しいことは各所のサイトで触れられていますのでここでは簡単に。 Adaptive Scalable Texture Compression の略で、ARM が開発しました。DXTCがS3の特許関係で色々とあったためか、 ASTC はロイヤリティフリーなことも取り上げられています。
基本的には他の現世代のテクスチャ圧縮と同じくブロックごとのモードを多数持っていることが特徴です。ASTC 固有の特徴は、なんといってもブロックサイズの変更ができるということではないかと思います。

実験

ASTCではブロックサイズを変更することができ、許容できる範囲で BPP を落として削減することができます。試行錯誤の余地があるといえます。
ここでは BC7 や PVRTC への対抗と考えて、それと同じレベルの BPP でチェックをしてみたいと思います。

圧縮のためのツールとしては Mali Texture Compression Tool を用いています。圧縮品質としては最大の品質レベルを選択してデータを作成しました。

ASTC 8BPP(4×4)での結果

8BPPとなるように 4×4 ブロックで圧縮を行いました。この場合は以下のような結果となりました。次の規格レベルだけあって予想通り綺麗に圧縮できていると思われます。左右に並べたくらいではちょっとわかりません。

compare_std_astc_sample01

compare_std_astc_sample02

ツールのほうでは圧縮前後でノイズ具合も表示できるのでこちらの画像も掲載しておきます。
ノイズは割と控えめな感じかと思われます。 [続きを読む]


ETC2の圧縮ノイズを調べてみた

今回は OpenGL ES 3.0 以降で使えるようになった ETC2 について試してみました。アルファチャンネル入りでの圧縮形式として標準的に使えるようになった形式です。基本的な実装方針は ETC1 の拡張したイメージになっています。

データの作成は Mali Texture Compression Tool を用いて行っています。品質は最高品質を選んでいますが、待てないほどではないにしろ割と時間がかかるかなという印象です。その分画質はどうなっているか確認してみたいと思います。

左がオリジナル、右が ETC2 圧縮したものですがどうでしょうか。違いはぱっと見た感じでわかるでしょうか?

compare-etc2-sample01
compare-etc2-sample02

個人的には ETC1 のころと違ってよく綺麗に圧縮できているのではないかと思っています。そこで今度はこれらの一部分を拡大して確認してみたいと思います。 続きを読む


PVRTC2の圧縮ノイズを調べてみた

今回は PVRTC2 の圧縮について、どのくらいの劣化が起こるのかを調べてみました。 PVRTC2 って有名なようでイマイチな感じで、これを検索キーワードにしても PVRTC1 の 2BPP モードがヒットする感じです。 PVRTC-I, PVRTC-II という表記の方がいいのかもしれませんが、 imgtec のブログでは PVRTC, PVRTC2 という記述をされているようです。

PVRTC2について

PVRTC2 は PVRTC をさらに拡張した形式となっています。基本的なブロックフォーマットはそのままに、ブロックごとの2色を記している最上位ビットに別の意味を持たせた感じにしています。それぞれに Opaque なビットは不要、他方から判定すればよし!というのは納得がいきます。
この別の意味を付与されたビットを HardBit と呼んでいます。これにより最近流行のブロックのモードを追加するということを実現しており、追加されたモードは Non-interpolated(非補間), Local palette(ローカルパレット) モードの2種類となっています。これらの仕組みから PVRTC2 は画質の向上のために用意されているようです。

参考: PVRTC,PVRTC2についての Imagination Technologies のブログ

実験

以前の BC7 のノイズ検証でも使ったデータを利用して確認してみます。PVRTC2 データの作成ついては、今のところ PVRTexTool で行えます。
このツールは前後でのノイズ(エラー)も表示させることが可能なため、以前のように別アプリで処理しなくても簡単に確認できます。ここではそのスクリーンショットを載せることで見ていきたいと思います。
注意事項としては、 BC7 と PVRTC2 を単純に比較してはいけないということです。お気づきかと思いますが、 BC7 は 8bit per pixel(BPP) であり、 PVRTC2 は 4BPP であるということです。つまり PVRTC2 が BC7 よりも2倍圧縮率が高いということで、すなわち BC7 より見た目が悪くても当然ということです。

pvrtc2-noise-sample01

pvrtc2-noise-sample02

よく言われていることではありますが、PVRTC系はアルファチャンネルも持たせられるがその場合カラーの品質が落ちる、というのが今回も健在のようです。最初の例ではアルファ抜きの部分にもノイズがありますし、アルファが変化するブロックにあるカラーブロックがひどいノイズとなっています。
アルファ不要のケースにおいてはノイズは階調が変わる輪郭部分に大きく発生していますが、等倍の目視ではあまり感じられないかと思います。 続きを読む


BC7の圧縮ノイズについて調べてみた

優秀だという BC7 圧縮の品質がどんなものか調べてみました。
そのためにはそこそこの品質以上の画像データが必要だったので友人に協力してもらい画像を使わせてもらっています。
この場を借りてお礼申し上げます。

BC7への圧縮については Codeplex からダウンロードできる Microsoft の TexConv を使用しています。この最高品質となる CPU で処理した結果ではなく、 GPU を用いた速度とのバランスがとれているであろうモードを選択しています。

比較

いきなりですが圧縮前後の画像を比較してみます。
左が圧縮前、右が圧縮後のデータです。圧縮ノイズなどは確認できるでしょうか?自分では等倍でぱっと見た感じわかりませんでした。心持ち髪の毛曲線部とアルファの部分でノイズが気になるかも程度です。
compare_std_bc7_sample01
compare_std_bc7_sample02

続きを読む


OpenGLでBC7テクスチャ圧縮を使う

今回は今までにやっていそうでやっていなかった OpenGL で圧縮テクスチャを使用する方法です。
基本的には、定番のDXT1,DXT3,DXT5 などの形式をロードする方法と全く同じなのですが、意外と誰もBC6H, BC7 で書いていなかったため、情報として残しておこうと思った次第です。

BC7テクスチャ圧縮について

詳しいことは他のサイトにお任せしますが、BC7はアルファチャンネル付きでも見た目の情報劣化が少ないテクスチャ圧縮形式です。従来はこの領域では DXT5 が使用されましたが、DXT5 は意外と汚いという認識があるようです。BC7はこの点を改善していますが、今のところ圧縮時間がそれなりにかかるのが懸念点となっています。
とはいっても、GPUの支援を使い一定レベルの変換は割と早くできますし、今となっては問題も少ないんじゃないでしょうか

BC7テクスチャをどう作るか

テクスチャを使用するプログラムは難しくないのですが、データを作成するところが現時点では問題になるかと思います。
いくつか方法はあるのですが、ここではマイクロソフトの公開している方法を紹介したいと思います。

DirectXTex プロジェクト一式をダウンロードすると、その中に TexConv というプロジェクトが含まれています。これをVisualStudio で開いて、ビルドするとコマンドラインツールとしての TexConv ができあがります。

詳しいオプションはツールのヘルプを見てほしいのですが、大体以下のような感じで使えます。入力フォーマットもそこそこ対応しているようです。

通常だとGPUが支援として使える状況であればそちらを使うようで、 -nogpu というオプションをつけるとフルにCPUで演算するモードとなります。
どのくらい重い処理なのか一度試してみるのもおもしろいと思います。2048×2048 なデータで試してみると15~20分くらい返ってこなかった気がします・・・。

BC7 形式で dds 出力すると従来の DDS と違い、DX10 用のヘッダも格納されている点に注意して、ロードプログラムを作成します。

プログラム

ロードする際の肝は、従来と変わらずの glCompressedTexImage2D 関数を使用します。気をつけるポイントは前に述べたデータ開始位置が異なることでしょうか。
DDSを識別するマジックナンバー、DDSヘッダ、DX10ヘッダ の分を先頭からずらした位置が BC7データの開始位置となります。

コード例としてはこんな感じになりました。
BC7 をロードする際には、 GL_COMPRESSED_RGBA_BPTC_UNORM_ARB をフォーマットとして設定して glCompressedImage を呼び出します。また本来ならば、DDSのヘッダから画像解像度を取り出して使うべきですが、手抜きして直接 256×256 を指定してしまっています。

OpenGL-BC7

補足

BC6Hの場合には、GL_COMPRESSED_RGB_BPTC_SIGNED_FLOAT_ARB, GL_COMPRESSED_RGB_BPTC_UNSIGNED_FLOAT_ARB を指定します。
また、BC7のSRGBが要求されるときには、GL_COMPRESSED_SRGB_ALPHA_BPTC_UNORM_ARB を使用します。
それ以外はロードの方法に変更はありません。


OpenGLでOut of memory とメモリの関係 (AMD)

今まで NVIDIA のもので調べていたので今回は同じプログラムを AMD Radeon 5450 を使ってデータ取得してみました。

  • Windows 7 x64 (2GB)
  • AMD Radeon HD 5450 (1GB)
  • ドライバは Catalyst Omega 14.12

プログラムは OpenGL を用いて 32MB 単位で頂点バッファを 300 フレーム間隔で確保していくものです。作成後、 Out of memory のエラーが返ってきたら終了します。

実験結果

何度か動かしてみましたが、 GL_OUT_OF_MEMORY のエラーが取得できませんでした。あふれた状態になったと思われるときには、アプリケーションがフリーズ状態に陥りました。 SwapBuffers の実行内部で無限ループしているような気配でした。
 この状況になるまでのデータで、システムの使用メモリ、 VRAM の使用量、共有メモリの使用量をグラフ化してみたものが以下のようになります。 NVIDIA の場合とは傾向が違っていておもしろいです。

radeon_ogl_outofmemory_log
今回の場合は、 VRAM に配置できる場合にはそちらに配置して、システムのメモリは消費しないようにみえます。実際にこのタイミングではプライベートヒープが増えているような感じではありませんでした。 観測タイミング次第によっては glBufferData の中身のテンポラリの DMA 転送タイミングで作業バッファぽいものが見えたりしますが、数フレーム後解放されたりしました。 VRAM に配置できない状況になったときに、初めてシステムのメモリを消費しての共有メモリ使用増加が観測できました。おおよそ 1.6GB ほどの使用量になったときにアプリケーションがフリーズ状態に陥ったように見えます。この環境ではビデオアダプタのプロパティで確認できたのが「利用可能な全グラフィックスメモリ 1791MB」とあり、最大値であるこの値にまで到達したのかなと思っています。

感想

AMD のグラフィックスドライバは余計な(?)システムメモリを消費しなかったので、 OpenGL 実装でも無駄はないという点に関心しました。一方で、メモリあふれのエラーを検知できないのはマズイですね。無駄なメモリは確保しないから、溢れさせないよう気をつけてアプリケーションを実装しましょう、ということでしょうか。

おまけ

同じようなテストを Windows8 (64bit) に切り替えて行ってみました。おおよそ同じ傾向になりました。ただシステムメモリの細かな変動が観測され、作業メモリとして使用している部分がみえたのかなと思っています。(これは以前に glBufferData 直後での内部動作でそのような動きを見せたためです。)
ドライバが標準的に導入されたものを使用し、 Catalyst Omega ではない点ももしかすると影響しているかもしれません。
radeon_ogl_outofmemory_log_win8