1 /*
2  * Copyright (c) 2024 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef VULKAN_NODE_CONTEXT_POOL_MANAGER_VK_H
17 #define VULKAN_NODE_CONTEXT_POOL_MANAGER_VK_H
18 
19 #include <cstdint>
20 #include <vulkan/vulkan_core.h>
21 
22 #include <base/containers/string.h>
23 #include <base/containers/unordered_map.h>
24 #include <base/containers/vector.h>
25 #include <render/device/pipeline_state_desc.h>
26 #include <render/namespace.h>
27 
28 #include "nodecontext/node_context_pool_manager.h"
29 #include "vulkan/pipeline_create_functions_vk.h"
30 
31 RENDER_BEGIN_NAMESPACE()
32 class Device;
33 class GpuResourceManager;
34 struct RenderCommandBeginRenderPass;
35 struct RenderPassAttachmentCompatibilityDesc;
36 
37 struct LowLevelCommandBufferVk {
38     VkCommandBuffer commandBuffer { VK_NULL_HANDLE };
39     VkSemaphore semaphore { VK_NULL_HANDLE };
40 };
41 
42 struct ContextCommandPoolVk {
43     // every command buffer is taken from the single pool and pre-allocated
44     VkCommandPool commandPool { VK_NULL_HANDLE };
45     LowLevelCommandBufferVk commandBuffer;
46 };
47 
48 struct ContextFramebufferCacheVk {
49     struct CacheValues {
50         uint64_t frameUseIndex { 0 };
51         VkFramebuffer frameBuffer { VK_NULL_HANDLE };
52     };
53     BASE_NS::unordered_map<uint64_t, CacheValues> hashToElement;
54 };
55 
56 struct ContextRenderPassCacheVk {
57     struct CacheValues {
58         uint64_t frameUseIndex { 0 };
59         VkRenderPass renderPass { VK_NULL_HANDLE };
60     };
61     BASE_NS::unordered_map<uint64_t, CacheValues> hashToElement;
62 };
63 
64 class NodeContextPoolManagerVk final : public NodeContextPoolManager {
65 public:
66     explicit NodeContextPoolManagerVk(Device& device, GpuResourceManager& gpuResourceManager, const GpuQueue& gpuQueue);
67     ~NodeContextPoolManagerVk();
68 
69     void BeginFrame() override;
70     void BeginBackendFrame() override;
71 
72     const ContextCommandPoolVk& GetContextCommandPool() const;
73     const ContextCommandPoolVk& GetContextSecondaryCommandPool() const;
74 
75     LowLevelRenderPassDataVk GetRenderPassData(const RenderCommandBeginRenderPass& beginRenderPass);
76 
77 private:
78     Device& device_;
79     GpuResourceManager& gpuResourceMgr_;
80     const GpuQueue gpuQueue_ {};
81 
82     uint32_t bufferingIndex_ { 0 };
83 
84     BASE_NS::vector<ContextCommandPoolVk> commandPools_;
85     BASE_NS::vector<ContextCommandPoolVk> commandSecondaryPools_;
86     ContextFramebufferCacheVk framebufferCache_;
87     ContextRenderPassCacheVk renderPassCache_;
88     ContextRenderPassCacheVk renderPassCompatibilityCache_;
89     RenderPassCreatorVk renderPassCreator_;
90 #if ((RENDER_VALIDATION_ENABLED == 1) || (RENDER_VULKAN_VALIDATION_ENABLED == 1))
91     void SetValidationDebugName(const BASE_NS::string_view debugName) override;
92     BASE_NS::string debugName_;
93     bool firstFrame_ { true };
94 #endif
95 #if (RENDER_VALIDATION_ENABLED == 1)
96     uint64_t frameIndexFront_ { 0 };
97     uint64_t frameIndexBack_ { 0 };
98 #endif
99 };
100 RENDER_END_NAMESPACE()
101 
102 #endif // VULKAN_NODE_CONTEXT_POOL_MANAGER_VK_H
103