世の中の多くの Windows 環境で安定して使えるグラフィックス API は DirectX11 や OpenGL といったところだと思います。
Vulkan API は新しい API のため、既存のライブラリやフレームワークではまだサポートされていなかったりします。そのような状況のためか、 NIVIDA の Vulkan Extension では、 Vulkan とその他 API でやりとりするための機能が用意されました。
また現時点においては、 Khronos の KHX 拡張としても整備が進みそうな気配です。NVIDIA だけでなくサポート範囲が広がってくれることに期待です。
紹介
そもそものちゃんとした記事はこちらの Getting Vulkan Ready for VR になります。ここでは NVIDIA が用意した拡張や DirectX11 のテクスチャを Vulkan のテクスチャとして使う事例が紹介されています。
NVIDIA が用意した拡張が以下の通りです。テクスチャを Vulkan – D3D11 と跨ぐにはこれらの拡張を全て使用することになります。
- VK_NV_external_memory
- VK_NV_external_memory_capabilities
- VK_NV_external_memory_win32
- VK_NV_win32_keyed_mutex
- VK_NV_dedicated_allocation
現在の Vulkan バージョン 1.0.48 の仕様書にはこれらの説明も記載されています。それでも説明に関しては NVIDIA のサイトの記事の方がわかりやすいと思います。
実験
DirectX11 でレンダーターゲットとして描画したテクスチャを Vulkan 側で使用するプログラムを作成してみました。
実行結果は以下のようになりました。中央の四角ポリゴンにテクスチャを貼っていますが、これが DirectX11 (D3D11) で描画したものになっています。
この環境ですが、 Vulkan SDK 1.0.42 で、 Windows10 x64, NVIDIA ドライバ 381.65 を使用しています。同じプログラムを Windows7 の環境で実行したらうまくテクスチャの共有というかインポートが成功せず、表示されませんでした・・・。どうやら
D3D11_RESOURCE_MISC_SHARED_NTHANDLE が Windows7 で指定することが出来ず、それに対応したコードにする必要がありそうでした。
NVIDIA のページを確認してみたところ、この分岐コードについて存在したので自分の手抜き実装による問題だった、ということのようです。
感想
今回のこの拡張について、 Vulkan の Validation Layer がちゃんと対応できていない気がします。VkWin32KeyedMutexAcquireReleaseInfoNV をコマンドキューに積んで実行すると、プログラムが落ちました。この部分については validation Layer でのエラー警告も出ていなかったのと、無効化すると正常に動いているようだったのでひとまずは使わないようにして動かしています。
さすがにこれらが NV 拡張のため、 Validation Layer の対応の方も優先度低いというのが予想できますが、個人的にはキューに積んで後で落ちる、というのは困ったなというところです。
OpenGL のときにも NVIDIA は DirectX との interop を拡張で用意してくれましたし、今回もまたこのような拡張が割と早い時期に用意してくれたということに感謝です。
他のベンダーも KHX 拡張のほうで追従してくれたらと願っています。ちなみに KHX のほうは今回全く触っていませんでした。何せ情報がほとんど無く、ちゃんと仕様書を読まなければいけない感があります。まず次にチャレンジするのは Vulkan のテクスチャを利用する方ですね。