ShaderExecutor: use descriptor arrays when uniform/buffer arrays are used in the...
authorAkos Dirner <adirner.uszeged@partner.samsung.com>
Tue, 1 Mar 2016 18:35:04 +0000 (19:35 +0100)
committerAkos Dirner <adirner.uszeged@partner.samsung.com>
Tue, 1 Mar 2016 18:35:04 +0000 (19:35 +0100)
external/vulkancts/modules/vulkan/shaderexecutor/vktOpaqueTypeIndexingTests.cpp
external/vulkancts/modules/vulkan/shaderexecutor/vktShaderExecutor.cpp
external/vulkancts/modules/vulkan/shaderexecutor/vktShaderExecutor.hpp

index 058f95f..67b9b7c 100644 (file)
@@ -874,8 +874,7 @@ tcu::TestStatus BlockArrayIndexingCaseInstance::iterate (void)
 
                checkSupported(descriptorType);
 
-               for (size_t i = 0 ; i < m_inValues.size(); i++)
-                       m_uniformSetup->addData(new UniformData<deUint32>(bindingLocation++, descriptorType, m_inValues[i]));
+               m_uniformSetup->addData(new UniformArrayData<deUint32>(bindingLocation++, descriptorType, m_inValues));
 
                if (m_indexExprType == INDEX_EXPR_TYPE_DYNAMIC_UNIFORM)
                {
@@ -1007,13 +1006,11 @@ void BlockArrayIndexingCase::createShaderSpec (void)
                global << "const highp int indexBase = 1;\n";
 
        global <<
-               "layout(set = 0, binding = " << binding << ") " << interfaceName << " " << blockName << "\n"
+               "layout(set = 0, binding = " << binding++ << ") " << interfaceName << " " << blockName << "\n"
                "{\n"
                "       highp uint value;\n"
                "} " << instanceName << "[" << numInstances << "];\n";
 
-       binding += numInstances;
-
        if (m_indexExprType == INDEX_EXPR_TYPE_DYNAMIC_UNIFORM)
        {
                for (int readNdx = 0; readNdx < numReads; readNdx++)
index 856e003..d43428c 100644 (file)
@@ -2956,15 +2956,15 @@ ShaderExecutor* createExecutor (glu::ShaderType shaderType, const ShaderSpec& sh
        }
 }
 
-void ShaderExecutor::setupUniformData (const VkDevice&                         vkDevice,
-                                                                          const DeviceInterface&               vk,
-                                                                          const VkQueue                                /*queue*/,
-                                                                          const deUint32                               queueFamilyIndex,
-                                                                          Allocator&                                   memAlloc,
-                                                                          deUint32                                             bindingLocation,
-                                                                          VkDescriptorType                             descriptorType,
-                                                                          deUint32                                             size,
-                                                                          const void*                                  dataPtr)
+de::MovePtr<ShaderExecutor::BufferUniform> ShaderExecutor::createBufferUniform (const VkDevice&                                vkDevice,
+                                                                                                                                                               const DeviceInterface&          vk,
+                                                                                                                                                               const VkQueue                           /*queue*/,
+                                                                                                                                                               const deUint32                          queueFamilyIndex,
+                                                                                                                                                               Allocator&                                      memAlloc,
+                                                                                                                                                               deUint32                                        bindingLocation,
+                                                                                                                                                               VkDescriptorType                        descriptorType,
+                                                                                                                                                               deUint32                                        size,
+                                                                                                                                                               const void*                                     dataPtr)
 {
        DE_ASSERT(descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER || descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_BUFFER);
 
@@ -2996,10 +2996,57 @@ void ShaderExecutor::setupUniformData (const VkDevice&                          vkDevice,
        uniformInfo->buffer = VkBufferSp(new Unique<VkBuffer>(buffer));
        uniformInfo->alloc = AllocationSp(alloc.release());
 
+       return uniformInfo;
+}
+
+void ShaderExecutor::setupUniformData (const VkDevice&                         vkDevice,
+                                                                          const DeviceInterface&               vk,
+                                                                          const VkQueue                                queue,
+                                                                          const deUint32                               queueFamilyIndex,
+                                                                          Allocator&                                   memAlloc,
+                                                                          deUint32                                             bindingLocation,
+                                                                          VkDescriptorType                             descriptorType,
+                                                                          deUint32                                             size,
+                                                                          const void*                                  dataPtr)
+{
+       de::MovePtr<BufferUniform>                      uniform                 = createBufferUniform(vkDevice, vk, queue, queueFamilyIndex, memAlloc, bindingLocation, descriptorType, size, dataPtr);
+
        m_descriptorSetLayoutBuilder.addSingleBinding(descriptorType, VK_SHADER_STAGE_ALL);
        m_descriptorPoolBuilder.addType(descriptorType);
 
-       m_uniformInfos.push_back(UniformInfoSp(new de::UniquePtr<UniformInfo>(uniformInfo)));
+       m_uniformInfos.push_back(UniformInfoSp(new de::UniquePtr<UniformInfo>(uniform)));
+}
+
+void ShaderExecutor::setupUniformArray (const VkDevice&                                vkDevice,
+                                                                               const DeviceInterface&          vk,
+                                                                               const VkQueue                           queue,
+                                                                               const deUint32                          queueFamilyIndex,
+                                                                               Allocator&                                      memAlloc,
+                                                                               deUint32                                        bindingLocation,
+                                                                               VkDescriptorType                        descriptorType,
+                                                                               deUint32                                        arraySize,
+                                                                               deUint32                                        size,
+                                                                               const void*                                     dataPtr)
+{
+       DE_ASSERT(arraySize > 0);
+
+       de::MovePtr<BufferArrayUniform>         bufferArray             (new BufferArrayUniform());
+
+       bufferArray->type = descriptorType;
+       bufferArray->location = bindingLocation;
+
+       for (deUint32 ndx = 0; ndx < arraySize; ++ndx)
+       {
+               const void*                                             bufferData              = ((deUint8*)dataPtr) + (ndx * size);
+               de::MovePtr<BufferUniform>              uniform                 = createBufferUniform(vkDevice, vk, queue, queueFamilyIndex, memAlloc, bindingLocation, descriptorType, size, bufferData);
+
+               bufferArray->uniforms.push_back(BufferUniformSp(new de::UniquePtr<BufferUniform>(uniform)));
+       }
+
+       m_descriptorSetLayoutBuilder.addArrayBinding(descriptorType, arraySize, VK_SHADER_STAGE_ALL);
+       m_descriptorPoolBuilder.addType(descriptorType, arraySize);
+
+       m_uniformInfos.push_back(UniformInfoSp(new de::UniquePtr<UniformInfo>(bufferArray)));
 }
 
 void ShaderExecutor::setupSamplerData (const VkDevice&                         vkDevice,
@@ -3044,7 +3091,7 @@ const void*       ShaderExecutor::getBufferPtr (const deUint32 bindingLocation) const
        for (; it != m_uniformInfos.end(); it++)
        {
                const UniformInfo* uniformInfo = it->get()->get();
-               if (uniformInfo->isBufferUniform() && uniformInfo->location == bindingLocation)
+               if (uniformInfo->getType() == UniformInfo::UNIFORM_TYPE_BUFFER && uniformInfo->location == bindingLocation)
                {
                        const BufferUniform* bufferUniform = static_cast<const BufferUniform*>(uniformInfo);
                        return bufferUniform->alloc->getHostPtr();
@@ -3070,12 +3117,25 @@ void ShaderExecutor::uploadUniforms (DescriptorSetUpdateBuilder& descriptorSetUp
 {
        for (std::vector<UniformInfoSp>::const_iterator it = m_uniformInfos.begin(); it != m_uniformInfos.end(); ++it)
        {
-               const UniformInfo* uniformInfo = it->get()->get();
+               const UniformInfo*                                                      uniformInfo             = it->get()->get();
+               UniformInfo::UniformType                                        uniformType             = uniformInfo->getType();
+
+               if (uniformType == UniformInfo::UNIFORM_TYPE_BUFFER_ARRAY)
+               {
+                       const BufferArrayUniform*                               arrayInfo               = static_cast<const BufferArrayUniform*>(uniformInfo);
+                       std::vector<VkDescriptorBufferInfo>             descriptors;
+
+                       for (std::vector<BufferUniformSp>::const_iterator ait = arrayInfo->uniforms.begin(); ait != arrayInfo->uniforms.end(); ++ait)
+                       {
+                               descriptors.push_back(ait->get()->get()->descriptor);
+                       }
 
-               if (uniformInfo->isSamplerArray())
+                       descriptorSetUpdateBuilder.writeArray(descriptorSet, DescriptorSetUpdateBuilder::Location::binding(uniformInfo->location), uniformInfo->type, (deUint32)descriptors.size(), &descriptors[0]);
+               }
+               else if (uniformType == UniformInfo::UNIFORM_TYPE_SAMPLER_ARRAY)
                {
-                       const SamplerArrayUniform*                      arrayInfo               = static_cast<const SamplerArrayUniform*>(uniformInfo);
-                       std::vector<VkDescriptorImageInfo>      descriptors;
+                       const SamplerArrayUniform*                              arrayInfo               = static_cast<const SamplerArrayUniform*>(uniformInfo);
+                       std::vector<VkDescriptorImageInfo>              descriptors;
 
                        for (std::vector<SamplerUniformSp>::const_iterator ait = arrayInfo->uniforms.begin(); ait != arrayInfo->uniforms.end(); ++ait)
                        {
@@ -3084,14 +3144,14 @@ void ShaderExecutor::uploadUniforms (DescriptorSetUpdateBuilder& descriptorSetUp
 
                        descriptorSetUpdateBuilder.writeArray(descriptorSet, DescriptorSetUpdateBuilder::Location::binding(uniformInfo->location), uniformInfo->type, (deUint32)descriptors.size(), &descriptors[0]);
                }
-               else if (uniformInfo->isBufferUniform())
+               else if (uniformType == UniformInfo::UNIFORM_TYPE_BUFFER)
                {
-                       const BufferUniform* bufferUniform = static_cast<const BufferUniform*>(uniformInfo);
+                       const BufferUniform*                                    bufferUniform   = static_cast<const BufferUniform*>(uniformInfo);
                        descriptorSetUpdateBuilder.writeSingle(descriptorSet, DescriptorSetUpdateBuilder::Location::binding(bufferUniform->location), bufferUniform->type, &bufferUniform->descriptor);
                }
-               else if (uniformInfo->isSamplerUniform())
+               else if (uniformType == UniformInfo::UNIFORM_TYPE_SAMPLER)
                {
-                       const SamplerUniform* samplerUniform = static_cast<const SamplerUniform*>(uniformInfo);
+                       const SamplerUniform*                                   samplerUniform  = static_cast<const SamplerUniform*>(uniformInfo);
                        descriptorSetUpdateBuilder.writeSingle(descriptorSet, DescriptorSetUpdateBuilder::Location::binding(samplerUniform->location), samplerUniform->type, &samplerUniform->descriptor);
                }
        }
index f8b9ad4..474254e 100644 (file)
@@ -130,6 +130,17 @@ public:
                                                                                                 deUint32                                       size,
                                                                                                 const void*                            dataPtr);
 
+       void                                    setupUniformArray       (const VkDevice&                        vkDevice,
+                                                                                                const DeviceInterface&         vk,
+                                                                                                const VkQueue                          queue,
+                                                                                                const deUint32                         queueFamilyIndex,
+                                                                                                Allocator&                                     memAlloc,
+                                                                                                deUint32                                       bindingLocation,
+                                                                                                VkDescriptorType                       descriptorType,
+                                                                                                deUint32                                       arraySize,
+                                                                                                deUint32                                       size,
+                                                                                                const void*                            dataPtr);
+
        void                                    setupSamplerData        (const VkDevice&                        vkDevice,
                                                                                                 const DeviceInterface&         vk,
                                                                                                 const VkQueue                          queue,
@@ -155,7 +166,8 @@ protected:
 
        class UniformInfo;
        typedef de::SharedPtr<de::UniquePtr<UniformInfo> >                      UniformInfoSp;
-
+       class BufferUniform;
+       typedef de::SharedPtr<de::UniquePtr<BufferUniform> >            BufferUniformSp;
        class SamplerUniform;
        typedef de::SharedPtr<de::UniquePtr<SamplerUniform> >           SamplerUniformSp;
 
@@ -168,11 +180,19 @@ protected:
        class UniformInfo
        {
        public:
+               enum UniformType
+               {
+                       UNIFORM_TYPE_BUFFER = 0,
+                       UNIFORM_TYPE_SAMPLER,
+                       UNIFORM_TYPE_BUFFER_ARRAY,
+                       UNIFORM_TYPE_SAMPLER_ARRAY,
+
+                       UNIFORM_TYPE_LAST
+               };
+
                                                                        UniformInfo                     (void) {}
                virtual                                         ~UniformInfo            (void) {}
-               virtual bool                            isSamplerArray          (void) const { return false; }
-               virtual bool                            isBufferUniform         (void) const { return false; }
-               virtual bool                            isSamplerUniform        (void) const { return false; }
+               virtual UniformType                     getType                         (void) const = 0;
 
                VkDescriptorType                        type;
                deUint32                                        location;
@@ -183,7 +203,7 @@ protected:
        public:
                                                                        BufferUniform           (void) {}
                virtual                                         ~BufferUniform          (void) {}
-               virtual bool                            isBufferUniform         (void) const { return true; }
+               virtual UniformType                     getType                         (void) const { return UNIFORM_TYPE_BUFFER; }
 
                VkBufferSp                                      buffer;
                AllocationSp                            alloc;
@@ -195,7 +215,8 @@ protected:
        public:
                                                                        SamplerUniform          (void) {}
                virtual                                         ~SamplerUniform         (void) {}
-               virtual bool                            isSamplerUniform        (void) const { return true; }
+               virtual UniformType                     getType                         (void) const { return UNIFORM_TYPE_SAMPLER; }
+
                VkImageSp                                       image;
                VkImageViewSp                           imageView;
                VkSamplerSp                                     sampler;
@@ -203,12 +224,22 @@ protected:
                VkDescriptorImageInfo           descriptor;
        };
 
+       class BufferArrayUniform : public UniformInfo
+       {
+       public:
+                                                                                       BufferArrayUniform              (void) {}
+               virtual                                                         ~BufferArrayUniform             (void) {}
+               virtual UniformType                                     getType                                 (void) const { return UNIFORM_TYPE_BUFFER_ARRAY; }
+
+               std::vector<BufferUniformSp>            uniforms;
+       };
+
        class SamplerArrayUniform : public UniformInfo
        {
        public:
                                                                                        SamplerArrayUniform             (void) {}
                virtual                                                         ~SamplerArrayUniform    (void) {}
-               virtual bool                                            isSamplerArray                  (void) const { return true; }
+               virtual UniformType                                     getType                                 (void) const { return UNIFORM_TYPE_SAMPLER_ARRAY; }
 
                std::vector<SamplerUniformSp>           uniforms;
        };
@@ -238,6 +269,16 @@ protected:
                                                                                                                                                 VkImageViewType                                imageViewType,
                                                                                                                                                 const void*                                    data);
 
+       de::MovePtr<BufferUniform>                              createBufferUniform                     (const VkDevice&                                vkDevice,
+                                                                                                                                                const DeviceInterface&                 vk,
+                                                                                                                                                const VkQueue                                  queue,
+                                                                                                                                                const deUint32                                 queueFamilyIndex,
+                                                                                                                                                Allocator&                                             memAlloc,
+                                                                                                                                                deUint32                                               bindingLocation,
+                                                                                                                                                VkDescriptorType                               descriptorType,
+                                                                                                                                                deUint32                                               size,
+                                                                                                                                                const void*                                    dataPtr);
+
        const ShaderSpec                                                                        m_shaderSpec;
        const glu::ShaderType                                                           m_shaderType;
 
@@ -299,6 +340,39 @@ void UniformData<T>::setup (ShaderExecutor& executor, const VkDevice& vkDevice,
        executor.setupUniformData(vkDevice, vk, queue, queueFamilyIndex, memAlloc, m_bindingLocation, m_descriptorType, sizeof(T), &m_data);
 }
 
+template<typename T>
+class UniformArrayData : public UniformDataBase
+{
+public:
+                                                       UniformArrayData        (deUint32 bindingLocation, VkDescriptorType descriptorType, const std::vector<T>& data);
+       virtual                                 ~UniformArrayData       (void);
+       virtual void                    setup                           (ShaderExecutor& executor, const VkDevice& vkDevice, const DeviceInterface& vk, const VkQueue queue, const deUint32 queueFamilyIndex, Allocator& memAlloc) const;
+
+private:
+       VkDescriptorType                m_descriptorType;
+       std::vector<T>                  m_data;
+};
+
+template<typename T>
+UniformArrayData<T>::UniformArrayData (deUint32 bindingLocation, VkDescriptorType descriptorType, const std::vector<T>& data)
+       : UniformDataBase               (bindingLocation)
+       , m_descriptorType              (descriptorType)
+       , m_data                                (data)
+{
+}
+
+template<typename T>
+UniformArrayData<T>::~UniformArrayData (void)
+{
+}
+
+template<typename T>
+void UniformArrayData<T>::setup (ShaderExecutor& executor, const VkDevice& vkDevice, const DeviceInterface& vk, const VkQueue queue, const deUint32 queueFamilyIndex, Allocator& memAlloc) const
+{
+       DE_ASSERT(!m_data.empty());
+       executor.setupUniformArray(vkDevice, vk, queue, queueFamilyIndex, memAlloc, m_bindingLocation, m_descriptorType, (deUint32)m_data.size(), sizeof(T), &m_data[0]);
+}
+
 class SamplerUniformData : public UniformDataBase
 {
 public: