Hash :
8049d082
Author :
Date :
2023-04-20T16:13:34
Vulkan: Split ShareGroupVk class from DisplayVK into its own files When ShareGroupVk class was introduced, it is a bit of convenience to put it in the DisplayVk.h and DisplayVk.cpp files. Now we have added more and more code into ShareGroupVk class and it deserves to have its own files. This CL added two files ShareGroupVk.h and ShareGroupVk.cpp and moved the class into the new files. No functional change is expected. Bug: None Change-Id: I8683a3dc4192612d6ec8abbc7f00424958f09598 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/4454639 Commit-Queue: Charlie Lao <cclao@google.com> Reviewed-by: Shahbaz Youssefi <syoussefi@chromium.org>
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181
//
// Copyright 2023 The ANGLE Project Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
//
// ShareGroupVk.h:
// Defines the class interface for ShareGroupVk, implementing ShareGroupImpl.
//
#ifndef LIBANGLE_RENDERER_VULKAN_SHAREGROUPVK_H_
#define LIBANGLE_RENDERER_VULKAN_SHAREGROUPVK_H_
#include "libANGLE/renderer/DisplayImpl.h"
#include "libANGLE/renderer/vulkan/ResourceVk.h"
#include "libANGLE/renderer/vulkan/vk_cache_utils.h"
#include "libANGLE/renderer/vulkan/vk_helpers.h"
#include "libANGLE/renderer/vulkan/vk_utils.h"
namespace rx
{
constexpr VkDeviceSize kMaxTotalEmptyBufferBytes = 16 * 1024 * 1024;
class RendererVk;
using ContextVkSet = std::set<ContextVk *>;
class TextureUpload
{
public:
TextureUpload() { mPrevUploadedMutableTexture = nullptr; }
~TextureUpload() { resetPrevTexture(); }
angle::Result onMutableTextureUpload(ContextVk *contextVk, TextureVk *newTexture);
void onTextureRelease(TextureVk *textureVk);
void resetPrevTexture() { mPrevUploadedMutableTexture = nullptr; }
private:
// Keep track of the previously stored texture. Used to flush mutable textures.
TextureVk *mPrevUploadedMutableTexture;
};
class UpdateDescriptorSetsBuilder final : angle::NonCopyable
{
public:
UpdateDescriptorSetsBuilder();
~UpdateDescriptorSetsBuilder();
VkDescriptorBufferInfo *allocDescriptorBufferInfos(size_t count);
VkDescriptorImageInfo *allocDescriptorImageInfos(size_t count);
VkWriteDescriptorSet *allocWriteDescriptorSets(size_t count);
VkBufferView *allocBufferViews(size_t count);
VkDescriptorBufferInfo &allocDescriptorBufferInfo() { return *allocDescriptorBufferInfos(1); }
VkDescriptorImageInfo &allocDescriptorImageInfo() { return *allocDescriptorImageInfos(1); }
VkWriteDescriptorSet &allocWriteDescriptorSet() { return *allocWriteDescriptorSets(1); }
VkBufferView &allocBufferView() { return *allocBufferViews(1); }
// Returns the number of written descriptor sets.
uint32_t flushDescriptorSetUpdates(VkDevice device);
private:
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
T *allocDescriptorInfos(std::vector<T> *descriptorVector, size_t count);
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
void growDescriptorCapacity(std::vector<T> *descriptorVector, size_t newSize);
std::vector<VkDescriptorBufferInfo> mDescriptorBufferInfos;
std::vector<VkDescriptorImageInfo> mDescriptorImageInfos;
std::vector<VkWriteDescriptorSet> mWriteDescriptorSets;
std::vector<VkBufferView> mBufferViews;
};
class ShareGroupVk : public ShareGroupImpl
{
public:
ShareGroupVk();
void onDestroy(const egl::Display *display) override;
FramebufferCache &getFramebufferCache() { return mFramebufferCache; }
// PipelineLayoutCache and DescriptorSetLayoutCache can be shared between multiple threads
// accessing them via shared contexts. The ShareGroup locks around gl entrypoints ensuring
// synchronous update to the caches.
PipelineLayoutCache &getPipelineLayoutCache() { return mPipelineLayoutCache; }
DescriptorSetLayoutCache &getDescriptorSetLayoutCache() { return mDescriptorSetLayoutCache; }
const ContextVkSet &getContexts() const { return mContexts; }
vk::MetaDescriptorPool &getMetaDescriptorPool(DescriptorSetIndex descriptorSetIndex)
{
return mMetaDescriptorPools[descriptorSetIndex];
}
size_t getContextCount() const { return mContexts.size(); }
// Used to flush the mutable textures more often.
angle::Result onMutableTextureUpload(ContextVk *contextVk, TextureVk *newTexture);
vk::BufferPool *getDefaultBufferPool(RendererVk *renderer,
VkDeviceSize size,
uint32_t memoryTypeIndex,
BufferUsageType usageType);
void pruneDefaultBufferPools(RendererVk *renderer);
bool isDueForBufferPoolPrune(RendererVk *renderer);
void calculateTotalBufferCount(size_t *bufferCount, VkDeviceSize *totalSize) const;
void logBufferPools() const;
void addContext(ContextVk *contextVk);
void removeContext(ContextVk *contextVk);
// Temporary workaround until VkSemaphore(s) will be used between different priorities.
angle::Result unifyContextsPriority(ContextVk *newContextVk);
// Temporary workaround until VkSemaphore(s) will be used between different priorities.
angle::Result lockDefaultContextsPriority(ContextVk *contextVk);
UpdateDescriptorSetsBuilder *getUpdateDescriptorSetsBuilder()
{
return &mUpdateDescriptorSetsBuilder;
}
void onTextureRelease(TextureVk *textureVk);
angle::Result scheduleMonolithicPipelineCreationTask(
ContextVk *contextVk,
vk::WaitableMonolithicPipelineCreationTask *taskOut);
void waitForCurrentMonolithicPipelineCreationTask();
private:
angle::Result updateContextsPriority(ContextVk *contextVk, egl::ContextPriority newPriority);
// VkFramebuffer caches
FramebufferCache mFramebufferCache;
void resetPrevTexture() { mTextureUpload.resetPrevTexture(); }
// ANGLE uses a PipelineLayout cache to store compatible pipeline layouts.
PipelineLayoutCache mPipelineLayoutCache;
// DescriptorSetLayouts are also managed in a cache.
DescriptorSetLayoutCache mDescriptorSetLayoutCache;
// Descriptor set caches
vk::DescriptorSetArray<vk::MetaDescriptorPool> mMetaDescriptorPools;
// The list of contexts within the share group
ContextVkSet mContexts;
// Priority of all Contexts in the mContexts
egl::ContextPriority mContextsPriority;
bool mIsContextsPriorityLocked;
// Storage for vkUpdateDescriptorSets
UpdateDescriptorSetsBuilder mUpdateDescriptorSetsBuilder;
// The per shared group buffer pools that all buffers should sub-allocate from.
enum class SuballocationAlgorithm : uint8_t
{
Buddy = 0,
General = 1,
InvalidEnum = 2,
EnumCount = InvalidEnum,
};
angle::PackedEnumMap<SuballocationAlgorithm, vk::BufferPoolPointerArray> mDefaultBufferPools;
angle::PackedEnumMap<BufferUsageType, size_t> mSizeLimitForBuddyAlgorithm;
// The system time when last pruneEmptyBuffer gets called.
double mLastPruneTime;
// The system time when the last monolithic pipeline creation job was launched. This is
// rate-limited to avoid hogging all cores and interfering with the application threads. A
// single pipeline creation job is currently supported.
double mLastMonolithicPipelineJobTime;
std::shared_ptr<angle::WaitableEvent> mMonolithicPipelineCreationEvent;
// Texture update manager used to flush uploaded mutable textures.
TextureUpload mTextureUpload;
// If true, it is expected that a BufferBlock may still in used by textures that outlived
// ShareGroup. The non-empty BufferBlock will be put into RendererVk's orphan list instead.
bool mOrphanNonEmptyBufferBlock;
};
} // namespace rx
#endif // LIBANGLE_RENDERER_VULKAN_SHAREGROUPVK_H_