[Vulkan] Shared memory descriptor set
This commit is contained in:
parent
d7341f9873
commit
afe304b328
|
@ -25,6 +25,9 @@ namespace gpu {
|
||||||
// system page size granularity.
|
// system page size granularity.
|
||||||
class SharedMemory {
|
class SharedMemory {
|
||||||
public:
|
public:
|
||||||
|
static constexpr uint32_t kBufferSizeLog2 = 29;
|
||||||
|
static constexpr uint32_t kBufferSize = 1 << kBufferSizeLog2;
|
||||||
|
|
||||||
virtual ~SharedMemory();
|
virtual ~SharedMemory();
|
||||||
// Call in the implementation-specific ClearCache.
|
// Call in the implementation-specific ClearCache.
|
||||||
virtual void ClearCache();
|
virtual void ClearCache();
|
||||||
|
@ -98,9 +101,6 @@ class SharedMemory {
|
||||||
// destructor.
|
// destructor.
|
||||||
void ShutdownCommon();
|
void ShutdownCommon();
|
||||||
|
|
||||||
static constexpr uint32_t kBufferSizeLog2 = 29;
|
|
||||||
static constexpr uint32_t kBufferSize = 1 << kBufferSizeLog2;
|
|
||||||
|
|
||||||
// Sparse allocations are 4 MB, so not too many of them are allocated, but
|
// Sparse allocations are 4 MB, so not too many of them are allocated, but
|
||||||
// also not to waste too much memory for padding (with 16 MB there's too
|
// also not to waste too much memory for padding (with 16 MB there's too
|
||||||
// much).
|
// much).
|
||||||
|
|
|
@ -123,22 +123,23 @@ bool VulkanCommandProcessor::SetupContext() {
|
||||||
uint32_t shared_memory_binding_count = uint32_t(1)
|
uint32_t shared_memory_binding_count = uint32_t(1)
|
||||||
<< shared_memory_binding_count_log2;
|
<< shared_memory_binding_count_log2;
|
||||||
VkDescriptorSetLayoutBinding
|
VkDescriptorSetLayoutBinding
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[1];
|
descriptor_set_layout_bindings_shared_memory_and_edram[1];
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[0].binding = 0;
|
descriptor_set_layout_bindings_shared_memory_and_edram[0].binding = 0;
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[0].descriptorType =
|
descriptor_set_layout_bindings_shared_memory_and_edram[0].descriptorType =
|
||||||
VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
|
VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[0].descriptorCount =
|
descriptor_set_layout_bindings_shared_memory_and_edram[0].descriptorCount =
|
||||||
shared_memory_binding_count;
|
shared_memory_binding_count;
|
||||||
// TODO(Triang3l): When fullDrawIndexUint32 fallback is added, force host
|
// TODO(Triang3l): When fullDrawIndexUint32 fallback is added, force host
|
||||||
// vertex shader access to the shared memory for the tessellation vertex
|
// vertex shader access to the shared memory for the tessellation vertex
|
||||||
// shader (to retrieve tessellation factors).
|
// shader (to retrieve tessellation factors).
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[0].stageFlags =
|
descriptor_set_layout_bindings_shared_memory_and_edram[0].stageFlags =
|
||||||
shader_stages_guest_vertex | VK_SHADER_STAGE_FRAGMENT_BIT;
|
shader_stages_guest_vertex | VK_SHADER_STAGE_FRAGMENT_BIT;
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram[0].pImmutableSamplers =
|
descriptor_set_layout_bindings_shared_memory_and_edram[0].pImmutableSamplers =
|
||||||
nullptr;
|
nullptr;
|
||||||
// TODO(Triang3l): EDRAM binding for the fragment shader interlocks case.
|
// TODO(Triang3l): EDRAM storage image binding for the fragment shader
|
||||||
|
// interlocks case.
|
||||||
descriptor_set_layout_create_info.pBindings =
|
descriptor_set_layout_create_info.pBindings =
|
||||||
descriptor_set_layout_binding_shared_memory_and_edram;
|
descriptor_set_layout_bindings_shared_memory_and_edram;
|
||||||
if (dfn.vkCreateDescriptorSetLayout(
|
if (dfn.vkCreateDescriptorSetLayout(
|
||||||
device, &descriptor_set_layout_create_info, nullptr,
|
device, &descriptor_set_layout_create_info, nullptr,
|
||||||
&descriptor_set_layout_shared_memory_and_edram_) != VK_SUCCESS) {
|
&descriptor_set_layout_shared_memory_and_edram_) != VK_SUCCESS) {
|
||||||
|
@ -155,19 +156,90 @@ bool VulkanCommandProcessor::SetupContext() {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Shared memory and EDRAM common bindings.
|
||||||
|
VkDescriptorPoolSize descriptor_pool_sizes[1];
|
||||||
|
descriptor_pool_sizes[0].type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
|
||||||
|
descriptor_pool_sizes[0].descriptorCount = shared_memory_binding_count;
|
||||||
|
// TODO(Triang3l): EDRAM storage image binding for the fragment shader
|
||||||
|
// interlocks case.
|
||||||
|
VkDescriptorPoolCreateInfo descriptor_pool_create_info;
|
||||||
|
descriptor_pool_create_info.sType =
|
||||||
|
VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO;
|
||||||
|
descriptor_pool_create_info.pNext = nullptr;
|
||||||
|
descriptor_pool_create_info.flags = 0;
|
||||||
|
descriptor_pool_create_info.maxSets = 1;
|
||||||
|
descriptor_pool_create_info.poolSizeCount = 1;
|
||||||
|
descriptor_pool_create_info.pPoolSizes = descriptor_pool_sizes;
|
||||||
|
if (dfn.vkCreateDescriptorPool(device, &descriptor_pool_create_info, nullptr,
|
||||||
|
&shared_memory_and_edram_descriptor_pool_) !=
|
||||||
|
VK_SUCCESS) {
|
||||||
|
XELOGE(
|
||||||
|
"Failed to create the Vulkan descriptor pool for shared memory and "
|
||||||
|
"EDRAM");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
VkDescriptorSetAllocateInfo descriptor_set_allocate_info;
|
||||||
|
descriptor_set_allocate_info.sType =
|
||||||
|
VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
|
||||||
|
descriptor_set_allocate_info.pNext = nullptr;
|
||||||
|
descriptor_set_allocate_info.descriptorPool =
|
||||||
|
shared_memory_and_edram_descriptor_pool_;
|
||||||
|
descriptor_set_allocate_info.descriptorSetCount = 1;
|
||||||
|
descriptor_set_allocate_info.pSetLayouts =
|
||||||
|
&descriptor_set_layout_shared_memory_and_edram_;
|
||||||
|
if (dfn.vkAllocateDescriptorSets(device, &descriptor_set_allocate_info,
|
||||||
|
&shared_memory_and_edram_descriptor_set_) !=
|
||||||
|
VK_SUCCESS) {
|
||||||
|
XELOGE(
|
||||||
|
"Failed to allocate the Vulkan descriptor set for shared memory and "
|
||||||
|
"EDRAM");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
VkDescriptorBufferInfo
|
||||||
|
shared_memory_descriptor_buffers_info[SharedMemory::kBufferSize /
|
||||||
|
(128 << 20)];
|
||||||
|
uint32_t shared_memory_binding_range =
|
||||||
|
SharedMemory::kBufferSize >> shared_memory_binding_count_log2;
|
||||||
|
for (uint32_t i = 0; i < shared_memory_binding_count; ++i) {
|
||||||
|
VkDescriptorBufferInfo& shared_memory_descriptor_buffer_info =
|
||||||
|
shared_memory_descriptor_buffers_info[i];
|
||||||
|
shared_memory_descriptor_buffer_info.buffer = shared_memory_->buffer();
|
||||||
|
shared_memory_descriptor_buffer_info.offset =
|
||||||
|
shared_memory_binding_range * i;
|
||||||
|
shared_memory_descriptor_buffer_info.range = shared_memory_binding_range;
|
||||||
|
}
|
||||||
|
VkWriteDescriptorSet write_descriptor_sets[1];
|
||||||
|
write_descriptor_sets[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
|
||||||
|
write_descriptor_sets[0].pNext = nullptr;
|
||||||
|
write_descriptor_sets[0].dstSet = shared_memory_and_edram_descriptor_set_;
|
||||||
|
write_descriptor_sets[0].dstBinding = 0;
|
||||||
|
write_descriptor_sets[0].dstArrayElement = 0;
|
||||||
|
write_descriptor_sets[0].descriptorCount = shared_memory_binding_count;
|
||||||
|
write_descriptor_sets[0].descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
|
||||||
|
write_descriptor_sets[0].pImageInfo = nullptr;
|
||||||
|
write_descriptor_sets[0].pBufferInfo = shared_memory_descriptor_buffers_info;
|
||||||
|
write_descriptor_sets[0].pTexelBufferView = nullptr;
|
||||||
|
// TODO(Triang3l): EDRAM storage image binding for the fragment shader
|
||||||
|
// interlocks case.
|
||||||
|
dfn.vkUpdateDescriptorSets(device, 1, write_descriptor_sets, 0, nullptr);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void VulkanCommandProcessor::ShutdownContext() {
|
void VulkanCommandProcessor::ShutdownContext() {
|
||||||
AwaitAllQueueOperationsCompletion();
|
AwaitAllQueueOperationsCompletion();
|
||||||
|
|
||||||
shared_memory_.reset();
|
|
||||||
|
|
||||||
const ui::vulkan::VulkanProvider& provider =
|
const ui::vulkan::VulkanProvider& provider =
|
||||||
GetVulkanContext().GetVulkanProvider();
|
GetVulkanContext().GetVulkanProvider();
|
||||||
const ui::vulkan::VulkanProvider::DeviceFunctions& dfn = provider.dfn();
|
const ui::vulkan::VulkanProvider::DeviceFunctions& dfn = provider.dfn();
|
||||||
VkDevice device = provider.device();
|
VkDevice device = provider.device();
|
||||||
|
|
||||||
|
ui::vulkan::util::DestroyAndNullHandle(
|
||||||
|
dfn.vkDestroyDescriptorPool, device,
|
||||||
|
shared_memory_and_edram_descriptor_pool_);
|
||||||
|
|
||||||
|
shared_memory_.reset();
|
||||||
|
|
||||||
for (const auto& pipeline_layout_pair : pipeline_layouts_) {
|
for (const auto& pipeline_layout_pair : pipeline_layouts_) {
|
||||||
dfn.vkDestroyPipelineLayout(
|
dfn.vkDestroyPipelineLayout(
|
||||||
device, pipeline_layout_pair.second.pipeline_layout, nullptr);
|
device, pipeline_layout_pair.second.pipeline_layout, nullptr);
|
||||||
|
|
|
@ -200,6 +200,9 @@ class VulkanCommandProcessor : public CommandProcessor {
|
||||||
std::unordered_map<uint32_t, PipelineLayout> pipeline_layouts_;
|
std::unordered_map<uint32_t, PipelineLayout> pipeline_layouts_;
|
||||||
|
|
||||||
std::unique_ptr<VulkanSharedMemory> shared_memory_;
|
std::unique_ptr<VulkanSharedMemory> shared_memory_;
|
||||||
|
|
||||||
|
VkDescriptorPool shared_memory_and_edram_descriptor_pool_ = VK_NULL_HANDLE;
|
||||||
|
VkDescriptorSet shared_memory_and_edram_descriptor_set_;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace vulkan
|
} // namespace vulkan
|
||||||
|
|
Loading…
Reference in New Issue