summaryrefslogtreecommitdiffstats
path: root/Graphics/GraphicsEngineVulkan
diff options
context:
space:
mode:
authorazhirnov <zh1dron@gmail.com>2021-01-26 07:13:23 +0000
committerazhirnov <zh1dron@gmail.com>2021-01-26 07:13:23 +0000
commitf8491bc2e3bd00dff8d86ad7f3da266005e01483 (patch)
tree5235768a948e41fc2c9516433148f5fa30372daa /Graphics/GraphicsEngineVulkan
parentremoved empty signature, added test for partially compatible pipeline layouts (diff)
downloadDiligentCore-f8491bc2e3bd00dff8d86ad7f3da266005e01483.tar.gz
DiligentCore-f8491bc2e3bd00dff8d86ad7f3da266005e01483.zip
added immutable samplers to descriptor set layout, fixed PRS tests
Diffstat (limited to 'Graphics/GraphicsEngineVulkan')
-rw-r--r--Graphics/GraphicsEngineVulkan/include/PipelineResourceSignatureVkImpl.hpp33
-rw-r--r--Graphics/GraphicsEngineVulkan/src/PipelineLayoutVk.cpp17
-rw-r--r--Graphics/GraphicsEngineVulkan/src/PipelineResourceSignatureVkImpl.cpp42
-rw-r--r--Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp11
4 files changed, 90 insertions, 13 deletions
diff --git a/Graphics/GraphicsEngineVulkan/include/PipelineResourceSignatureVkImpl.hpp b/Graphics/GraphicsEngineVulkan/include/PipelineResourceSignatureVkImpl.hpp
index 4bdb1865..3dfb7a4b 100644
--- a/Graphics/GraphicsEngineVulkan/include/PipelineResourceSignatureVkImpl.hpp
+++ b/Graphics/GraphicsEngineVulkan/include/PipelineResourceSignatureVkImpl.hpp
@@ -83,6 +83,7 @@ public:
Uint32 GetDynamicStorageBufferCount() const { return m_DynamicStorageBufferCount; }
Uint32 GetNumDescriptorSets() const;
+ SHADER_TYPE GetActiveShaderStages() const { return m_ShaderStages; }
Uint32 GetNumShaderStages() const { return m_NumShaderStages; }
SHADER_TYPE GetShaderStageType(Uint32 StageIndex) const;
@@ -92,16 +93,15 @@ public:
SRB = 1 // in SRB
};
- // sizeof(ResourceAttribs) == 12, x64
+ // sizeof(ResourceAttribs) == 16, x64
struct ResourceAttribs
{
private:
static constexpr Uint32 _DescrTypeBits = 4;
static constexpr Uint32 _DescrSetBits = 1;
static constexpr Uint32 _BindingIndexBits = 16;
- static constexpr Uint32 _SamplerIndBits = 10;
+ static constexpr Uint32 _SamplerIndBits = 16;
static constexpr Uint32 _SamplerAssignedBits = 1;
- static_assert((_DescrTypeBits + _DescrSetBits + _BindingIndexBits + _SamplerIndBits + _SamplerAssignedBits) % 8 == 0, "Fields are not properly packed");
static_assert((1u << _DescrTypeBits) >= static_cast<Uint32>(DescriptorType::Count), "Not enough bits to store DescriptorType values");
static_assert((1u << _DescrSetBits) >= MAX_DESCR_SET_PER_SIGNATURE, "Not enough bits to store descriptor set index");
@@ -164,6 +164,28 @@ public:
return m_Desc.Resources[ResIndex];
}
+ struct ImmutableSamplerAttribs
+ {
+ RefCntAutoPtr<ISampler> Ptr;
+ Uint32 DescrSet : 16;
+ Uint32 BindingIndex : 16;
+
+ ImmutableSamplerAttribs() :
+ DescrSet{~0u}, BindingIndex{~0u} {}
+ };
+
+ const ImmutableSamplerAttribs& GetImmutableSamplerAttribs(Uint32 SampIndex) const
+ {
+ VERIFY_EXPR(SampIndex < m_Desc.NumImmutableSamplers);
+ return m_ImmutableSamplers[SampIndex];
+ }
+
+ const ImmutableSamplerDesc& GetImmutableSamplerDesc(Uint32 SampIndex) const
+ {
+ VERIFY_EXPR(SampIndex < m_Desc.NumImmutableSamplers);
+ return m_Desc.ImmutableSamplers[SampIndex];
+ }
+
VkDescriptorSetLayout GetStaticVkDescriptorSetLayout() const { return m_VkDescSetLayouts[0]; }
VkDescriptorSetLayout GetDynamicVkDescriptorSetLayout() const { return m_VkDescSetLayouts[1]; }
@@ -275,10 +297,7 @@ private:
ShaderResourceCacheVk* m_pResourceCache = nullptr;
ShaderVariableManagerVk* m_StaticVarsMgrs = nullptr; // [m_NumShaderStages]
-
- using ImmutableSamplerPtrType = RefCntAutoPtr<ISampler>;
-
- ImmutableSamplerPtrType* m_ImmutableSamplers = nullptr; // [m_Desc.NumImmutableSamplers]
+ ImmutableSamplerAttribs* m_ImmutableSamplers = nullptr; // [m_Desc.NumImmutableSamplers]
SRBMemoryAllocator m_SRBMemAllocator;
};
diff --git a/Graphics/GraphicsEngineVulkan/src/PipelineLayoutVk.cpp b/Graphics/GraphicsEngineVulkan/src/PipelineLayoutVk.cpp
index 7d1d2c7c..969fe16e 100644
--- a/Graphics/GraphicsEngineVulkan/src/PipelineLayoutVk.cpp
+++ b/Graphics/GraphicsEngineVulkan/src/PipelineLayoutVk.cpp
@@ -33,6 +33,7 @@
#include "PipelineLayoutVk.hpp"
#include "RenderDeviceVkImpl.hpp"
#include "VulkanTypeConversions.hpp"
+#include "StringTools.hpp"
namespace Diligent
{
@@ -175,6 +176,22 @@ bool PipelineLayoutVk::GetResourceInfo(const char* Name, SHADER_TYPE Stage, Reso
Info.Type = ResDesc.ResourceType;
Info.BindingIndex = Attr.BindingIndex;
Info.DescrSetIndex = m_FirstDescrSetIndex[i] + Attr.DescrSet;
+ Info.Signature = pSignature;
+ return true;
+ }
+ }
+
+ for (Uint32 s = 0, SampCount = pSignature->GetImmutableSamplerCount(); s < SampCount; ++s)
+ {
+ const auto& Desc = pSignature->GetImmutableSamplerDesc(s);
+ const auto& Attr = pSignature->GetImmutableSamplerAttribs(s);
+
+ if (Attr.Ptr && (Desc.ShaderStages & Stage) && StreqSuff(Name, Desc.SamplerOrTextureName, pSignature->GetCombinedSamplerSuffix()))
+ {
+ Info.Type = SHADER_RESOURCE_TYPE_SAMPLER;
+ Info.BindingIndex = Attr.BindingIndex;
+ Info.DescrSetIndex = m_FirstDescrSetIndex[i] + Attr.DescrSet;
+ Info.Signature = pSignature;
return true;
}
}
diff --git a/Graphics/GraphicsEngineVulkan/src/PipelineResourceSignatureVkImpl.cpp b/Graphics/GraphicsEngineVulkan/src/PipelineResourceSignatureVkImpl.cpp
index d3426240..b51d74b6 100644
--- a/Graphics/GraphicsEngineVulkan/src/PipelineResourceSignatureVkImpl.cpp
+++ b/Graphics/GraphicsEngineVulkan/src/PipelineResourceSignatureVkImpl.cpp
@@ -283,7 +283,7 @@ PipelineResourceSignatureVkImpl::PipelineResourceSignatureVkImpl(IReferenceCount
// Reserve at least 1 element because m_pResourceAttribs must hold a pointer to memory
MemPool.AddSpace<ResourceAttribs>(std::max(1u, Desc.NumResources));
- MemPool.AddSpace<ImmutableSamplerPtrType>(Desc.NumImmutableSamplers);
+ MemPool.AddSpace<ImmutableSamplerAttribs>(Desc.NumImmutableSamplers);
ReserveSpaceForDescription(MemPool, Desc);
@@ -335,7 +335,7 @@ PipelineResourceSignatureVkImpl::PipelineResourceSignatureVkImpl(IReferenceCount
MemPool.Reserve();
m_pResourceAttribs = MemPool.Allocate<ResourceAttribs>(std::max(1u, m_Desc.NumResources));
- m_ImmutableSamplers = MemPool.ConstructArray<ImmutableSamplerPtrType>(m_Desc.NumImmutableSamplers);
+ m_ImmutableSamplers = MemPool.ConstructArray<ImmutableSamplerAttribs>(m_Desc.NumImmutableSamplers);
// The memory is now owned by PipelineResourceSignatureVkImpl and will be freed by Destruct().
auto* Ptr = MemPool.ReleaseOwnership();
@@ -457,10 +457,10 @@ void PipelineResourceSignatureVkImpl::CreateLayout(const CacheOffsetsType& Cache
{
auto& ImmutableSampler = m_ImmutableSamplers[SrcImmutableSamplerInd];
const auto& ImmutableSamplerDesc = m_Desc.ImmutableSamplers[SrcImmutableSamplerInd].Desc;
- if (!ImmutableSampler)
- GetDevice()->CreateSampler(ImmutableSamplerDesc, &ImmutableSampler);
+ if (!ImmutableSampler.Ptr)
+ GetDevice()->CreateSampler(ImmutableSamplerDesc, &ImmutableSampler.Ptr);
- pVkImmutableSamplers = TempAllocator.ConstructArray<VkSampler>(ResDesc.ArraySize, ImmutableSampler.RawPtr<SamplerVkImpl>()->GetVkSampler());
+ pVkImmutableSamplers = TempAllocator.ConstructArray<VkSampler>(ResDesc.ArraySize, ImmutableSampler.Ptr.RawPtr<SamplerVkImpl>()->GetVkSampler());
}
}
@@ -512,6 +512,36 @@ void PipelineResourceSignatureVkImpl::CreateLayout(const CacheOffsetsType& Cache
VERIFY_EXPR(BindingIndices[CACHE_GROUP_DYN_SB_DYN_VAR] == BindingCount[CACHE_GROUP_DYN_UB_DYN_VAR] + BindingCount[CACHE_GROUP_DYN_SB_DYN_VAR]);
VERIFY_EXPR(BindingIndices[CACHE_GROUP_OTHER_DYN_VAR] == BindingCount[CACHE_GROUP_DYN_UB_DYN_VAR] + BindingCount[CACHE_GROUP_DYN_SB_DYN_VAR] + BindingCount[CACHE_GROUP_OTHER_DYN_VAR]);
+ // Add immutable samplers that is not exist in m_Desc.Resources
+ // If static/mutable descriptor set layout is empty, then add samplers to dynamic layout.
+ for (Uint32 i = 0; i < m_Desc.NumImmutableSamplers; ++i)
+ {
+ auto& ImmutableSampler = m_ImmutableSamplers[i];
+ const auto& SamplerDesc = m_Desc.ImmutableSamplers[i];
+ const Uint32 SetIdx = (DSMapping[0] < MAX_DESCR_SET_PER_SIGNATURE ? 0 : 1);
+ auto& BindingIndex = BindingIndices[SetIdx * 3 + 2];
+
+ if (ImmutableSampler.Ptr)
+ continue;
+
+ GetDevice()->CreateSampler(SamplerDesc.Desc, &ImmutableSampler.Ptr);
+
+ ImmutableSampler.DescrSet = DSMapping[SetIdx];
+ ImmutableSampler.BindingIndex = BindingIndex;
+
+ VERIFY_EXPR(ImmutableSampler.BindingIndex == BindingIndex);
+ ++BindingIndex;
+
+ vkSetLayoutBindings[SetIdx].emplace_back();
+ auto& vkSetLayoutBinding = vkSetLayoutBindings[SetIdx].back();
+
+ vkSetLayoutBinding.binding = ImmutableSampler.BindingIndex;
+ vkSetLayoutBinding.descriptorCount = 1;
+ vkSetLayoutBinding.stageFlags = ShaderTypesToVkShaderStageFlags(SamplerDesc.ShaderStages);
+ vkSetLayoutBinding.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER;
+ vkSetLayoutBinding.pImmutableSamplers = TempAllocator.Construct<VkSampler>(ImmutableSampler.Ptr.RawPtr<SamplerVkImpl>()->GetVkSampler());
+ }
+
if (m_Desc.SRBAllocationGranularity > 1)
{
std::array<size_t, MAX_SHADERS_IN_PIPELINE> ShaderVariableDataSizes = {};
@@ -647,7 +677,7 @@ void PipelineResourceSignatureVkImpl::Destruct()
for (Uint32 i = 0; i < m_Desc.NumImmutableSamplers; ++i)
{
- m_ImmutableSamplers[i].~ImmutableSamplerPtrType();
+ m_ImmutableSamplers[i].~ImmutableSamplerAttribs();
}
m_ImmutableSamplers = nullptr;
diff --git a/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp b/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp
index dc184e1b..41585909 100644
--- a/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp
+++ b/Graphics/GraphicsEngineVulkan/src/PipelineStateVkImpl.cpp
@@ -857,6 +857,17 @@ void PipelineStateVkImpl::InitPipelineLayout(const PipelineStateCreateInfo& Crea
"' that is not present in any pipeline resource signature that is used to create pipeline state '",
m_Desc.Name, "'.");
}
+
+ SHADER_RESOURCE_TYPE Type;
+ PIPELINE_RESOURCE_FLAGS Flags;
+ GetShaderResourceTypeAndFlags(Res.Type, Type, Flags);
+ if (Type != Info.Type)
+ {
+ LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource with name '", Res.Name,
+ "' and type '", GetShaderResourceTypeLiteralName(Type), "' that is not compatible with type '",
+ GetShaderResourceTypeLiteralName(Info.Type), "' in pipeline resource signature '", Info.Signature->GetDesc().Name, "'.");
+ }
+
SPIRV[Res.BindingDecorationOffset] = Info.BindingIndex;
SPIRV[Res.DescriptorSetDecorationOffset] = Info.DescrSetIndex;
});