[vulkan] Implenting layouts use for indexing descriptors
This commit is contained in:
parent
603b07a8a4
commit
191af43721
|
|
@ -1,4 +1,4 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2021 yuzu Emulator Project
|
||||
|
|
|
|||
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2021 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
|
@ -27,23 +30,58 @@ public:
|
|||
return device->IsKhrPushDescriptorSupported() &&
|
||||
num_descriptors <= device->MaxPushDescriptors();
|
||||
}
|
||||
|
||||
// TODO(crueter): utilize layout binding flags
|
||||
|
||||
vk::DescriptorSetLayout CreateDescriptorSetLayout(bool use_push_descriptor) const {
|
||||
if (bindings.empty()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
variable_descriptor_count = 0;
|
||||
binding_flags.clear();
|
||||
|
||||
VkDescriptorSetLayoutBindingFlagsCreateInfo binding_flags_ci{
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_BINDING_FLAGS_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.bindingCount = 0,
|
||||
.pBindingFlags = nullptr,
|
||||
};
|
||||
|
||||
const bool use_descriptor_indexing =
|
||||
!use_push_descriptor && device->isExtDescriptorIndexingSupported();
|
||||
const void* layout_next = nullptr;
|
||||
if (use_descriptor_indexing) {
|
||||
binding_flags.assign(bindings.size(), 0);
|
||||
for (size_t i = 0; i < bindings.size(); ++i) {
|
||||
if (bindings[i].descriptorCount > 1) {
|
||||
binding_flags[i] |= VK_DESCRIPTOR_BINDING_PARTIALLY_BOUND_BIT;
|
||||
}
|
||||
}
|
||||
|
||||
if (bindings.back().descriptorCount > 1) {
|
||||
binding_flags.back() |= VK_DESCRIPTOR_BINDING_VARIABLE_DESCRIPTOR_COUNT_BIT;
|
||||
variable_descriptor_count = bindings.back().descriptorCount;
|
||||
}
|
||||
|
||||
binding_flags_ci.bindingCount = static_cast<u32>(binding_flags.size());
|
||||
binding_flags_ci.pBindingFlags = binding_flags.data();
|
||||
layout_next = &binding_flags_ci;
|
||||
}
|
||||
|
||||
const VkDescriptorSetLayoutCreateFlags flags =
|
||||
use_push_descriptor ? VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR : 0;
|
||||
return device->GetLogical().CreateDescriptorSetLayout({
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.pNext = layout_next,
|
||||
.flags = flags,
|
||||
.bindingCount = static_cast<u32>(bindings.size()),
|
||||
.pBindings = bindings.data(),
|
||||
});
|
||||
}
|
||||
|
||||
u32 VariableDescriptorCount() const noexcept {
|
||||
return variable_descriptor_count;
|
||||
}
|
||||
|
||||
vk::DescriptorUpdateTemplate CreateTemplate(VkDescriptorSetLayout descriptor_set_layout,
|
||||
VkPipelineLayout pipeline_layout,
|
||||
bool use_push_descriptor) const {
|
||||
|
|
@ -130,8 +168,10 @@ private:
|
|||
bool is_compute{};
|
||||
boost::container::small_vector<VkDescriptorSetLayoutBinding, 32> bindings;
|
||||
boost::container::small_vector<VkDescriptorUpdateTemplateEntry, 32> entries;
|
||||
mutable boost::container::small_vector<VkDescriptorBindingFlags, 32> binding_flags;
|
||||
u32 binding{};
|
||||
u32 num_descriptors{};
|
||||
mutable u32 variable_descriptor_count{};
|
||||
size_t offset{};
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@
|
|||
#include <numeric>
|
||||
#include <optional>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "video_core/renderer_vulkan/vk_texture_cache.h"
|
||||
|
||||
|
|
@ -237,9 +238,36 @@ ComputePass::ComputePass(const Device& device_, DescriptorPool& descriptor_pool,
|
|||
vk::Span<VkPushConstantRange> push_constants, std::span<const u32> code,
|
||||
std::optional<u32> optional_subgroup_size)
|
||||
: device{device_} {
|
||||
u32 variable_descriptor_count{};
|
||||
std::vector<VkDescriptorBindingFlags> binding_flags;
|
||||
VkDescriptorSetLayoutBindingFlagsCreateInfo binding_flags_ci{
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_BINDING_FLAGS_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.bindingCount = 0,
|
||||
.pBindingFlags = nullptr,
|
||||
};
|
||||
const bool use_descriptor_indexing = device.isExtDescriptorIndexingSupported();
|
||||
const void* layout_next = nullptr;
|
||||
if (use_descriptor_indexing && !bindings.empty()) {
|
||||
binding_flags.assign(bindings.size(), 0);
|
||||
for (size_t i = 0; i < bindings.size(); ++i) {
|
||||
if (bindings[i].descriptorCount > 1) {
|
||||
binding_flags[i] |= VK_DESCRIPTOR_BINDING_PARTIALLY_BOUND_BIT;
|
||||
}
|
||||
}
|
||||
if (bindings.back().descriptorCount > 1) {
|
||||
binding_flags.back() |= VK_DESCRIPTOR_BINDING_VARIABLE_DESCRIPTOR_COUNT_BIT;
|
||||
variable_descriptor_count = bindings.back().descriptorCount;
|
||||
}
|
||||
|
||||
binding_flags_ci.bindingCount = static_cast<u32>(binding_flags.size());
|
||||
binding_flags_ci.pBindingFlags = binding_flags.data();
|
||||
layout_next = &binding_flags_ci;
|
||||
}
|
||||
|
||||
descriptor_set_layout = device.GetLogical().CreateDescriptorSetLayout({
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.pNext = layout_next,
|
||||
.flags = 0,
|
||||
.bindingCount = bindings.size(),
|
||||
.pBindings = bindings.data(),
|
||||
|
|
@ -266,7 +294,8 @@ ComputePass::ComputePass(const Device& device_, DescriptorPool& descriptor_pool,
|
|||
.pipelineLayout = *layout,
|
||||
.set = 0,
|
||||
});
|
||||
descriptor_allocator = descriptor_pool.Allocator(*descriptor_set_layout, bank_info);
|
||||
descriptor_allocator =
|
||||
descriptor_pool.Allocator(*descriptor_set_layout, bank_info, variable_descriptor_count);
|
||||
}
|
||||
if (code.empty()) {
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
|
||||
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2019 yuzu Emulator Project
|
||||
|
|
@ -88,9 +88,10 @@ static void AllocatePool(const Device& device, DescriptorBank& bank) {
|
|||
}
|
||||
|
||||
DescriptorAllocator::DescriptorAllocator(const Device& device_, MasterSemaphore& master_semaphore_,
|
||||
DescriptorBank& bank_, VkDescriptorSetLayout layout_)
|
||||
DescriptorBank& bank_, VkDescriptorSetLayout layout_,
|
||||
u32 variable_descriptor_count_)
|
||||
: ResourcePool(master_semaphore_, SETS_GROW_RATE), device{&device_}, bank{&bank_},
|
||||
layout{layout_} {}
|
||||
layout{layout_}, variable_descriptor_count{variable_descriptor_count_} {}
|
||||
|
||||
VkDescriptorSet DescriptorAllocator::Commit() {
|
||||
const size_t index = CommitResource();
|
||||
|
|
@ -103,9 +104,25 @@ void DescriptorAllocator::Allocate(size_t begin, size_t end) {
|
|||
|
||||
vk::DescriptorSets DescriptorAllocator::AllocateDescriptors(size_t count) {
|
||||
const std::vector<VkDescriptorSetLayout> layouts(count, layout);
|
||||
|
||||
std::vector<u32> variable_descriptor_counts;
|
||||
VkDescriptorSetVariableDescriptorCountAllocateInfo variable_descriptor_count_info{
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_VARIABLE_DESCRIPTOR_COUNT_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.descriptorSetCount = 0,
|
||||
.pDescriptorCounts = nullptr,
|
||||
};
|
||||
const void* allocate_next = nullptr;
|
||||
if (variable_descriptor_count != 0) {
|
||||
variable_descriptor_counts.assign(count, variable_descriptor_count);
|
||||
variable_descriptor_count_info.descriptorSetCount = static_cast<u32>(count);
|
||||
variable_descriptor_count_info.pDescriptorCounts = variable_descriptor_counts.data();
|
||||
allocate_next = &variable_descriptor_count_info;
|
||||
}
|
||||
|
||||
VkDescriptorSetAllocateInfo allocate_info{
|
||||
.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO,
|
||||
.pNext = nullptr,
|
||||
.pNext = allocate_next,
|
||||
.descriptorPool = *bank->pools.back(),
|
||||
.descriptorSetCount = static_cast<u32>(count),
|
||||
.pSetLayouts = layouts.data(),
|
||||
|
|
@ -131,18 +148,22 @@ DescriptorPool::DescriptorPool(const Device& device_, Scheduler& scheduler)
|
|||
DescriptorPool::~DescriptorPool() = default;
|
||||
|
||||
DescriptorAllocator DescriptorPool::Allocator(VkDescriptorSetLayout layout,
|
||||
std::span<const Shader::Info> infos) {
|
||||
return Allocator(layout, MakeBankInfo(infos));
|
||||
std::span<const Shader::Info> infos,
|
||||
u32 variable_descriptor_count) {
|
||||
return Allocator(layout, MakeBankInfo(infos), variable_descriptor_count);
|
||||
}
|
||||
|
||||
DescriptorAllocator DescriptorPool::Allocator(VkDescriptorSetLayout layout,
|
||||
const Shader::Info& info) {
|
||||
return Allocator(layout, MakeBankInfo(std::array{info}));
|
||||
const Shader::Info& info,
|
||||
u32 variable_descriptor_count) {
|
||||
return Allocator(layout, MakeBankInfo(std::array{info}), variable_descriptor_count);
|
||||
}
|
||||
|
||||
DescriptorAllocator DescriptorPool::Allocator(VkDescriptorSetLayout layout,
|
||||
const DescriptorBankInfo& info) {
|
||||
return DescriptorAllocator(device, master_semaphore, Bank(info), layout);
|
||||
const DescriptorBankInfo& info,
|
||||
u32 variable_descriptor_count) {
|
||||
return DescriptorAllocator(device, master_semaphore, Bank(info), layout,
|
||||
variable_descriptor_count);
|
||||
}
|
||||
|
||||
DescriptorBank& DescriptorPool::Bank(const DescriptorBankInfo& reqs) {
|
||||
|
|
|
|||
|
|
@ -1,3 +1,6 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
// SPDX-FileCopyrightText: Copyright 2019 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
|
@ -47,7 +50,8 @@ public:
|
|||
|
||||
private:
|
||||
explicit DescriptorAllocator(const Device& device_, MasterSemaphore& master_semaphore_,
|
||||
DescriptorBank& bank_, VkDescriptorSetLayout layout_);
|
||||
DescriptorBank& bank_, VkDescriptorSetLayout layout_,
|
||||
u32 variable_descriptor_count_);
|
||||
|
||||
void Allocate(size_t begin, size_t end) override;
|
||||
|
||||
|
|
@ -56,6 +60,7 @@ private:
|
|||
const Device* device{};
|
||||
DescriptorBank* bank{};
|
||||
VkDescriptorSetLayout layout{};
|
||||
u32 variable_descriptor_count{};
|
||||
|
||||
std::vector<vk::DescriptorSets> sets;
|
||||
};
|
||||
|
|
@ -69,9 +74,12 @@ public:
|
|||
DescriptorPool(const DescriptorPool&) = delete;
|
||||
|
||||
DescriptorAllocator Allocator(VkDescriptorSetLayout layout,
|
||||
std::span<const Shader::Info> infos);
|
||||
DescriptorAllocator Allocator(VkDescriptorSetLayout layout, const Shader::Info& info);
|
||||
DescriptorAllocator Allocator(VkDescriptorSetLayout layout, const DescriptorBankInfo& info);
|
||||
std::span<const Shader::Info> infos,
|
||||
u32 variable_descriptor_count = 0);
|
||||
DescriptorAllocator Allocator(VkDescriptorSetLayout layout, const Shader::Info& info,
|
||||
u32 variable_descriptor_count = 0);
|
||||
DescriptorAllocator Allocator(VkDescriptorSetLayout layout, const DescriptorBankInfo& info,
|
||||
u32 variable_descriptor_count = 0);
|
||||
|
||||
private:
|
||||
DescriptorBank& Bank(const DescriptorBankInfo& reqs);
|
||||
|
|
|
|||
|
|
@ -273,7 +273,8 @@ GraphicsPipeline::GraphicsPipeline(
|
|||
descriptor_set_layout = builder.CreateDescriptorSetLayout(uses_push_descriptor);
|
||||
|
||||
if (!uses_push_descriptor) {
|
||||
descriptor_allocator = descriptor_pool.Allocator(*descriptor_set_layout, stage_infos);
|
||||
descriptor_allocator = descriptor_pool.Allocator(
|
||||
*descriptor_set_layout, stage_infos, builder.VariableDescriptorCount());
|
||||
}
|
||||
|
||||
const VkDescriptorSetLayout set_layout{*descriptor_set_layout};
|
||||
|
|
|
|||
|
|
@ -475,6 +475,9 @@ Device::Device(VkInstance instance_, vk::PhysicalDevice physical_, VkSurfaceKHR
|
|||
|
||||
if (extensions.descriptor_indexing && Settings::values.descriptor_indexing.GetValue()) {
|
||||
first_next = &descriptor_indexing;
|
||||
} else {
|
||||
RemoveExtension(extensions.descriptor_indexing,
|
||||
VK_EXT_DESCRIPTOR_INDEXING_EXTENSION_NAME);
|
||||
}
|
||||
|
||||
is_blit_depth24_stencil8_supported = TestDepthStencilBlits(VK_FORMAT_D24_UNORM_S8_UINT);
|
||||
|
|
|
|||
Loading…
Reference in New Issue