From 65668fbc0d583862e0627da35fb65ec05530c555 Mon Sep 17 00:00:00 2001 From: sunghyun kim Date: Wed, 22 Nov 2023 13:59:11 +0900 Subject: [PATCH] [Tizen] Revert "Moved shader cache to graphics backend" This reverts commit 5402aeac11d588e5d906f8e9f87076584b181339. Change-Id: Ic37d2430b50c51fd133a2292795cf6cd4f9e927c --- .../dali-test-suite-utils/test-gl-abstraction.h | 27 +----- dali/internal/file.list | 1 + dali/internal/render/common/render-manager.cpp | 9 +- dali/internal/render/renderers/render-renderer.cpp | 34 ++++--- dali/internal/render/renderers/render-renderer.h | 6 +- dali/internal/render/renderers/shader-cache.cpp | 79 ++++++++++++++++ dali/internal/render/renderers/shader-cache.h | 102 +++++++++++++++++++++ 7 files changed, 211 insertions(+), 47 deletions(-) create mode 100644 dali/internal/render/renderers/shader-cache.cpp create mode 100644 dali/internal/render/renderers/shader-cache.h diff --git a/automated-tests/src/dali/dali-test-suite-utils/test-gl-abstraction.h b/automated-tests/src/dali/dali-test-suite-utils/test-gl-abstraction.h index 3f04a6b..2ca98dc 100644 --- a/automated-tests/src/dali/dali-test-suite-utils/test-gl-abstraction.h +++ b/automated-tests/src/dali/dali-test-suite-utils/test-gl-abstraction.h @@ -1041,32 +1041,7 @@ public: for(const auto& uniform : mActiveUniforms) { - std::string name = uniform.name; - if(uniform.size <= 1) - { - GetUniformLocation(program, name.c_str()); - } - else - { - // Convert single active uniform from "uBlah[0]" or "uStruct[0].element" to N versions of the same - std::string suffix; - auto iter = name.find("["); // Search for index operator - if(iter != std::string::npos) - { - name = uniform.name.substr(0, iter); // Strip off index operator - iter = uniform.name.find("]"); - if(iter != std::string::npos && iter + 1 != uniform.name.length()) - { - suffix = uniform.name.substr(iter + 1); - } - } - for(int i = 0; i < uniform.size; ++i) - { - std::stringstream nss; - nss << name << "[" << i << "]" << suffix; - GetUniformLocation(program, nss.str().c_str()); // Generate N uniforms in the uniform map - } - } + GetUniformLocation(program, uniform.name.c_str()); } for(const auto& uniform : mCustomUniformData) diff --git a/dali/internal/file.list b/dali/internal/file.list index 7556532..2ec62c0 100644 --- a/dali/internal/file.list +++ b/dali/internal/file.list @@ -122,6 +122,7 @@ SET( internal_src_files ${internal_src_dir}/render/renderers/render-sampler.cpp ${internal_src_dir}/render/renderers/render-texture.cpp ${internal_src_dir}/render/renderers/render-vertex-buffer.cpp + ${internal_src_dir}/render/renderers/shader-cache.cpp ${internal_src_dir}/render/renderers/uniform-buffer.cpp ${internal_src_dir}/render/renderers/uniform-buffer-manager.cpp ${internal_src_dir}/render/renderers/uniform-buffer-view.cpp diff --git a/dali/internal/render/common/render-manager.cpp b/dali/internal/render/common/render-manager.cpp index 48464b0..6d42e84 100644 --- a/dali/internal/render/common/render-manager.cpp +++ b/dali/internal/render/common/render-manager.cpp @@ -42,6 +42,7 @@ #include #include #include +#include #include #include #include @@ -141,6 +142,7 @@ struct RenderManager::Impl : graphicsController(graphicsController), renderAlgorithms(graphicsController), programController(graphicsController), + shaderCache(graphicsController), depthBufferAvailable(depthBufferAvailableParam), stencilBufferAvailable(stencilBufferAvailableParam), partialUpdateAvailable(partialUpdateAvailableParam) @@ -195,7 +197,8 @@ struct RenderManager::Impl OwnerKeyContainer textureDiscardQueue; ///< Discarded textures - ProgramController programController; ///< Owner of the programs + ProgramController programController; ///< Owner of the programs + Render::ShaderCache shaderCache; ///< The cache for the graphics shaders std::unique_ptr uniformBufferManager; ///< The uniform buffer manager std::unique_ptr pipelineCache; @@ -249,7 +252,7 @@ void RenderManager::SetShaderSaver(ShaderSaver& upstream) void RenderManager::AddRenderer(const Render::RendererKey& renderer) { // Initialize the renderer as we are now in render thread - renderer->Initialize(mImpl->graphicsController, mImpl->programController, *(mImpl->uniformBufferManager.get()), *(mImpl->pipelineCache.get())); + renderer->Initialize(mImpl->graphicsController, mImpl->programController, mImpl->shaderCache, *(mImpl->uniformBufferManager.get()), *(mImpl->pipelineCache.get())); mImpl->rendererContainer.PushBack(renderer); } @@ -521,6 +524,7 @@ void RenderManager::PreRender(Integration::RenderStatus& status, bool forceClear if(mImpl->frameCount % CACHE_CLEAN_FRAME_COUNT == 1) { mImpl->programController.ResetReferenceCount(); + mImpl->shaderCache.ResetReferenceCount(); } */ @@ -1155,6 +1159,7 @@ void RenderManager::PostRender() if(mImpl->frameCount % CACHE_CLEAN_FRAME_COUNT == 0) { mImpl->programController.ClearUnusedCache(); + mImpl->shaderCache.ClearUnusedCache(); } */ diff --git a/dali/internal/render/renderers/render-renderer.cpp b/dali/internal/render/renderers/render-renderer.cpp index 4baebf9..dbace21 100644 --- a/dali/internal/render/renderers/render-renderer.cpp +++ b/dali/internal/render/renderers/render-renderer.cpp @@ -32,6 +32,7 @@ #include #include #include +#include #include #include #include @@ -239,10 +240,11 @@ Renderer::Renderer(SceneGraph::RenderDataProvider* dataProvider, mBlendingOptions.SetBlendColor(blendColor); } -void Renderer::Initialize(Graphics::Controller& graphicsController, ProgramCache& programCache, Render::UniformBufferManager& uniformBufferManager, Render::PipelineCache& pipelineCache) +void Renderer::Initialize(Graphics::Controller& graphicsController, ProgramCache& programCache, Render::ShaderCache& shaderCache, Render::UniformBufferManager& uniformBufferManager, Render::PipelineCache& pipelineCache) { mGraphicsController = &graphicsController; mProgramCache = &programCache; + mShaderCache = &shaderCache; mUniformBufferManager = &uniformBufferManager; mPipelineCache = &pipelineCache; } @@ -507,28 +509,24 @@ Program* Renderer::PrepareProgram(const SceneGraph::RenderInstruction& instructi // If program doesn't have Gfx program object assigned yet, prepare it. if(!program->GetGraphicsProgramPtr()) { - Graphics::ShaderCreateInfo vertexShaderCreateInfo; - vertexShaderCreateInfo.SetPipelineStage(Graphics::PipelineStage::VERTEX_SHADER); - vertexShaderCreateInfo.SetSourceMode(shaderData->GetSourceMode()); - const std::vector& vertexShaderSrc = shaderData->GetShaderForPipelineStage(Graphics::PipelineStage::VERTEX_SHADER); - vertexShaderCreateInfo.SetSourceSize(vertexShaderSrc.size()); - vertexShaderCreateInfo.SetSourceData(static_cast(vertexShaderSrc.data())); - auto vertexShader = mGraphicsController->CreateShader(vertexShaderCreateInfo, nullptr); - - Graphics::ShaderCreateInfo fragmentShaderCreateInfo; - fragmentShaderCreateInfo.SetPipelineStage(Graphics::PipelineStage::FRAGMENT_SHADER); - fragmentShaderCreateInfo.SetSourceMode(shaderData->GetSourceMode()); - const std::vector& fragmentShaderSrc = shaderData->GetShaderForPipelineStage(Graphics::PipelineStage::FRAGMENT_SHADER); - fragmentShaderCreateInfo.SetSourceSize(fragmentShaderSrc.size()); - fragmentShaderCreateInfo.SetSourceData(static_cast(fragmentShaderSrc.data())); - auto fragmentShader = mGraphicsController->CreateShader(fragmentShaderCreateInfo, nullptr); + const std::vector& vertShader = shaderData->GetShaderForPipelineStage(Graphics::PipelineStage::VERTEX_SHADER); + const std::vector& fragShader = shaderData->GetShaderForPipelineStage(Graphics::PipelineStage::FRAGMENT_SHADER); + Dali::Graphics::Shader& vertexShader = mShaderCache->GetShader( + vertShader, + Graphics::PipelineStage::VERTEX_SHADER, + shaderData->GetSourceMode()); + + Dali::Graphics::Shader& fragmentShader = mShaderCache->GetShader( + fragShader, + Graphics::PipelineStage::FRAGMENT_SHADER, + shaderData->GetSourceMode()); std::vector shaderStates{ Graphics::ShaderState() - .SetShader(*vertexShader.get()) + .SetShader(vertexShader) .SetPipelineStage(Graphics::PipelineStage::VERTEX_SHADER), Graphics::ShaderState() - .SetShader(*fragmentShader.get()) + .SetShader(fragmentShader) .SetPipelineStage(Graphics::PipelineStage::FRAGMENT_SHADER)}; auto createInfo = Graphics::ProgramCreateInfo(); diff --git a/dali/internal/render/renderers/render-renderer.h b/dali/internal/render/renderers/render-renderer.h index c8e9d3c..1daa103 100644 --- a/dali/internal/render/renderers/render-renderer.h +++ b/dali/internal/render/renderers/render-renderer.h @@ -56,6 +56,7 @@ class RenderInstruction; //for reflection effect namespace Render { +struct ShaderCache; class PipelineCache; struct PipelineCacheL2; class UniformBufferManager; @@ -176,11 +177,13 @@ public: * This is called when the renderer is inside render thread * @param[in] graphicsController The graphics controller to use * @param[in] programCache Cache of program objects + * @param[in] shaderCache Cache of shaders * @param[in] uniformBufferManager Uniform buffer manager * @param[in] pipelineCache Cache of pipelines */ void Initialize(Graphics::Controller& graphicsController, ProgramCache& programCache, + Render::ShaderCache& shaderCache, Render::UniformBufferManager& uniformBufferManager, Render::PipelineCache& pipelineCache); @@ -620,7 +623,8 @@ private: Render::Geometry* mGeometry; - ProgramCache* mProgramCache{nullptr}; + ProgramCache* mProgramCache{nullptr}; + Render::ShaderCache* mShaderCache{nullptr}; Render::UniformBufferManager* mUniformBufferManager{}; std::vector mUniformBufferBindings{}; diff --git a/dali/internal/render/renderers/shader-cache.cpp b/dali/internal/render/renderers/shader-cache.cpp new file mode 100644 index 0000000..90d042c --- /dev/null +++ b/dali/internal/render/renderers/shader-cache.cpp @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2023 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include + +namespace Dali +{ +namespace Internal +{ +namespace Render +{ +ShaderCache::ShaderCache(Dali::Graphics::Controller& controller) +: mController(controller) +{ +} + +Dali::Graphics::Shader& ShaderCache::GetShader(const std::vector& shaderCode, Graphics::PipelineStage stage, Graphics::ShaderSourceMode type) +{ + for(auto&& item : mItems) + { + if(item.shaderCode == shaderCode && item.stage == stage && item.type == type) + { + ++item.refCount; + return *item.shader.get(); + } + } + + Graphics::ShaderCreateInfo shaderCreateInfo; + shaderCreateInfo.SetPipelineStage(stage); + shaderCreateInfo.SetSourceData(static_cast(shaderCode.data())); + shaderCreateInfo.SetSourceSize(shaderCode.size()); + shaderCreateInfo.SetSourceMode(type); + + Graphics::UniquePtr shader = mController.CreateShader(shaderCreateInfo, nullptr); + + mItems.emplace_back(std::move(shader), shaderCode, stage, type); + return *mItems.back().shader.get(); +} + +void ShaderCache::ResetReferenceCount() +{ + for(auto&& item : mItems) + { + item.refCount = 0u; + } +} + +void ShaderCache::ClearUnusedCache() +{ + for(auto iter = mItems.begin(); iter != mItems.end();) + { + if(iter->refCount == 0u) + { + iter = mItems.erase(iter); + } + else + { + ++iter; + } + } +} + +} // namespace Render +} // namespace Internal +} // namespace Dali diff --git a/dali/internal/render/renderers/shader-cache.h b/dali/internal/render/renderers/shader-cache.h new file mode 100644 index 0000000..9ed2034 --- /dev/null +++ b/dali/internal/render/renderers/shader-cache.h @@ -0,0 +1,102 @@ +#ifndef DALI_INTERNAL_SHADER_CACHE_H +#define DALI_INTERNAL_SHADER_CACHE_H + +/* + * Copyright (c) 2023 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include +#include + +namespace Dali +{ +namespace Internal +{ +namespace Render +{ +/** + * Caches graphics shaders as they are created by SceneGraph::Shader. + */ +struct ShaderCache +{ + struct Item + { + Item() = default; + Item(const Item&) = delete; + Item(Item&&) = default; + Item& operator=(const Item&) = delete; + Item& operator=(Item&&) = default; + + Item(Graphics::UniquePtr shader, + const std::vector& shaderCode, + Graphics::PipelineStage stage, + Graphics::ShaderSourceMode type) + : shader(std::move(shader)), + shaderCode(shaderCode), + stage(stage), + type(type), + refCount{1u} + { + } + + ~Item() = default; + + Graphics::UniquePtr shader{nullptr}; + std::vector shaderCode; + Graphics::PipelineStage stage; + Graphics::ShaderSourceMode type; + uint16_t refCount; + }; + + /** + * Constructor + * + * @param[in] controller The graphics controller + */ + explicit ShaderCache(Dali::Graphics::Controller& controller); + + /** + * Get a shader from it's source code + * It will increate getted shader item reference count. + * + * @param[in] shaderCode The shader code + * @param[in] stage The pipeline stage (e.g. VERTEX_SHADER or FRAGMENT_SHADER etc.) + * @param[in] type The type of the shader (i.e. text or binary) + * @return the graphics shader + */ + Dali::Graphics::Shader& GetShader(const std::vector& shaderCode, Graphics::PipelineStage stage, Graphics::ShaderSourceMode type); + + /** + * @brief Reset all items reference count as 0. + */ + void ResetReferenceCount(); + + /** + * @brief Clear items who the reference count is 0. + */ + void ClearUnusedCache(); + +private: + std::vector mItems; + Dali::Graphics::Controller& mController; +}; + +} // namespace Render +} // namespace Internal +} // namespace Dali + +#endif //DALI_INTERNAL_SHADER_CACHE_H -- 2.7.4