From b3dfe383c6d31ff3dbd76dcfb32de8d536382f3e Mon Sep 17 00:00:00 2001 From: lucy96chen <47800040+lucy96chen@users.noreply.github.com> Date: Mon, 4 Oct 2021 09:46:33 -0700 Subject: Get native handles for TextureResource and BufferResource (#1960) * Added getNativeHandle() to TextureResource and BufferResource; Implemented getNativeHandle() in Vulkan and D3D12; Added new unit test files for the aforementioned implementation * Added missing getNativeHandle() implementations to renderer-shared.cpp and CUDA * Finished new getNativeHandle() unit tests for ITextureResource and IBufferResource; Modified ICommandQueue and ICommandBuffer unit tests to call QueryInterface to convert to IUnknown then back and compare resulting pointers for equality * Unit tests updated and pass locally * Cast m_buffer.m_buffer and m_image to uint64_t --- .../gfx-unit-test-tool/gfx-unit-test-tool.vcxproj | 6 +- .../gfx-unit-test-tool.vcxproj.filters | 10 +- slang-gfx.h | 9 ++ .../gfx-unit-test/existing-device-handle-test.cpp | 8 +- tools/gfx-unit-test/get-buffer-handle-test.cpp | 98 -------------------- .../get-buffer-resource-handle-test.cpp | 102 +++++++++++++++++++++ tools/gfx-unit-test/get-cmd-buffer-handle-test.cpp | 100 ++++++++++++++++++++ tools/gfx-unit-test/get-cmd-queue-handle-test.cpp | 84 +++++++++++++++++ tools/gfx-unit-test/get-queue-handle-test.cpp | 82 ----------------- .../get-texture-resource-handle-test.cpp | 94 +++++++++++++++++++ tools/gfx/cuda/render-cuda.cpp | 12 +++ tools/gfx/d3d12/render-d3d12.cpp | 12 +++ tools/gfx/debug-layer.cpp | 10 ++ tools/gfx/debug-layer.h | 2 + tools/gfx/renderer-shared.cpp | 11 +++ tools/gfx/renderer-shared.h | 2 + tools/gfx/vulkan/render-vk.cpp | 12 +++ 17 files changed, 466 insertions(+), 188 deletions(-) delete mode 100644 tools/gfx-unit-test/get-buffer-handle-test.cpp create mode 100644 tools/gfx-unit-test/get-buffer-resource-handle-test.cpp create mode 100644 tools/gfx-unit-test/get-cmd-buffer-handle-test.cpp create mode 100644 tools/gfx-unit-test/get-cmd-queue-handle-test.cpp delete mode 100644 tools/gfx-unit-test/get-queue-handle-test.cpp create mode 100644 tools/gfx-unit-test/get-texture-resource-handle-test.cpp diff --git a/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj b/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj index ec0c7f3c5..b5be6aaa7 100644 --- a/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj +++ b/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj @@ -274,8 +274,10 @@ - - + + + + diff --git a/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj.filters b/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj.filters index 73763e62b..ccbb1a482 100644 --- a/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj.filters +++ b/build/visual-studio/gfx-unit-test-tool/gfx-unit-test-tool.vcxproj.filters @@ -23,10 +23,16 @@ Source Files - + Source Files - + + Source Files + + + Source Files + + Source Files diff --git a/slang-gfx.h b/slang-gfx.h index ac2b7b774..1b587fd9f 100644 --- a/slang-gfx.h +++ b/slang-gfx.h @@ -304,8 +304,13 @@ public: int elementSize = 0; ///< Get the element stride. If > 0, this is a structured buffer Format format = Format::Unknown; }; + + // Pointer to the buffer resource. + typedef uint64_t NativeHandle; + virtual SLANG_NO_THROW Desc* SLANG_MCALL getDesc() = 0; virtual SLANG_NO_THROW DeviceAddress SLANG_MCALL getDeviceAddress() = 0; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) = 0; }; #define SLANG_UUID_IBufferResource \ { \ @@ -401,7 +406,11 @@ public: int64_t strideZ; }; + // A pointer to the resource if D3D12. + typedef uint64_t NativeHandle; + virtual SLANG_NO_THROW Desc* SLANG_MCALL getDesc() = 0; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) = 0; }; #define SLANG_UUID_ITextureResource \ { \ diff --git a/tools/gfx-unit-test/existing-device-handle-test.cpp b/tools/gfx-unit-test/existing-device-handle-test.cpp index a8ebb67c9..2a4ffea26 100644 --- a/tools/gfx-unit-test/existing-device-handle-test.cpp +++ b/tools/gfx-unit-test/existing-device-handle-test.cpp @@ -100,7 +100,7 @@ namespace gfx_test { if ((api & context->enabledApis) == 0) { - return SLANG_IGNORE_TEST; + SLANG_IGNORE_TEST; } Slang::ComPtr device; IDevice::Desc deviceDesc = {}; @@ -116,7 +116,7 @@ namespace gfx_test deviceDesc.deviceType = gfx::DeviceType::Vulkan; break; default: - return SLANG_IGNORE_TEST; + SLANG_IGNORE_TEST; } deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; @@ -125,7 +125,7 @@ namespace gfx_test auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); if (SLANG_FAILED(createDeviceResult)) { - return SLANG_IGNORE_TEST; + SLANG_IGNORE_TEST; } IDevice::NativeHandle handle = {}; @@ -136,7 +136,7 @@ namespace gfx_test auto createTestDeviceResult = gfxCreateDevice(&testDeviceDesc, testDevice.writeRef()); if (SLANG_FAILED(createTestDeviceResult)) { - return SLANG_IGNORE_TEST; + SLANG_IGNORE_TEST; } existingDeviceHandleTestImpl(testDevice, context); diff --git a/tools/gfx-unit-test/get-buffer-handle-test.cpp b/tools/gfx-unit-test/get-buffer-handle-test.cpp deleted file mode 100644 index c8bd9bca5..000000000 --- a/tools/gfx-unit-test/get-buffer-handle-test.cpp +++ /dev/null @@ -1,98 +0,0 @@ -#include "tools/unit-test/slang-unit-test.h" - -#include "slang-gfx.h" -#include "gfx-test-util.h" -#include "tools/gfx-util/shader-cursor.h" -#include "source/core/slang-basic.h" - -#if SLANG_WINDOWS_FAMILY -#include -#endif - -using namespace gfx; - -namespace gfx_test -{ - void getBufferHandleTestImpl(IDevice* device, UnitTestContext* context) - { - // We need to create a transient heap in order to create a command buffer. - Slang::ComPtr transientHeap; - ITransientResourceHeap::Desc transientHeapDesc = {}; - transientHeapDesc.constantBufferSize = 4096; - GFX_CHECK_CALL_ABORT( - device->createTransientResourceHeap(transientHeapDesc, transientHeap.writeRef())); - - auto commandBuffer = transientHeap->createCommandBuffer(); - struct CloseComandBufferRAII - { - ICommandBuffer* m_commandBuffer; - ~CloseComandBufferRAII() - { - m_commandBuffer->close(); - } - } closeCommandBufferRAII{ commandBuffer }; - ICommandBuffer::NativeHandle handle = 0; - GFX_CHECK_CALL_ABORT(commandBuffer->getNativeHandle(&handle)); - if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) - { - // Check that the handle is not null, which is defined as 0. - SLANG_CHECK(handle != 0); - } -#if SLANG_WINDOWS_FAMILY - else - { - auto d3d12Handle = (ID3D12GraphicsCommandList*)handle; - Slang::ComPtr testHandle; - GFX_CHECK_CALL_ABORT(d3d12Handle->QueryInterface(testHandle.writeRef())); - } -#endif - } - - void getBufferHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) - { - if ((api & context->enabledApis) == 0) - { - SLANG_IGNORE_TEST; - } - Slang::ComPtr device; - IDevice::Desc deviceDesc = {}; - switch (api) - { - case Slang::RenderApiFlag::D3D11: - deviceDesc.deviceType = gfx::DeviceType::DirectX11; - break; - case Slang::RenderApiFlag::D3D12: - deviceDesc.deviceType = gfx::DeviceType::DirectX12; - break; - case Slang::RenderApiFlag::Vulkan: - deviceDesc.deviceType = gfx::DeviceType::Vulkan; - break; - default: - SLANG_IGNORE_TEST; - } - deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; - const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; - deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); - deviceDesc.slang.searchPaths = searchPaths; - auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); - if (SLANG_FAILED(createDeviceResult)) - { - SLANG_IGNORE_TEST; - } - - getBufferHandleTestImpl(device, context); - } - -#if SLANG_WINDOWS_FAMILY - SLANG_UNIT_TEST(getBufferHandleD3D12) - { - return getBufferHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); - } -#endif - - SLANG_UNIT_TEST(getBufferHandleVulkan) - { - return getBufferHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); - } - -} diff --git a/tools/gfx-unit-test/get-buffer-resource-handle-test.cpp b/tools/gfx-unit-test/get-buffer-resource-handle-test.cpp new file mode 100644 index 000000000..35ad167f2 --- /dev/null +++ b/tools/gfx-unit-test/get-buffer-resource-handle-test.cpp @@ -0,0 +1,102 @@ +#include "tools/unit-test/slang-unit-test.h" + +#include "slang-gfx.h" +#include "gfx-test-util.h" +#include "tools/gfx-util/shader-cursor.h" +#include "source/core/slang-basic.h" + +#if SLANG_WINDOWS_FAMILY +#include +#endif + +using namespace gfx; + +namespace gfx_test +{ + void getBufferResourceHandleTestImpl(IDevice* device, UnitTestContext* context) + { + const int numberCount = 1; + float initialData[] = { 0.0f }; + IBufferResource::Desc bufferDesc = {}; + bufferDesc.sizeInBytes = numberCount * sizeof(float); + bufferDesc.format = gfx::Format::Unknown; + bufferDesc.elementSize = sizeof(float); + bufferDesc.allowedStates = ResourceStateSet( + ResourceState::ShaderResource, + ResourceState::UnorderedAccess, + ResourceState::CopyDestination, + ResourceState::CopySource); + bufferDesc.defaultState = ResourceState::UnorderedAccess; + bufferDesc.cpuAccessFlags = AccessFlag::Write | AccessFlag::Read; + + ComPtr buffer; + GFX_CHECK_CALL_ABORT(device->createBufferResource( + bufferDesc, + (void*)initialData, + buffer.writeRef())); + + IBufferResource::NativeHandle handle; + GFX_CHECK_CALL_ABORT(buffer->getNativeHandle(&handle)); + if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) + { + SLANG_CHECK(handle != NULL); + } +#if SLANG_WINDOWS_FAMILY + else + { + auto d3d12Handle = (ID3D12Resource*)handle; + Slang::ComPtr testHandle1; + GFX_CHECK_CALL_ABORT(d3d12Handle->QueryInterface(testHandle1.writeRef())); + Slang::ComPtr testHandle2; + GFX_CHECK_CALL_ABORT(testHandle1->QueryInterface(testHandle2.writeRef())); + SLANG_CHECK(d3d12Handle == testHandle2.get()); + } +#endif + } + + void getBufferResourceHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) + { + if ((api & context->enabledApis) == 0) + { + SLANG_IGNORE_TEST; + } + Slang::ComPtr device; + IDevice::Desc deviceDesc = {}; + switch (api) + { + case Slang::RenderApiFlag::D3D11: + deviceDesc.deviceType = gfx::DeviceType::DirectX11; + break; + case Slang::RenderApiFlag::D3D12: + deviceDesc.deviceType = gfx::DeviceType::DirectX12; + break; + case Slang::RenderApiFlag::Vulkan: + deviceDesc.deviceType = gfx::DeviceType::Vulkan; + break; + default: + SLANG_IGNORE_TEST; + } + deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; + const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; + deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); + deviceDesc.slang.searchPaths = searchPaths; + auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); + if (SLANG_FAILED(createDeviceResult)) + { + SLANG_IGNORE_TEST; + } + + getBufferResourceHandleTestImpl(device, context); + } + + SLANG_UNIT_TEST(getBufferResourceHandleD3D12) + { + return getBufferResourceHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); + } + + SLANG_UNIT_TEST(getBufferResourceHandleVulkan) + { + return getBufferResourceHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); + } + +} diff --git a/tools/gfx-unit-test/get-cmd-buffer-handle-test.cpp b/tools/gfx-unit-test/get-cmd-buffer-handle-test.cpp new file mode 100644 index 000000000..62a00c3c2 --- /dev/null +++ b/tools/gfx-unit-test/get-cmd-buffer-handle-test.cpp @@ -0,0 +1,100 @@ +#include "tools/unit-test/slang-unit-test.h" + +#include "slang-gfx.h" +#include "gfx-test-util.h" +#include "tools/gfx-util/shader-cursor.h" +#include "source/core/slang-basic.h" + +#if SLANG_WINDOWS_FAMILY +#include +#endif + +using namespace gfx; + +namespace gfx_test +{ + void getBufferHandleTestImpl(IDevice* device, UnitTestContext* context) + { + // We need to create a transient heap in order to create a command buffer. + Slang::ComPtr transientHeap; + ITransientResourceHeap::Desc transientHeapDesc = {}; + transientHeapDesc.constantBufferSize = 4096; + GFX_CHECK_CALL_ABORT( + device->createTransientResourceHeap(transientHeapDesc, transientHeap.writeRef())); + + auto commandBuffer = transientHeap->createCommandBuffer(); + struct CloseComandBufferRAII + { + ICommandBuffer* m_commandBuffer; + ~CloseComandBufferRAII() + { + m_commandBuffer->close(); + } + } closeCommandBufferRAII{ commandBuffer }; + ICommandBuffer::NativeHandle handle = 0; + GFX_CHECK_CALL_ABORT(commandBuffer->getNativeHandle(&handle)); + if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) + { + SLANG_CHECK(handle != NULL); + } +#if SLANG_WINDOWS_FAMILY + else + { + auto d3d12Handle = (ID3D12GraphicsCommandList*)handle; + Slang::ComPtr testHandle1; + GFX_CHECK_CALL_ABORT(d3d12Handle->QueryInterface(testHandle1.writeRef())); + Slang::ComPtr testHandle2; + GFX_CHECK_CALL_ABORT(d3d12Handle->QueryInterface(testHandle2.writeRef())); + SLANG_CHECK(d3d12Handle == testHandle2.get()); + } +#endif + } + + void getBufferHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) + { + if ((api & context->enabledApis) == 0) + { + SLANG_IGNORE_TEST; + } + Slang::ComPtr device; + IDevice::Desc deviceDesc = {}; + switch (api) + { + case Slang::RenderApiFlag::D3D11: + deviceDesc.deviceType = gfx::DeviceType::DirectX11; + break; + case Slang::RenderApiFlag::D3D12: + deviceDesc.deviceType = gfx::DeviceType::DirectX12; + break; + case Slang::RenderApiFlag::Vulkan: + deviceDesc.deviceType = gfx::DeviceType::Vulkan; + break; + default: + SLANG_IGNORE_TEST; + } + deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; + const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; + deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); + deviceDesc.slang.searchPaths = searchPaths; + auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); + if (SLANG_FAILED(createDeviceResult)) + { + SLANG_IGNORE_TEST; + } + + getBufferHandleTestImpl(device, context); + } + +#if SLANG_WINDOWS_FAMILY + SLANG_UNIT_TEST(getCmdBufferHandleD3D12) + { + return getBufferHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); + } +#endif + + SLANG_UNIT_TEST(getCmdBufferHandleVulkan) + { + return getBufferHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); + } + +} diff --git a/tools/gfx-unit-test/get-cmd-queue-handle-test.cpp b/tools/gfx-unit-test/get-cmd-queue-handle-test.cpp new file mode 100644 index 000000000..5e530e3f2 --- /dev/null +++ b/tools/gfx-unit-test/get-cmd-queue-handle-test.cpp @@ -0,0 +1,84 @@ +#include "tools/unit-test/slang-unit-test.h" + +#include "slang-gfx.h" +#include "gfx-test-util.h" +#include "tools/gfx-util/shader-cursor.h" +#include "source/core/slang-basic.h" + +#if SLANG_WINDOWS_FAMILY +#include +#endif + +using namespace gfx; + +namespace gfx_test +{ + void getQueueHandleTestImpl(IDevice* device, UnitTestContext* context) + { + ICommandQueue::Desc queueDesc = { ICommandQueue::QueueType::Graphics }; + auto queue = device->createCommandQueue(queueDesc); + ICommandQueue::NativeHandle handle; + GFX_CHECK_CALL_ABORT(queue->getNativeHandle(&handle)); + if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) + { + SLANG_CHECK(handle != NULL); + } +#if SLANG_WINDOWS_FAMILY + else + { + auto d3d12Queue = (ID3D12CommandQueue*)handle; + Slang::ComPtr testHandle1; + GFX_CHECK_CALL_ABORT(d3d12Queue->QueryInterface(testHandle1.writeRef())); + Slang::ComPtr testHandle2; + GFX_CHECK_CALL_ABORT(testHandle1->QueryInterface(testHandle2.writeRef())); + SLANG_CHECK(d3d12Queue == testHandle2.get()); + } +#endif + } + + void getQueueHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) + { + if ((api & context->enabledApis) == 0) + { + SLANG_IGNORE_TEST; + } + Slang::ComPtr device; + IDevice::Desc deviceDesc = {}; + switch (api) + { + case Slang::RenderApiFlag::D3D11: + deviceDesc.deviceType = gfx::DeviceType::DirectX11; + break; + case Slang::RenderApiFlag::D3D12: + deviceDesc.deviceType = gfx::DeviceType::DirectX12; + break; + case Slang::RenderApiFlag::Vulkan: + deviceDesc.deviceType = gfx::DeviceType::Vulkan; + break; + default: + SLANG_IGNORE_TEST; + } + deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; + const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; + deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); + deviceDesc.slang.searchPaths = searchPaths; + auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); + if (SLANG_FAILED(createDeviceResult)) + { + SLANG_IGNORE_TEST; + } + + getQueueHandleTestImpl(device, context); + } + + SLANG_UNIT_TEST(getCmdQueueHandleD3D12) + { + return getQueueHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); + } + + SLANG_UNIT_TEST(getCmdQueueHandleVulkan) + { + return getQueueHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); + } + +} diff --git a/tools/gfx-unit-test/get-queue-handle-test.cpp b/tools/gfx-unit-test/get-queue-handle-test.cpp deleted file mode 100644 index f16e740bf..000000000 --- a/tools/gfx-unit-test/get-queue-handle-test.cpp +++ /dev/null @@ -1,82 +0,0 @@ -#include "tools/unit-test/slang-unit-test.h" - -#include "slang-gfx.h" -#include "gfx-test-util.h" -#include "tools/gfx-util/shader-cursor.h" -#include "source/core/slang-basic.h" - -#if SLANG_WINDOWS_FAMILY -#include -#endif - -using namespace gfx; - -namespace gfx_test -{ - void getQueueHandleTestImpl(IDevice* device, UnitTestContext* context) - { - ICommandQueue::Desc queueDesc = { ICommandQueue::QueueType::Graphics }; - auto queue = device->createCommandQueue(queueDesc); - ICommandQueue::NativeHandle handle; - GFX_CHECK_CALL_ABORT(queue->getNativeHandle(&handle)); - if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) - { - // Check that the handle is not null, which is defined as 0. - SLANG_CHECK(handle != 0); - } -#if SLANG_WINDOWS_FAMILY - else - { - auto d3d12Queue = (ID3D12CommandQueue*)handle; - Slang::ComPtr testHandle; - GFX_CHECK_CALL_ABORT(d3d12Queue->QueryInterface(testHandle.writeRef())); - } -#endif - } - - void getQueueHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) - { - if ((api & context->enabledApis) == 0) - { - SLANG_IGNORE_TEST; - } - Slang::ComPtr device; - IDevice::Desc deviceDesc = {}; - switch (api) - { - case Slang::RenderApiFlag::D3D11: - deviceDesc.deviceType = gfx::DeviceType::DirectX11; - break; - case Slang::RenderApiFlag::D3D12: - deviceDesc.deviceType = gfx::DeviceType::DirectX12; - break; - case Slang::RenderApiFlag::Vulkan: - deviceDesc.deviceType = gfx::DeviceType::Vulkan; - break; - default: - SLANG_IGNORE_TEST; - } - deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; - const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; - deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); - deviceDesc.slang.searchPaths = searchPaths; - auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); - if (SLANG_FAILED(createDeviceResult)) - { - SLANG_IGNORE_TEST; - } - - getQueueHandleTestImpl(device, context); - } - - SLANG_UNIT_TEST(getQueueHandleD3D12) - { - return getQueueHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); - } - - SLANG_UNIT_TEST(getQueueHandleVulkan) - { - return getQueueHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); - } - -} diff --git a/tools/gfx-unit-test/get-texture-resource-handle-test.cpp b/tools/gfx-unit-test/get-texture-resource-handle-test.cpp new file mode 100644 index 000000000..4883a28bd --- /dev/null +++ b/tools/gfx-unit-test/get-texture-resource-handle-test.cpp @@ -0,0 +1,94 @@ +#include "tools/unit-test/slang-unit-test.h" + +#include "slang-gfx.h" +#include "gfx-test-util.h" +#include "tools/gfx-util/shader-cursor.h" +#include "source/core/slang-basic.h" + +#if SLANG_WINDOWS_FAMILY +#include +#endif + +using namespace gfx; + +namespace gfx_test +{ + void getTextureResourceHandleTestImpl(IDevice* device, UnitTestContext* context) + { + ITextureResource::Desc desc = {}; + desc.type = IResource::Type::Texture2D; + desc.numMipLevels = 1; + desc.size.width = 1; + desc.size.height = 1; + desc.size.depth = 1; + desc.defaultState = ResourceState::UnorderedAccess; + desc.format = Format::RGBA_Float16; + + Slang::ComPtr buffer; + buffer = device->createTextureResource(desc); + + ITextureResource::NativeHandle handle; + GFX_CHECK_CALL_ABORT(buffer->getNativeHandle(&handle)); + if (device->getDeviceInfo().deviceType == gfx::DeviceType::Vulkan) + { + SLANG_CHECK(handle != NULL); + } +#if SLANG_WINDOWS_FAMILY + else + { + auto d3d12Handle = (ID3D12Resource*)handle; + Slang::ComPtr testHandle1; + GFX_CHECK_CALL_ABORT(d3d12Handle->QueryInterface(testHandle1.writeRef())); + Slang::ComPtr testHandle2; + GFX_CHECK_CALL_ABORT(testHandle1->QueryInterface(testHandle2.writeRef())); + SLANG_CHECK(d3d12Handle == testHandle2.get()); + } +#endif + } + + void getTextureResourceHandleTestAPI(UnitTestContext* context, Slang::RenderApiFlag::Enum api) + { + if ((api & context->enabledApis) == 0) + { + SLANG_IGNORE_TEST; + } + Slang::ComPtr device; + IDevice::Desc deviceDesc = {}; + switch (api) + { + case Slang::RenderApiFlag::D3D11: + deviceDesc.deviceType = gfx::DeviceType::DirectX11; + break; + case Slang::RenderApiFlag::D3D12: + deviceDesc.deviceType = gfx::DeviceType::DirectX12; + break; + case Slang::RenderApiFlag::Vulkan: + deviceDesc.deviceType = gfx::DeviceType::Vulkan; + break; + default: + SLANG_IGNORE_TEST; + } + deviceDesc.slang.slangGlobalSession = context->slangGlobalSession; + const char* searchPaths[] = { "", "../../tools/gfx-unit-test", "tools/gfx-unit-test" }; + deviceDesc.slang.searchPathCount = (SlangInt)SLANG_COUNT_OF(searchPaths); + deviceDesc.slang.searchPaths = searchPaths; + auto createDeviceResult = gfxCreateDevice(&deviceDesc, device.writeRef()); + if (SLANG_FAILED(createDeviceResult)) + { + SLANG_IGNORE_TEST; + } + + getTextureResourceHandleTestImpl(device, context); + } + + SLANG_UNIT_TEST(getTextureResourceHandleD3D12) + { + return getTextureResourceHandleTestAPI(unitTestContext, Slang::RenderApiFlag::D3D12); + } + + SLANG_UNIT_TEST(getTextureResourceHandleVulkan) + { + return getTextureResourceHandleTestAPI(unitTestContext, Slang::RenderApiFlag::Vulkan); + } + +} diff --git a/tools/gfx/cuda/render-cuda.cpp b/tools/gfx/cuda/render-cuda.cpp index ec6f1212a..788baed0d 100644 --- a/tools/gfx/cuda/render-cuda.cpp +++ b/tools/gfx/cuda/render-cuda.cpp @@ -193,6 +193,12 @@ public: { return (DeviceAddress)m_cudaMemory; } + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = getBindlessHandle(); + return SLANG_OK; + } }; class TextureCUDAResource : public TextureResource @@ -234,6 +240,12 @@ public: CUmipmappedArray m_cudaMipMappedArray = CUmipmappedArray(); RefPtr m_cudaContext; + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = getBindlessHandle(); + return SLANG_OK; + } }; class CUDAResourceView : public ResourceViewBase diff --git a/tools/gfx/d3d12/render-d3d12.cpp b/tools/gfx/d3d12/render-d3d12.cpp index 2d8c5fa10..4002450f3 100644 --- a/tools/gfx/d3d12/render-d3d12.cpp +++ b/tools/gfx/d3d12/render-d3d12.cpp @@ -219,6 +219,12 @@ public: { return (DeviceAddress)m_resource.getResource()->GetGPUVirtualAddress(); } + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = (uint64_t)m_resource.getResource(); + return SLANG_OK; + } }; class TextureResourceImpl: public TextureResource @@ -234,6 +240,12 @@ public: D3D12Resource m_resource; D3D12_RESOURCE_STATES m_defaultState; + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = (uint64_t)m_resource.getResource(); + return SLANG_OK; + } }; class SamplerStateImpl : public ISamplerState, public ComObject diff --git a/tools/gfx/debug-layer.cpp b/tools/gfx/debug-layer.cpp index 74b319a08..869a93411 100644 --- a/tools/gfx/debug-layer.cpp +++ b/tools/gfx/debug-layer.cpp @@ -692,6 +692,11 @@ DeviceAddress DebugBufferResource::getDeviceAddress() return baseObject->getDeviceAddress(); } +Result DebugBufferResource::getNativeHandle(NativeHandle* outHandle) +{ + return baseObject->getNativeHandle(outHandle); +} + IResource::Type DebugTextureResource::getType() { SLANG_GFX_API_FUNC; @@ -704,6 +709,11 @@ ITextureResource::Desc* DebugTextureResource::getDesc() return baseObject->getDesc(); } +Result DebugTextureResource::getNativeHandle(NativeHandle* outHandle) +{ + return baseObject->getNativeHandle(outHandle); +} + DebugCommandBuffer::DebugCommandBuffer() { SLANG_GFX_API_FUNC; diff --git a/tools/gfx/debug-layer.h b/tools/gfx/debug-layer.h index 88e0e5ecd..2f0bc76ce 100644 --- a/tools/gfx/debug-layer.h +++ b/tools/gfx/debug-layer.h @@ -144,6 +144,7 @@ public: virtual SLANG_NO_THROW Type SLANG_MCALL getType() override; virtual SLANG_NO_THROW Desc* SLANG_MCALL getDesc() override; virtual SLANG_NO_THROW DeviceAddress SLANG_MCALL getDeviceAddress() override; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override; }; class DebugTextureResource : public DebugObject @@ -155,6 +156,7 @@ public: ITextureResource* getInterface(const Slang::Guid& guid); virtual SLANG_NO_THROW Type SLANG_MCALL getType() override; virtual SLANG_NO_THROW Desc* SLANG_MCALL getDesc() override; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override; }; class DebugResourceView : public DebugObject diff --git a/tools/gfx/renderer-shared.cpp b/tools/gfx/renderer-shared.cpp index 18f99ad1b..c5a0c826d 100644 --- a/tools/gfx/renderer-shared.cpp +++ b/tools/gfx/renderer-shared.cpp @@ -74,6 +74,11 @@ IResource* BufferResource::getInterface(const Slang::Guid& guid) SLANG_NO_THROW IResource::Type SLANG_MCALL BufferResource::getType() { return m_type; } SLANG_NO_THROW IBufferResource::Desc* SLANG_MCALL BufferResource::getDesc() { return &m_desc; } +Result BufferResource::getNativeHandle(NativeHandle* outHandle) +{ + *outHandle = NULL; + return SLANG_OK; +} IResource* TextureResource::getInterface(const Slang::Guid& guid) { @@ -86,6 +91,12 @@ IResource* TextureResource::getInterface(const Slang::Guid& guid) SLANG_NO_THROW IResource::Type SLANG_MCALL TextureResource::getType() { return m_type; } SLANG_NO_THROW ITextureResource::Desc* SLANG_MCALL TextureResource::getDesc() { return &m_desc; } +Result TextureResource::getNativeHandle(NativeHandle* outHandle) +{ + *outHandle = NULL; + return SLANG_OK; +} + StageType mapStage(SlangStage stage) { switch( stage ) diff --git a/tools/gfx/renderer-shared.h b/tools/gfx/renderer-shared.h index 5710bc74e..5df3ee92b 100644 --- a/tools/gfx/renderer-shared.h +++ b/tools/gfx/renderer-shared.h @@ -218,6 +218,7 @@ public: virtual SLANG_NO_THROW IResource::Type SLANG_MCALL getType() SLANG_OVERRIDE; virtual SLANG_NO_THROW IBufferResource::Desc* SLANG_MCALL getDesc() SLANG_OVERRIDE; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) SLANG_OVERRIDE; protected: Desc m_desc; @@ -240,6 +241,7 @@ public: virtual SLANG_NO_THROW IResource::Type SLANG_MCALL getType() SLANG_OVERRIDE; virtual SLANG_NO_THROW ITextureResource::Desc* SLANG_MCALL getDesc() SLANG_OVERRIDE; + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) SLANG_OVERRIDE; protected: Desc m_desc; diff --git a/tools/gfx/vulkan/render-vk.cpp b/tools/gfx/vulkan/render-vk.cpp index 7af7d086f..d2cbd6790 100644 --- a/tools/gfx/vulkan/render-vk.cpp +++ b/tools/gfx/vulkan/render-vk.cpp @@ -203,6 +203,12 @@ public: return (DeviceAddress)m_buffer.m_api->vkGetBufferDeviceAddress( m_buffer.m_api->m_device, &info); } + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = (uint64_t)m_buffer.m_buffer; + return SLANG_OK; + } }; class TextureResourceImpl : public TextureResource @@ -229,6 +235,12 @@ public: VkDeviceMemory m_imageMemory = VK_NULL_HANDLE; bool m_isWeakImageReference = false; RefPtr m_device; + + virtual SLANG_NO_THROW Result SLANG_MCALL getNativeHandle(NativeHandle* outHandle) override + { + *outHandle = (uint64_t)m_image; + return SLANG_OK; + } }; class SamplerStateImpl : public ISamplerState, public ComObject -- cgit v1.2.3