diff options
| author | Egor Yusov <egor.yusov@gmail.com> | 2018-04-11 05:34:26 +0000 |
|---|---|---|
| committer | Egor Yusov <egor.yusov@gmail.com> | 2018-04-11 05:34:26 +0000 |
| commit | b0e7f725f922b138eb0090eb3bd41eb562c39887 (patch) | |
| tree | 32b87b5fa3585d9b20a22c72ea84433f7b1eeae3 /Graphics/GraphicsEngineVulkan | |
| parent | Minor changes (diff) | |
| download | DiligentCore-b0e7f725f922b138eb0090eb3bd41eb562c39887.tar.gz DiligentCore-b0e7f725f922b138eb0090eb3bd41eb562c39887.zip | |
Added vulkan render pass creation
Diffstat (limited to 'Graphics/GraphicsEngineVulkan')
6 files changed, 123 insertions, 2 deletions
diff --git a/Graphics/GraphicsEngineVulkan/include/PipelineStateVkImpl.h b/Graphics/GraphicsEngineVulkan/include/PipelineStateVkImpl.h index 762511ba..65e9eb3d 100644 --- a/Graphics/GraphicsEngineVulkan/include/PipelineStateVkImpl.h +++ b/Graphics/GraphicsEngineVulkan/include/PipelineStateVkImpl.h @@ -32,6 +32,7 @@ #include "RootSignature.h" #include "ShaderResourceLayoutVk.h" #include "AdaptiveFixedBlockAllocator.h" +#include "VulkanUtilities/VulkanObjectWrappers.h" /// Namespace for the Direct3D11 implementation of the graphics engine namespace Diligent @@ -82,6 +83,8 @@ public: private: + void CreateRenderPass(const VulkanUtilities::VulkanLogicalDevice &LogicalDevice); + #if 0 void ParseShaderResourceLayout(IShader *pShader); @@ -123,6 +126,8 @@ private: // Default SRB must be defined after allocators std::unique_ptr<class ShaderResourceBindingVkImpl, STDDeleter<ShaderResourceBindingVkImpl, FixedBlockMemoryAllocator> > m_pDefaultShaderResBinding; #endif + VulkanUtilities::RenderPassWrapper m_RenderPass; + }; } diff --git a/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanLogicalDevice.h b/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanLogicalDevice.h index facdba27..48f6d660 100644 --- a/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanLogicalDevice.h +++ b/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanLogicalDevice.h @@ -68,6 +68,7 @@ namespace VulkanUtilities ImageWrapper CreateImage (const VkImageCreateInfo &ImageCI, const char *DebugName = "")const; ImageViewWrapper CreateImageView (const VkImageViewCreateInfo &ImageViewCI, const char *DebugName = "")const; FenceWrapper CreateFence (const VkFenceCreateInfo &FenceCI, const char *DebugName = "")const; + RenderPassWrapper CreateRenderPass (const VkRenderPassCreateInfo &RenderPassCI,const char *DebugName = "")const; DeviceMemoryWrapper AllocateDeviceMemory(const VkMemoryAllocateInfo &AllocInfo, const char *DebugName = "")const; VkCommandBuffer AllocateVkCommandBuffer(const VkCommandBufferAllocateInfo &AllocInfo, const char *DebugName = "")const; @@ -78,6 +79,7 @@ namespace VulkanUtilities void ReleaseVulkanObject(ImageWrapper&& Image)const; void ReleaseVulkanObject(ImageViewWrapper&& ImageView)const; void ReleaseVulkanObject(FenceWrapper&& Fence)const; + void ReleaseVulkanObject(RenderPassWrapper&& RenderPass)const; void ReleaseVulkanObject(DeviceMemoryWrapper&& Memory)const; VkMemoryRequirements GetBufferMemoryRequirements(VkBuffer vkBuffer)const; diff --git a/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanObjectWrappers.h b/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanObjectWrappers.h index 8e6747a3..745f6b9d 100644 --- a/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanObjectWrappers.h +++ b/Graphics/GraphicsEngineVulkan/include/VulkanUtilities/VulkanObjectWrappers.h @@ -95,4 +95,5 @@ namespace VulkanUtilities using ImageViewWrapper = VulkanObjectWrapper<VkImageView>; using DeviceMemoryWrapper = VulkanObjectWrapper<VkDeviceMemory>; using FenceWrapper = VulkanObjectWrapper<VkFence>; + using RenderPassWrapper = VulkanObjectWrapper<VkRenderPass>; } diff --git a/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp b/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp index e7e59daa..173c7eb9 100644 --- a/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp +++ b/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp @@ -79,6 +79,92 @@ void PipelineStateVkImpl::ParseShaderResourceLayout(IShader *pShader) m_pShaderResourceLayouts[ShaderInd]->Initialize(pDeviceVkImpl->GetVkDevice(), pShaderVk->GetShaderResources(), GetRawAllocator(), nullptr, 0, nullptr, &m_RootSig); } */ + +void PipelineStateVkImpl::CreateRenderPass(const VulkanUtilities::VulkanLogicalDevice &LogicalDevice) +{ + const auto& GraphicsPipeline = m_Desc.GraphicsPipeline; + // Create render pass (7.1) + VkRenderPassCreateInfo RenderPassCI = {}; + RenderPassCI.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO; + RenderPassCI.pNext = nullptr; + RenderPassCI.flags = 0; // reserved for future use + RenderPassCI.attachmentCount = (GraphicsPipeline.DSVFormat != TEX_FORMAT_UNKNOWN ? 1 : 0) + GraphicsPipeline.NumRenderTargets; + std::vector<VkAttachmentDescription> Attachments(RenderPassCI.attachmentCount); + uint32_t AttachmentInd = 0; + VkSampleCountFlagBits SampleCountFlags = static_cast<VkSampleCountFlagBits>(1 << (GraphicsPipeline.SmplDesc.Count - 1)); + VkAttachmentReference DepthAttachmentReference = {}; + if (GraphicsPipeline.DSVFormat != TEX_FORMAT_UNKNOWN) + { + auto& DepthAttachment = Attachments[AttachmentInd]; + DepthAttachmentReference.attachment = AttachmentInd; + DepthAttachmentReference.layout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL; + + DepthAttachment.flags = 0; // Allowed value VK_ATTACHMENT_DESCRIPTION_MAY_ALIAS_BIT + DepthAttachment.format = TexFormatToVkFormat(GraphicsPipeline.DSVFormat); + DepthAttachment.samples = SampleCountFlags; + DepthAttachment.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD; // previous contents of the image within the render area + // will be preserved. For attachments with a depth/stencil format, + // this uses the access type VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_READ_BIT. + DepthAttachment.storeOp = VK_ATTACHMENT_STORE_OP_STORE; // the contents generated during the render pass and within the render + // area are written to memory. For attachments with a depth/stencil format, + // this uses the access type VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT. + DepthAttachment.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_LOAD; + DepthAttachment.stencilStoreOp = VK_ATTACHMENT_STORE_OP_STORE; + DepthAttachment.initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL; + DepthAttachment.finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL; + + ++AttachmentInd; + } + std::vector<VkAttachmentReference> ColorAttachmentReferences(GraphicsPipeline.NumRenderTargets); + for (Uint32 rt = 0; rt < GraphicsPipeline.NumRenderTargets; ++rt, ++AttachmentInd) + { + auto& ColorAttachment = Attachments[AttachmentInd]; + auto& ColorAttachmentRef = ColorAttachmentReferences[rt]; + ColorAttachmentRef.attachment = AttachmentInd; + ColorAttachmentRef.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; + + ColorAttachment.flags = 0; // Allowed value VK_ATTACHMENT_DESCRIPTION_MAY_ALIAS_BIT + ColorAttachment.format = TexFormatToVkFormat(GraphicsPipeline.RTVFormats[rt]); + ColorAttachment.samples = SampleCountFlags; + ColorAttachment.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD; // previous contents of the image within the render area + // will be preserved. For attachments with a depth/stencil format, + // this uses the access type VK_ACCESS_COLOR_ATTACHMENT_READ_BIT. + ColorAttachment.storeOp = VK_ATTACHMENT_STORE_OP_STORE; // the contents generated during the render pass and within the render + // area are written to memory. For attachments with a color format, + // this uses the access type VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT. + ColorAttachment.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; + ColorAttachment.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; + ColorAttachment.initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; + ColorAttachment.finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; + } + + RenderPassCI.pAttachments = Attachments.data(); + + VkSubpassDescription SubpassDesc = {}; + RenderPassCI.subpassCount = 1; + RenderPassCI.pSubpasses = &SubpassDesc; + RenderPassCI.dependencyCount = 0; // the number of dependencies between pairs of subpasses, or zero indicating no dependencies. + RenderPassCI.pDependencies = nullptr; // an array of dependencyCount number of VkSubpassDependency structures describing + // dependencies between pairs of subpasses, or NULL if dependencyCount is zero. + + + SubpassDesc.flags = 0; // All bits for this type are defined by extensions + SubpassDesc.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS; // Currently, only graphics subpasses are supported. + SubpassDesc.inputAttachmentCount = 0; + SubpassDesc.pInputAttachments = nullptr; + SubpassDesc.colorAttachmentCount = GraphicsPipeline.NumRenderTargets; + SubpassDesc.pColorAttachments = ColorAttachmentReferences.data(); + SubpassDesc.pResolveAttachments = nullptr; + SubpassDesc.pDepthStencilAttachment = GraphicsPipeline.DSVFormat != TEX_FORMAT_UNKNOWN ? &DepthAttachmentReference : nullptr; + SubpassDesc.preserveAttachmentCount = 0; + SubpassDesc.pPreserveAttachments = nullptr; + + std::string RenderPassName = "Render pass for '"; + RenderPassName += m_Desc.Name; + RenderPassName += '\''; + m_RenderPass = LogicalDevice.CreateRenderPass(RenderPassCI, RenderPassName.c_str()); +} + PipelineStateVkImpl :: PipelineStateVkImpl(IReferenceCounters *pRefCounters, RenderDeviceVkImpl *pDeviceVk, const PipelineStateDesc &PipelineDesc) : TPipelineStateBase(pRefCounters, pDeviceVk, PipelineDesc)/*, m_DummyVar(*this), @@ -86,7 +172,8 @@ PipelineStateVkImpl :: PipelineStateVkImpl(IReferenceCounters *pRefCounters, Ren m_pDefaultShaderResBinding(nullptr, STDDeleter<ShaderResourceBindingVkImpl, FixedBlockMemoryAllocator>(pDeviceVk->GetSRBAllocator()) ) */ { - //auto pVkDevice = pDeviceVk->GetVkDevice(); + const auto &LogicalDevice = pDeviceVk->GetLogicalDevice(); + if (PipelineDesc.IsComputePipeline) { #if 0 @@ -124,7 +211,8 @@ PipelineStateVkImpl :: PipelineStateVkImpl(IReferenceCounters *pRefCounters, Ren } else { - const auto& GraphicsPipeline = PipelineDesc.GraphicsPipeline; + CreateRenderPass(LogicalDevice); + #if 0 Vk_GRAPHICS_PIPELINE_STATE_DESC VkPSODesc = {}; @@ -231,6 +319,9 @@ PipelineStateVkImpl :: PipelineStateVkImpl(IReferenceCounters *pRefCounters, Ren PipelineStateVkImpl::~PipelineStateVkImpl() { + auto pDeviceVkImpl = ValidatedCast<RenderDeviceVkImpl>(GetDevice()); + pDeviceVkImpl->SafeReleaseVkObject(std::move(m_RenderPass)); + #if 0 auto &ShaderResLayoutAllocator = GetRawAllocator(); for(Int32 l = 0; l < _countof(m_pShaderResourceLayouts); ++l) diff --git a/Graphics/GraphicsEngineVulkan/src/RenderDeviceVkImpl.cpp b/Graphics/GraphicsEngineVulkan/src/RenderDeviceVkImpl.cpp index 6579e643..84917dbb 100644 --- a/Graphics/GraphicsEngineVulkan/src/RenderDeviceVkImpl.cpp +++ b/Graphics/GraphicsEngineVulkan/src/RenderDeviceVkImpl.cpp @@ -410,6 +410,7 @@ template void RenderDeviceVkImpl::SafeReleaseVkObject<VkBufferView>(VulkanUtilit template void RenderDeviceVkImpl::SafeReleaseVkObject<VkImage>(VulkanUtilities::ImageWrapper &&Object); template void RenderDeviceVkImpl::SafeReleaseVkObject<VkImageView>(VulkanUtilities::ImageViewWrapper &&Object); template void RenderDeviceVkImpl::SafeReleaseVkObject<VkDeviceMemory>(VulkanUtilities::DeviceMemoryWrapper &&Object); +template void RenderDeviceVkImpl::SafeReleaseVkObject<VkRenderPass>(VulkanUtilities::RenderPassWrapper &&Object); void RenderDeviceVkImpl::DiscardStaleVkObjects(Uint64 CmdListNumber, Uint64 FenceValue) diff --git a/Graphics/GraphicsEngineVulkan/src/VulkanUtilities/VulkanLogicalDevice.cpp b/Graphics/GraphicsEngineVulkan/src/VulkanUtilities/VulkanLogicalDevice.cpp index f5a89277..23471e99 100644 --- a/Graphics/GraphicsEngineVulkan/src/VulkanUtilities/VulkanLogicalDevice.cpp +++ b/Graphics/GraphicsEngineVulkan/src/VulkanUtilities/VulkanLogicalDevice.cpp @@ -169,6 +169,21 @@ namespace VulkanUtilities return FenceWrapper{ GetSharedPtr(), std::move(vkFence) }; } + RenderPassWrapper VulkanLogicalDevice::CreateRenderPass(const VkRenderPassCreateInfo &RenderPassCI, const char *DebugName)const + { + if (DebugName == nullptr) + DebugName = ""; + + VkRenderPass vkRenderPass = VK_NULL_HANDLE; + auto err = vkCreateRenderPass(m_VkDevice, &RenderPassCI, m_VkAllocator, &vkRenderPass); + CHECK_VK_ERROR_AND_THROW(err, "Failed to create Render Pass '", DebugName, '\''); + + if (DebugName != nullptr && *DebugName != 0) + VulkanUtilities::SetRenderPassName(m_VkDevice, vkRenderPass, DebugName); + + return RenderPassWrapper{ GetSharedPtr(), std::move(vkRenderPass) }; + } + DeviceMemoryWrapper VulkanLogicalDevice::AllocateDeviceMemory(const VkMemoryAllocateInfo &AllocInfo, const char *DebugName)const { @@ -238,6 +253,12 @@ namespace VulkanUtilities Fence.m_VkObject = VK_NULL_HANDLE; } + void VulkanLogicalDevice::ReleaseVulkanObject(RenderPassWrapper&& RenderPass)const + { + vkDestroyRenderPass(m_VkDevice, RenderPass.m_VkObject, m_VkAllocator); + RenderPass.m_VkObject = VK_NULL_HANDLE; + } + void VulkanLogicalDevice::ReleaseVulkanObject(DeviceMemoryWrapper&& Memory)const { vkFreeMemory(m_VkDevice, Memory.m_VkObject, m_VkAllocator); |
