From 6386188a3675e80b28fde1d4485e4294ad18fad8 Mon Sep 17 00:00:00 2001 From: Simon Kallweit <64953474+skallweitNV@users.noreply.github.com> Date: Mon, 21 Oct 2024 14:29:47 +0200 Subject: [PATCH] move acceleration structure utils (#86) --- src/d3d/d3d-util.cpp | 120 ------------------- src/d3d/d3d-util.h | 48 -------- src/d3d12/d3d12-acceleration-structure.cpp | 118 ++++++++++++++++++ src/d3d12/d3d12-acceleration-structure.h | 47 ++++++++ src/d3d12/d3d12-command-encoder.cpp | 2 +- src/d3d12/d3d12-device.cpp | 2 +- src/vulkan/vk-acceleration-structure.cpp | 132 +++++++++++++++++++++ src/vulkan/vk-acceleration-structure.h | 49 ++++++++ src/vulkan/vk-util.cpp | 131 -------------------- src/vulkan/vk-util.h | 49 -------- 10 files changed, 348 insertions(+), 350 deletions(-) diff --git a/src/d3d/d3d-util.cpp b/src/d3d/d3d-util.cpp index 9b6aa4c6..716d0807 100644 --- a/src/d3d/d3d-util.cpp +++ b/src/d3d/d3d-util.cpp @@ -1098,124 +1098,4 @@ Result D3DUtil::findAdapters( return SLANG_OK; } -#if SLANG_RHI_DXR -Result D3DAccelerationStructureInputsBuilder::build( - const AccelerationStructureBuildDesc& buildDesc, - IDebugCallback* callback -) -{ - if (buildDesc.inputCount < 1) - { - return SLANG_E_INVALID_ARG; - } - - AccelerationStructureBuildInputType type = (AccelerationStructureBuildInputType&)buildDesc.inputs[0]; - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - if ((AccelerationStructureBuildInputType&)buildDesc.inputs[i] != type) - { - return SLANG_E_INVALID_ARG; - } - } - - desc.Flags = translateBuildFlags(buildDesc.flags); - switch (buildDesc.mode) - { - case AccelerationStructureBuildMode::Build: - desc.Flags |= D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_UPDATE; - break; - case AccelerationStructureBuildMode::Update: - desc.Flags |= D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PERFORM_UPDATE; - break; - default: - return SLANG_E_INVALID_ARG; - } - - switch (type) - { - case AccelerationStructureBuildInputType::Instances: - { - if (buildDesc.inputCount > 1) - { - return SLANG_E_INVALID_ARG; - } - const AccelerationStructureBuildInputInstances& instances = - (const AccelerationStructureBuildInputInstances&)buildDesc.inputs[0]; - desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_TOP_LEVEL; - desc.NumDescs = 1; - desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; - desc.InstanceDescs = instances.instanceBuffer.getDeviceAddress(); - break; - } - case AccelerationStructureBuildInputType::Triangles: - { - geomDescs.resize(buildDesc.inputCount); - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - const AccelerationStructureBuildInputTriangles& triangles = - (const AccelerationStructureBuildInputTriangles&)buildDesc.inputs[i]; - if (triangles.vertexBufferCount != 1) - { - return SLANG_E_INVALID_ARG; - } - D3D12_RAYTRACING_GEOMETRY_DESC& geomDesc = geomDescs[i]; - geomDesc.Type = D3D12_RAYTRACING_GEOMETRY_TYPE_TRIANGLES; - geomDesc.Flags = translateGeometryFlags(triangles.flags); - geomDesc.Triangles.VertexBuffer.StartAddress = triangles.vertexBuffers[0].getDeviceAddress(); - geomDesc.Triangles.VertexBuffer.StrideInBytes = triangles.vertexStride; - geomDesc.Triangles.VertexCount = triangles.vertexCount; - geomDesc.Triangles.VertexFormat = D3DUtil::getMapFormat(triangles.vertexFormat); - if (triangles.indexBuffer) - { - geomDesc.Triangles.IndexBuffer = triangles.indexBuffer.getDeviceAddress(); - geomDesc.Triangles.IndexCount = triangles.indexCount; - geomDesc.Triangles.IndexFormat = D3DUtil::getIndexFormat(triangles.indexFormat); - } - else - { - geomDesc.Triangles.IndexBuffer = 0; - geomDesc.Triangles.IndexCount = 0; - geomDesc.Triangles.IndexFormat = DXGI_FORMAT_UNKNOWN; - } - geomDesc.Triangles.Transform3x4 = - triangles.preTransformBuffer ? triangles.preTransformBuffer.getDeviceAddress() : 0; - } - desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL; - desc.NumDescs = geomDescs.size(); - desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; - desc.pGeometryDescs = geomDescs.data(); - break; - } - case AccelerationStructureBuildInputType::ProceduralPrimitives: - { - geomDescs.resize(buildDesc.inputCount); - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - const AccelerationStructureBuildInputProceduralPrimitives& proceduralPrimitives = - (const AccelerationStructureBuildInputProceduralPrimitives&)buildDesc.inputs[i]; - if (proceduralPrimitives.aabbBufferCount != 1) - { - return SLANG_E_INVALID_ARG; - } - D3D12_RAYTRACING_GEOMETRY_DESC& geomDesc = geomDescs[i]; - geomDesc.Type = D3D12_RAYTRACING_GEOMETRY_TYPE_PROCEDURAL_PRIMITIVE_AABBS; - geomDesc.Flags = translateGeometryFlags(proceduralPrimitives.flags); - geomDesc.AABBs.AABBCount = proceduralPrimitives.primitiveCount; - geomDesc.AABBs.AABBs.StartAddress = proceduralPrimitives.aabbBuffers[0].getDeviceAddress(); - geomDesc.AABBs.AABBs.StrideInBytes = proceduralPrimitives.aabbStride; - } - desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL; - desc.NumDescs = geomDescs.size(); - desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; - desc.pGeometryDescs = geomDescs.data(); - break; - } - default: - return SLANG_E_INVALID_ARG; - } - - return SLANG_OK; -} -#endif - } // namespace rhi diff --git a/src/d3d/d3d-util.h b/src/d3d/d3d-util.h index 5b3454b8..5df9c886 100644 --- a/src/d3d/d3d-util.h +++ b/src/d3d/d3d-util.h @@ -149,52 +149,4 @@ class D3DUtil static Result waitForCrashDumpCompletion(HRESULT res); }; -#if SLANG_RHI_DXR -struct D3DAccelerationStructureInputsBuilder -{ - D3D12_BUILD_RAYTRACING_ACCELERATION_STRUCTURE_INPUTS desc = {}; - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_PREBUILD_INFO prebuildInfo = {}; - std::vector geomDescs; - Result build(const AccelerationStructureBuildDesc& buildDesc, IDebugCallback* callback); - -private: - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAGS translateBuildFlags(AccelerationStructureBuildFlags flags) - { - static_assert( - uint32_t(AccelerationStructureBuildFlags::None) == D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_NONE - ); - static_assert( - uint32_t(AccelerationStructureBuildFlags::AllowUpdate) == - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_UPDATE - ); - static_assert( - uint32_t(AccelerationStructureBuildFlags::AllowCompaction) == - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_COMPACTION - ); - static_assert( - uint32_t(AccelerationStructureBuildFlags::PreferFastTrace) == - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PREFER_FAST_TRACE - ); - static_assert( - uint32_t(AccelerationStructureBuildFlags::PreferFastBuild) == - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PREFER_FAST_BUILD - ); - static_assert( - uint32_t(AccelerationStructureBuildFlags::MinimizeMemory) == - D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_MINIMIZE_MEMORY - ); - return (D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAGS)flags; - } - D3D12_RAYTRACING_GEOMETRY_FLAGS translateGeometryFlags(AccelerationStructureGeometryFlags flags) - { - static_assert(uint32_t(AccelerationStructureGeometryFlags::None) == D3D12_RAYTRACING_GEOMETRY_FLAG_NONE); - static_assert(uint32_t(AccelerationStructureGeometryFlags::Opaque) == D3D12_RAYTRACING_GEOMETRY_FLAG_OPAQUE); - static_assert( - uint32_t(AccelerationStructureGeometryFlags::NoDuplicateAnyHitInvocation) == - D3D12_RAYTRACING_GEOMETRY_FLAG_NO_DUPLICATE_ANYHIT_INVOCATION - ); - return (D3D12_RAYTRACING_GEOMETRY_FLAGS)flags; - } -}; -#endif } // namespace rhi diff --git a/src/d3d12/d3d12-acceleration-structure.cpp b/src/d3d12/d3d12-acceleration-structure.cpp index 214c6551..faa4949c 100644 --- a/src/d3d12/d3d12-acceleration-structure.cpp +++ b/src/d3d12/d3d12-acceleration-structure.cpp @@ -29,6 +29,124 @@ DeviceAddress AccelerationStructureImpl::getDeviceAddress() return m_buffer->getDeviceAddress(); } +Result AccelerationStructureInputsBuilder::build( + const AccelerationStructureBuildDesc& buildDesc, + IDebugCallback* callback +) +{ + if (buildDesc.inputCount < 1) + { + return SLANG_E_INVALID_ARG; + } + + AccelerationStructureBuildInputType type = (AccelerationStructureBuildInputType&)buildDesc.inputs[0]; + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + if ((AccelerationStructureBuildInputType&)buildDesc.inputs[i] != type) + { + return SLANG_E_INVALID_ARG; + } + } + + desc.Flags = translateBuildFlags(buildDesc.flags); + switch (buildDesc.mode) + { + case AccelerationStructureBuildMode::Build: + desc.Flags |= D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_UPDATE; + break; + case AccelerationStructureBuildMode::Update: + desc.Flags |= D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PERFORM_UPDATE; + break; + default: + return SLANG_E_INVALID_ARG; + } + + switch (type) + { + case AccelerationStructureBuildInputType::Instances: + { + if (buildDesc.inputCount > 1) + { + return SLANG_E_INVALID_ARG; + } + const AccelerationStructureBuildInputInstances& instances = + (const AccelerationStructureBuildInputInstances&)buildDesc.inputs[0]; + desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_TOP_LEVEL; + desc.NumDescs = 1; + desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; + desc.InstanceDescs = instances.instanceBuffer.getDeviceAddress(); + break; + } + case AccelerationStructureBuildInputType::Triangles: + { + geomDescs.resize(buildDesc.inputCount); + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + const AccelerationStructureBuildInputTriangles& triangles = + (const AccelerationStructureBuildInputTriangles&)buildDesc.inputs[i]; + if (triangles.vertexBufferCount != 1) + { + return SLANG_E_INVALID_ARG; + } + D3D12_RAYTRACING_GEOMETRY_DESC& geomDesc = geomDescs[i]; + geomDesc.Type = D3D12_RAYTRACING_GEOMETRY_TYPE_TRIANGLES; + geomDesc.Flags = translateGeometryFlags(triangles.flags); + geomDesc.Triangles.VertexBuffer.StartAddress = triangles.vertexBuffers[0].getDeviceAddress(); + geomDesc.Triangles.VertexBuffer.StrideInBytes = triangles.vertexStride; + geomDesc.Triangles.VertexCount = triangles.vertexCount; + geomDesc.Triangles.VertexFormat = D3DUtil::getMapFormat(triangles.vertexFormat); + if (triangles.indexBuffer) + { + geomDesc.Triangles.IndexBuffer = triangles.indexBuffer.getDeviceAddress(); + geomDesc.Triangles.IndexCount = triangles.indexCount; + geomDesc.Triangles.IndexFormat = D3DUtil::getIndexFormat(triangles.indexFormat); + } + else + { + geomDesc.Triangles.IndexBuffer = 0; + geomDesc.Triangles.IndexCount = 0; + geomDesc.Triangles.IndexFormat = DXGI_FORMAT_UNKNOWN; + } + geomDesc.Triangles.Transform3x4 = + triangles.preTransformBuffer ? triangles.preTransformBuffer.getDeviceAddress() : 0; + } + desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL; + desc.NumDescs = geomDescs.size(); + desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; + desc.pGeometryDescs = geomDescs.data(); + break; + } + case AccelerationStructureBuildInputType::ProceduralPrimitives: + { + geomDescs.resize(buildDesc.inputCount); + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + const AccelerationStructureBuildInputProceduralPrimitives& proceduralPrimitives = + (const AccelerationStructureBuildInputProceduralPrimitives&)buildDesc.inputs[i]; + if (proceduralPrimitives.aabbBufferCount != 1) + { + return SLANG_E_INVALID_ARG; + } + D3D12_RAYTRACING_GEOMETRY_DESC& geomDesc = geomDescs[i]; + geomDesc.Type = D3D12_RAYTRACING_GEOMETRY_TYPE_PROCEDURAL_PRIMITIVE_AABBS; + geomDesc.Flags = translateGeometryFlags(proceduralPrimitives.flags); + geomDesc.AABBs.AABBCount = proceduralPrimitives.primitiveCount; + geomDesc.AABBs.AABBs.StartAddress = proceduralPrimitives.aabbBuffers[0].getDeviceAddress(); + geomDesc.AABBs.AABBs.StrideInBytes = proceduralPrimitives.aabbStride; + } + desc.Type = D3D12_RAYTRACING_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL; + desc.NumDescs = geomDescs.size(); + desc.DescsLayout = D3D12_ELEMENTS_LAYOUT_ARRAY; + desc.pGeometryDescs = geomDescs.data(); + break; + } + default: + return SLANG_E_INVALID_ARG; + } + + return SLANG_OK; +} + #endif // SLANG_RHI_DXR } // namespace rhi::d3d12 diff --git a/src/d3d12/d3d12-acceleration-structure.h b/src/d3d12/d3d12-acceleration-structure.h index 3f94ca69..d51c4e4d 100644 --- a/src/d3d12/d3d12-acceleration-structure.h +++ b/src/d3d12/d3d12-acceleration-structure.h @@ -29,6 +29,53 @@ class AccelerationStructureImpl : public AccelerationStructure virtual SLANG_NO_THROW DeviceAddress SLANG_MCALL getDeviceAddress() override; }; +struct AccelerationStructureInputsBuilder +{ + D3D12_BUILD_RAYTRACING_ACCELERATION_STRUCTURE_INPUTS desc = {}; + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_PREBUILD_INFO prebuildInfo = {}; + std::vector geomDescs; + Result build(const AccelerationStructureBuildDesc& buildDesc, IDebugCallback* callback); + +private: + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAGS translateBuildFlags(AccelerationStructureBuildFlags flags) + { + static_assert( + uint32_t(AccelerationStructureBuildFlags::None) == D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_NONE + ); + static_assert( + uint32_t(AccelerationStructureBuildFlags::AllowUpdate) == + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_UPDATE + ); + static_assert( + uint32_t(AccelerationStructureBuildFlags::AllowCompaction) == + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_ALLOW_COMPACTION + ); + static_assert( + uint32_t(AccelerationStructureBuildFlags::PreferFastTrace) == + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PREFER_FAST_TRACE + ); + static_assert( + uint32_t(AccelerationStructureBuildFlags::PreferFastBuild) == + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_PREFER_FAST_BUILD + ); + static_assert( + uint32_t(AccelerationStructureBuildFlags::MinimizeMemory) == + D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAG_MINIMIZE_MEMORY + ); + return (D3D12_RAYTRACING_ACCELERATION_STRUCTURE_BUILD_FLAGS)flags; + } + D3D12_RAYTRACING_GEOMETRY_FLAGS translateGeometryFlags(AccelerationStructureGeometryFlags flags) + { + static_assert(uint32_t(AccelerationStructureGeometryFlags::None) == D3D12_RAYTRACING_GEOMETRY_FLAG_NONE); + static_assert(uint32_t(AccelerationStructureGeometryFlags::Opaque) == D3D12_RAYTRACING_GEOMETRY_FLAG_OPAQUE); + static_assert( + uint32_t(AccelerationStructureGeometryFlags::NoDuplicateAnyHitInvocation) == + D3D12_RAYTRACING_GEOMETRY_FLAG_NO_DUPLICATE_ANYHIT_INVOCATION + ); + return (D3D12_RAYTRACING_GEOMETRY_FLAGS)flags; + } +}; + #endif // SLANG_RHI_DXR } // namespace rhi::d3d12 diff --git a/src/d3d12/d3d12-command-encoder.cpp b/src/d3d12/d3d12-command-encoder.cpp index a7385d47..04f2c1ae 100644 --- a/src/d3d12/d3d12-command-encoder.cpp +++ b/src/d3d12/d3d12-command-encoder.cpp @@ -1166,7 +1166,7 @@ void RayTracingPassEncoderImpl::buildAccelerationStructure( buildDesc.DestAccelerationStructureData = dstImpl->getDeviceAddress(); buildDesc.SourceAccelerationStructureData = srcImpl ? srcImpl->getDeviceAddress() : 0; buildDesc.ScratchAccelerationStructureData = scratchBuffer.buffer->getDeviceAddress() + scratchBuffer.offset; - D3DAccelerationStructureInputsBuilder builder; + AccelerationStructureInputsBuilder builder; builder.build(desc, m_device->m_debugCallback); buildDesc.Inputs = builder.desc; diff --git a/src/d3d12/d3d12-device.cpp b/src/d3d12/d3d12-device.cpp index 4cf9a6d0..9749af31 100644 --- a/src/d3d12/d3d12-device.cpp +++ b/src/d3d12/d3d12-device.cpp @@ -1707,7 +1707,7 @@ Result DeviceImpl::getAccelerationStructureSizes( if (!m_device5) return SLANG_E_NOT_AVAILABLE; - D3DAccelerationStructureInputsBuilder inputsBuilder; + AccelerationStructureInputsBuilder inputsBuilder; SLANG_RETURN_ON_FAIL(inputsBuilder.build(desc, m_debugCallback)); D3D12_RAYTRACING_ACCELERATION_STRUCTURE_PREBUILD_INFO prebuildInfo; diff --git a/src/vulkan/vk-acceleration-structure.cpp b/src/vulkan/vk-acceleration-structure.cpp index beac794b..9af9f9e0 100644 --- a/src/vulkan/vk-acceleration-structure.cpp +++ b/src/vulkan/vk-acceleration-structure.cpp @@ -1,6 +1,7 @@ #include "vk-acceleration-structure.h" #include "vk-device.h" #include "vk-buffer.h" +#include "vk-util.h" namespace rhi::vk { @@ -29,4 +30,135 @@ DeviceAddress AccelerationStructureImpl::getDeviceAddress() return m_buffer->getDeviceAddress(); } +Result AccelerationStructureBuildGeometryInfoBuilder::build( + const AccelerationStructureBuildDesc& buildDesc, + IDebugCallback* debugCallback +) +{ + if (buildDesc.inputCount < 1) + { + return SLANG_E_INVALID_ARG; + } + + AccelerationStructureBuildInputType type = (AccelerationStructureBuildInputType&)buildDesc.inputs[0]; + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + if ((AccelerationStructureBuildInputType&)buildDesc.inputs[i] != type) + { + return SLANG_E_INVALID_ARG; + } + } + + buildInfo.dstAccelerationStructure = VK_NULL_HANDLE; + switch (buildDesc.mode) + { + case AccelerationStructureBuildMode::Build: + buildInfo.mode = VK_BUILD_ACCELERATION_STRUCTURE_MODE_BUILD_KHR; + break; + case AccelerationStructureBuildMode::Update: + buildInfo.mode = VK_BUILD_ACCELERATION_STRUCTURE_MODE_UPDATE_KHR; + break; + default: + return SLANG_E_INVALID_ARG; + } + buildInfo.flags = translateBuildFlags(buildDesc.flags); + geometries.resize(buildDesc.inputCount); + primitiveCounts.resize(buildDesc.inputCount); + buildInfo.pGeometries = geometries.data(); + buildInfo.geometryCount = geometries.size(); + + switch (type) + { + case AccelerationStructureBuildInputType::Instances: + { + if (buildDesc.inputCount > 1) + { + return SLANG_E_INVALID_ARG; + } + const AccelerationStructureBuildInputInstances& instances = + (const AccelerationStructureBuildInputInstances&)buildDesc.inputs[0]; + + VkAccelerationStructureGeometryKHR& geometry = geometries[0]; + geometry.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_KHR; + geometry.geometryType = VK_GEOMETRY_TYPE_INSTANCES_KHR; + geometry.geometry.instances.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_INSTANCES_DATA_KHR; + geometry.geometry.instances.arrayOfPointers = 0; + geometry.geometry.instances.data.deviceAddress = instances.instanceBuffer.getDeviceAddress(); + + primitiveCounts[0] = instances.instanceCount; + + buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_TOP_LEVEL_KHR; + break; + } + case AccelerationStructureBuildInputType::Triangles: + { + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + const AccelerationStructureBuildInputTriangles& triangles = + (const AccelerationStructureBuildInputTriangles&)buildDesc.inputs[i]; + if (triangles.vertexBufferCount != 1) + { + return SLANG_E_INVALID_ARG; + } + + VkAccelerationStructureGeometryKHR& geometry = geometries[i]; + geometry.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_KHR; + geometry.geometryType = VK_GEOMETRY_TYPE_TRIANGLES_KHR; + geometry.flags = translateGeometryFlags(triangles.flags); + geometry.geometry.triangles.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_TRIANGLES_DATA_KHR; + geometry.geometry.triangles.vertexFormat = VulkanUtil::getVkFormat(triangles.vertexFormat); + geometry.geometry.triangles.vertexData.deviceAddress = triangles.vertexBuffers[0].getDeviceAddress(); + geometry.geometry.triangles.vertexStride = triangles.vertexStride; + geometry.geometry.triangles.maxVertex = triangles.vertexCount - 1; + if (triangles.indexBuffer) + { + geometry.geometry.triangles.indexType = + triangles.indexFormat == IndexFormat::UInt32 ? VK_INDEX_TYPE_UINT32 : VK_INDEX_TYPE_UINT16; + geometry.geometry.triangles.indexData.deviceAddress = triangles.indexBuffer.getDeviceAddress(); + } + else + { + geometry.geometry.triangles.indexType = VK_INDEX_TYPE_NONE_KHR; + geometry.geometry.triangles.indexData.deviceAddress = 0; + } + geometry.geometry.triangles.transformData.deviceAddress = + triangles.preTransformBuffer ? triangles.preTransformBuffer.getDeviceAddress() : 0; + + primitiveCounts[i] = max(triangles.vertexCount, triangles.indexCount) / 3; + } + + buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL_KHR; + break; + } + case AccelerationStructureBuildInputType::ProceduralPrimitives: + { + for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) + { + const AccelerationStructureBuildInputProceduralPrimitives& proceduralPrimitives = + (const AccelerationStructureBuildInputProceduralPrimitives&)buildDesc.inputs[i]; + if (proceduralPrimitives.aabbBufferCount != 1) + { + return SLANG_E_INVALID_ARG; + } + + VkAccelerationStructureGeometryKHR& geometry = geometries[i]; + geometry.geometryType = VK_GEOMETRY_TYPE_AABBS_KHR; + geometry.flags = translateGeometryFlags(proceduralPrimitives.flags); + geometry.geometry.aabbs.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_AABBS_DATA_KHR; + geometry.geometry.aabbs.data.deviceAddress = proceduralPrimitives.aabbBuffers[0].getDeviceAddress(); + geometry.geometry.aabbs.stride = proceduralPrimitives.aabbStride; + + primitiveCounts[i] = proceduralPrimitives.primitiveCount; + } + + buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL_KHR; + break; + } + default: + return SLANG_E_INVALID_ARG; + } + + return SLANG_OK; +} + } // namespace rhi::vk diff --git a/src/vulkan/vk-acceleration-structure.h b/src/vulkan/vk-acceleration-structure.h index ae2c6922..224d0f41 100644 --- a/src/vulkan/vk-acceleration-structure.h +++ b/src/vulkan/vk-acceleration-structure.h @@ -26,4 +26,53 @@ class AccelerationStructureImpl : public AccelerationStructure virtual SLANG_NO_THROW DeviceAddress SLANG_MCALL getDeviceAddress() override; }; +struct AccelerationStructureBuildGeometryInfoBuilder +{ +public: + VkAccelerationStructureBuildGeometryInfoKHR buildInfo = { + VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_BUILD_GEOMETRY_INFO_KHR + }; + std::vector primitiveCounts; + + Result build(const AccelerationStructureBuildDesc& buildDesc, IDebugCallback* debugCallback); + +private: + std::vector geometries; + + VkBuildAccelerationStructureFlagsKHR translateBuildFlags(AccelerationStructureBuildFlags flags) + { + VkBuildAccelerationStructureFlagsKHR result = VkBuildAccelerationStructureFlagsKHR(0); + if (is_set(flags, AccelerationStructureBuildFlags::AllowCompaction)) + { + result |= VK_BUILD_ACCELERATION_STRUCTURE_ALLOW_COMPACTION_BIT_KHR; + } + if (is_set(flags, AccelerationStructureBuildFlags::AllowUpdate)) + { + result |= VK_BUILD_ACCELERATION_STRUCTURE_ALLOW_UPDATE_BIT_KHR; + } + if (is_set(flags, AccelerationStructureBuildFlags::MinimizeMemory)) + { + result |= VK_BUILD_ACCELERATION_STRUCTURE_LOW_MEMORY_BIT_KHR; + } + if (is_set(flags, AccelerationStructureBuildFlags::PreferFastBuild)) + { + result |= VK_BUILD_ACCELERATION_STRUCTURE_PREFER_FAST_BUILD_BIT_KHR; + } + if (is_set(flags, AccelerationStructureBuildFlags::PreferFastTrace)) + { + result |= VK_BUILD_ACCELERATION_STRUCTURE_PREFER_FAST_TRACE_BIT_KHR; + } + return result; + } + VkGeometryFlagsKHR translateGeometryFlags(AccelerationStructureGeometryFlags flags) + { + VkGeometryFlagsKHR result = VkGeometryFlagsKHR(0); + if (is_set(flags, AccelerationStructureGeometryFlags::Opaque)) + result |= VK_GEOMETRY_OPAQUE_BIT_KHR; + if (is_set(flags, AccelerationStructureGeometryFlags::NoDuplicateAnyHitInvocation)) + result |= VK_GEOMETRY_NO_DUPLICATE_ANY_HIT_INVOCATION_BIT_KHR; + return result; + } +}; + } // namespace rhi::vk diff --git a/src/vulkan/vk-util.cpp b/src/vulkan/vk-util.cpp index a47d2670..c22ed516 100644 --- a/src/vulkan/vk-util.cpp +++ b/src/vulkan/vk-util.cpp @@ -661,135 +661,4 @@ VkImageLayout VulkanUtil::mapResourceStateToLayout(ResourceState state) } } -Result AccelerationStructureBuildGeometryInfoBuilder::build( - const AccelerationStructureBuildDesc& buildDesc, - IDebugCallback* debugCallback -) -{ - if (buildDesc.inputCount < 1) - { - return SLANG_E_INVALID_ARG; - } - - AccelerationStructureBuildInputType type = (AccelerationStructureBuildInputType&)buildDesc.inputs[0]; - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - if ((AccelerationStructureBuildInputType&)buildDesc.inputs[i] != type) - { - return SLANG_E_INVALID_ARG; - } - } - - buildInfo.dstAccelerationStructure = VK_NULL_HANDLE; - switch (buildDesc.mode) - { - case AccelerationStructureBuildMode::Build: - buildInfo.mode = VK_BUILD_ACCELERATION_STRUCTURE_MODE_BUILD_KHR; - break; - case AccelerationStructureBuildMode::Update: - buildInfo.mode = VK_BUILD_ACCELERATION_STRUCTURE_MODE_UPDATE_KHR; - break; - default: - return SLANG_E_INVALID_ARG; - } - buildInfo.flags = translateBuildFlags(buildDesc.flags); - geometries.resize(buildDesc.inputCount); - primitiveCounts.resize(buildDesc.inputCount); - buildInfo.pGeometries = geometries.data(); - buildInfo.geometryCount = geometries.size(); - - switch (type) - { - case AccelerationStructureBuildInputType::Instances: - { - if (buildDesc.inputCount > 1) - { - return SLANG_E_INVALID_ARG; - } - const AccelerationStructureBuildInputInstances& instances = - (const AccelerationStructureBuildInputInstances&)buildDesc.inputs[0]; - - VkAccelerationStructureGeometryKHR& geometry = geometries[0]; - geometry.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_KHR; - geometry.geometryType = VK_GEOMETRY_TYPE_INSTANCES_KHR; - geometry.geometry.instances.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_INSTANCES_DATA_KHR; - geometry.geometry.instances.arrayOfPointers = 0; - geometry.geometry.instances.data.deviceAddress = instances.instanceBuffer.getDeviceAddress(); - - primitiveCounts[0] = instances.instanceCount; - - buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_TOP_LEVEL_KHR; - break; - } - case AccelerationStructureBuildInputType::Triangles: - { - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - const AccelerationStructureBuildInputTriangles& triangles = - (const AccelerationStructureBuildInputTriangles&)buildDesc.inputs[i]; - if (triangles.vertexBufferCount != 1) - { - return SLANG_E_INVALID_ARG; - } - - VkAccelerationStructureGeometryKHR& geometry = geometries[i]; - geometry.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_KHR; - geometry.geometryType = VK_GEOMETRY_TYPE_TRIANGLES_KHR; - geometry.flags = translateGeometryFlags(triangles.flags); - geometry.geometry.triangles.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_TRIANGLES_DATA_KHR; - geometry.geometry.triangles.vertexFormat = VulkanUtil::getVkFormat(triangles.vertexFormat); - geometry.geometry.triangles.vertexData.deviceAddress = triangles.vertexBuffers[0].getDeviceAddress(); - geometry.geometry.triangles.vertexStride = triangles.vertexStride; - geometry.geometry.triangles.maxVertex = triangles.vertexCount - 1; - if (triangles.indexBuffer) - { - geometry.geometry.triangles.indexType = - triangles.indexFormat == IndexFormat::UInt32 ? VK_INDEX_TYPE_UINT32 : VK_INDEX_TYPE_UINT16; - geometry.geometry.triangles.indexData.deviceAddress = triangles.indexBuffer.getDeviceAddress(); - } - else - { - geometry.geometry.triangles.indexType = VK_INDEX_TYPE_NONE_KHR; - geometry.geometry.triangles.indexData.deviceAddress = 0; - } - geometry.geometry.triangles.transformData.deviceAddress = - triangles.preTransformBuffer ? triangles.preTransformBuffer.getDeviceAddress() : 0; - - primitiveCounts[i] = max(triangles.vertexCount, triangles.indexCount) / 3; - } - - buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL_KHR; - break; - } - case AccelerationStructureBuildInputType::ProceduralPrimitives: - { - for (GfxIndex i = 0; i < buildDesc.inputCount; ++i) - { - const AccelerationStructureBuildInputProceduralPrimitives& proceduralPrimitives = - (const AccelerationStructureBuildInputProceduralPrimitives&)buildDesc.inputs[i]; - if (proceduralPrimitives.aabbBufferCount != 1) - { - return SLANG_E_INVALID_ARG; - } - - VkAccelerationStructureGeometryKHR& geometry = geometries[i]; - geometry.geometryType = VK_GEOMETRY_TYPE_AABBS_KHR; - geometry.flags = translateGeometryFlags(proceduralPrimitives.flags); - geometry.geometry.aabbs.sType = VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_GEOMETRY_AABBS_DATA_KHR; - geometry.geometry.aabbs.data.deviceAddress = proceduralPrimitives.aabbBuffers[0].getDeviceAddress(); - geometry.geometry.aabbs.stride = proceduralPrimitives.aabbStride; - - primitiveCounts[i] = proceduralPrimitives.primitiveCount; - } - - buildInfo.type = VK_ACCELERATION_STRUCTURE_TYPE_BOTTOM_LEVEL_KHR; - break; - } - default: - return SLANG_E_INVALID_ARG; - } - - return SLANG_OK; -} - } // namespace rhi::vk diff --git a/src/vulkan/vk-util.h b/src/vulkan/vk-util.h index 19bfb7da..82a1430b 100644 --- a/src/vulkan/vk-util.h +++ b/src/vulkan/vk-util.h @@ -130,53 +130,4 @@ struct VulkanUtil static VkSamplerReductionMode translateReductionOp(TextureReductionOp op); }; -struct AccelerationStructureBuildGeometryInfoBuilder -{ -public: - VkAccelerationStructureBuildGeometryInfoKHR buildInfo = { - VK_STRUCTURE_TYPE_ACCELERATION_STRUCTURE_BUILD_GEOMETRY_INFO_KHR - }; - std::vector primitiveCounts; - - Result build(const AccelerationStructureBuildDesc& buildDesc, IDebugCallback* debugCallback); - -private: - std::vector geometries; - - VkBuildAccelerationStructureFlagsKHR translateBuildFlags(AccelerationStructureBuildFlags flags) - { - VkBuildAccelerationStructureFlagsKHR result = VkBuildAccelerationStructureFlagsKHR(0); - if (is_set(flags, AccelerationStructureBuildFlags::AllowCompaction)) - { - result |= VK_BUILD_ACCELERATION_STRUCTURE_ALLOW_COMPACTION_BIT_KHR; - } - if (is_set(flags, AccelerationStructureBuildFlags::AllowUpdate)) - { - result |= VK_BUILD_ACCELERATION_STRUCTURE_ALLOW_UPDATE_BIT_KHR; - } - if (is_set(flags, AccelerationStructureBuildFlags::MinimizeMemory)) - { - result |= VK_BUILD_ACCELERATION_STRUCTURE_LOW_MEMORY_BIT_KHR; - } - if (is_set(flags, AccelerationStructureBuildFlags::PreferFastBuild)) - { - result |= VK_BUILD_ACCELERATION_STRUCTURE_PREFER_FAST_BUILD_BIT_KHR; - } - if (is_set(flags, AccelerationStructureBuildFlags::PreferFastTrace)) - { - result |= VK_BUILD_ACCELERATION_STRUCTURE_PREFER_FAST_TRACE_BIT_KHR; - } - return result; - } - VkGeometryFlagsKHR translateGeometryFlags(AccelerationStructureGeometryFlags flags) - { - VkGeometryFlagsKHR result = VkGeometryFlagsKHR(0); - if (is_set(flags, AccelerationStructureGeometryFlags::Opaque)) - result |= VK_GEOMETRY_OPAQUE_BIT_KHR; - if (is_set(flags, AccelerationStructureGeometryFlags::NoDuplicateAnyHitInvocation)) - result |= VK_GEOMETRY_NO_DUPLICATE_ANY_HIT_INVOCATION_BIT_KHR; - return result; - } -}; - } // namespace rhi::vk