mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-07-05 22:41:25 +12:00
vk: Spec compliance.
- TODO: Implement push_constants path instead of copy + bind descriptor sets
This commit is contained in:
parent
d6b4440ef9
commit
26a56ef1f1
3 changed files with 82 additions and 42 deletions
|
@ -655,7 +655,7 @@ VKGSRender::VKGSRender() : GSRender()
|
|||
m_texture_upload_buffer_ring_info.create(VK_BUFFER_USAGE_TRANSFER_SRC_BIT, VK_TEXTURE_UPLOAD_RING_BUFFER_SIZE_M * 0x100000, "texture upload buffer", 32 * 0x100000);
|
||||
|
||||
const auto limits = m_device->gpu().get_limits();
|
||||
m_texbuffer_view_size = std::min(limits.maxTexelBufferElements, 0x4000000u);
|
||||
m_texbuffer_view_size = std::min(limits.maxTexelBufferElements, VK_ATTRIB_RING_BUFFER_SIZE_M * 0x100000u);
|
||||
|
||||
if (m_texbuffer_view_size < 0x800000)
|
||||
{
|
||||
|
@ -1029,6 +1029,38 @@ void VKGSRender::check_heap_status()
|
|||
}
|
||||
}
|
||||
|
||||
void VKGSRender::check_descriptors()
|
||||
{
|
||||
// Ease resource pressure if the number of draw calls becomes too high or we are running low on memory resources
|
||||
const auto required_descriptors = rsx::method_registers.current_draw_clause.pass_count();
|
||||
verify(HERE), required_descriptors < DESCRIPTOR_MAX_DRAW_CALLS;
|
||||
if ((required_descriptors + m_current_frame->used_descriptors) > DESCRIPTOR_MAX_DRAW_CALLS)
|
||||
{
|
||||
//No need to stall if we have more than one frame queue anyway
|
||||
flush_command_queue();
|
||||
|
||||
CHECK_RESULT(vkResetDescriptorPool(*m_device, m_current_frame->descriptor_pool, 0));
|
||||
m_current_frame->used_descriptors = 0;
|
||||
}
|
||||
}
|
||||
|
||||
VkDescriptorSet VKGSRender::allocate_descriptor_set()
|
||||
{
|
||||
verify(HERE), m_current_frame->used_descriptors < DESCRIPTOR_MAX_DRAW_CALLS;
|
||||
|
||||
VkDescriptorSetAllocateInfo alloc_info = {};
|
||||
alloc_info.descriptorPool = m_current_frame->descriptor_pool;
|
||||
alloc_info.descriptorSetCount = 1;
|
||||
alloc_info.pSetLayouts = &descriptor_layouts;
|
||||
alloc_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
|
||||
|
||||
VkDescriptorSet new_descriptor_set;
|
||||
CHECK_RESULT(vkAllocateDescriptorSets(*m_device, &alloc_info, &new_descriptor_set));
|
||||
m_current_frame->used_descriptors++;
|
||||
|
||||
return new_descriptor_set;
|
||||
}
|
||||
|
||||
void VKGSRender::begin()
|
||||
{
|
||||
rsx::thread::begin();
|
||||
|
@ -1042,29 +1074,7 @@ void VKGSRender::begin()
|
|||
if (!framebuffer_status_valid)
|
||||
return;
|
||||
|
||||
//Ease resource pressure if the number of draw calls becomes too high or we are running low on memory resources
|
||||
if (m_current_frame->used_descriptors >= DESCRIPTOR_MAX_DRAW_CALLS)
|
||||
{
|
||||
//No need to stall if we have more than one frame queue anyway
|
||||
flush_command_queue();
|
||||
|
||||
CHECK_RESULT(vkResetDescriptorPool(*m_device, m_current_frame->descriptor_pool, 0));
|
||||
m_current_frame->used_descriptors = 0;
|
||||
}
|
||||
|
||||
check_heap_status();
|
||||
|
||||
VkDescriptorSetAllocateInfo alloc_info = {};
|
||||
alloc_info.descriptorPool = m_current_frame->descriptor_pool;
|
||||
alloc_info.descriptorSetCount = 1;
|
||||
alloc_info.pSetLayouts = &descriptor_layouts;
|
||||
alloc_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
|
||||
|
||||
VkDescriptorSet new_descriptor_set;
|
||||
CHECK_RESULT(vkAllocateDescriptorSets(*m_device, &alloc_info, &new_descriptor_set));
|
||||
|
||||
m_current_frame->descriptor_set = new_descriptor_set;
|
||||
m_current_frame->used_descriptors++;
|
||||
}
|
||||
|
||||
void VKGSRender::update_draw_state()
|
||||
|
@ -1207,25 +1217,36 @@ void VKGSRender::emit_geometry(u32 sub_index)
|
|||
}
|
||||
else
|
||||
{
|
||||
// Vertex env update will change information in the descriptor set
|
||||
// Make a copy for the next draw call
|
||||
// TODO: Restructure program to allow use of push constants when possible
|
||||
// NOTE: AMD has insuffecient push constants buffer memory which is unfortunate
|
||||
VkDescriptorSet new_descriptor_set = allocate_descriptor_set();
|
||||
std::array<VkCopyDescriptorSet, VK_NUM_DESCRIPTOR_BINDINGS> copy_set;
|
||||
|
||||
for (u32 n = 0; n < VK_NUM_DESCRIPTOR_BINDINGS; ++n)
|
||||
{
|
||||
copy_set[n] =
|
||||
{
|
||||
VK_STRUCTURE_TYPE_COPY_DESCRIPTOR_SET, // sType
|
||||
nullptr, // pNext
|
||||
m_current_frame->descriptor_set, // srcSet
|
||||
n, // srcBinding
|
||||
0u, // srcArrayElement
|
||||
new_descriptor_set, // dstSet
|
||||
n, // dstBinding
|
||||
0u, // dstArrayElement
|
||||
1u // descriptorCount
|
||||
};
|
||||
}
|
||||
|
||||
vkUpdateDescriptorSets(*m_device, 0, 0, VK_NUM_DESCRIPTOR_BINDINGS, copy_set.data());
|
||||
m_current_frame->descriptor_set = new_descriptor_set;
|
||||
|
||||
if (persistent_buffer != old_persistent_buffer || volatile_buffer != old_volatile_buffer)
|
||||
{
|
||||
/* VkDescriptorSetAllocateInfo alloc_info = {};
|
||||
alloc_info.descriptorPool = m_current_frame->descriptor_pool;
|
||||
alloc_info.descriptorSetCount = 1;
|
||||
alloc_info.pSetLayouts = &descriptor_layouts;
|
||||
alloc_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO;
|
||||
|
||||
VkDescriptorSet new_descriptor_set;
|
||||
CHECK_RESULT(vkAllocateDescriptorSets(*m_device, &alloc_info, &new_descriptor_set));
|
||||
|
||||
VkCopyDescriptorSet copy = {};
|
||||
copy.sType = VK_STRUCTURE_TYPE_COPY_DESCRIPTOR_SET;
|
||||
copy
|
||||
|
||||
m_current_frame->descriptor_set = new_descriptor_set;
|
||||
m_current_frame->used_descriptors++;
|
||||
|
||||
update_descriptors = true;*/
|
||||
// Rare event, we need to actually change the descriptors
|
||||
update_descriptors = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1236,10 +1257,11 @@ void VKGSRender::emit_geometry(u32 sub_index)
|
|||
{
|
||||
m_program->bind_uniform(persistent_buffer, vk::glsl::program_input_type::input_type_texel_buffer, "persistent_input_stream", m_current_frame->descriptor_set);
|
||||
m_program->bind_uniform(volatile_buffer, vk::glsl::program_input_type::input_type_texel_buffer, "volatile_input_stream", m_current_frame->descriptor_set);
|
||||
|
||||
vkCmdBindDescriptorSets(*m_current_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &m_current_frame->descriptor_set, 0, nullptr);
|
||||
}
|
||||
|
||||
// Bind the new set of descriptors for use with this draw call
|
||||
vkCmdBindDescriptorSets(*m_current_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &m_current_frame->descriptor_set, 0, nullptr);
|
||||
|
||||
//std::chrono::time_point<steady_clock> draw_start = steady_clock::now();
|
||||
//m_setup_time += std::chrono::duration_cast<std::chrono::microseconds>(draw_start - vertex_end).count();
|
||||
|
||||
|
@ -1539,6 +1561,10 @@ void VKGSRender::end()
|
|||
return;
|
||||
}
|
||||
|
||||
// Allocate descriptor set
|
||||
check_descriptors();
|
||||
m_current_frame->descriptor_set = allocate_descriptor_set();
|
||||
|
||||
// Load program execution environment
|
||||
load_program_env();
|
||||
|
||||
|
|
|
@ -424,6 +424,9 @@ private:
|
|||
|
||||
void check_heap_status();
|
||||
|
||||
void check_descriptors();
|
||||
VkDescriptorSet allocate_descriptor_set();
|
||||
|
||||
vk::vertex_upload_info upload_vertex_data();
|
||||
|
||||
bool load_program();
|
||||
|
|
|
@ -257,6 +257,17 @@ namespace rsx
|
|||
return (draw_command_ranges.empty() && inline_vertex_array.empty());
|
||||
}
|
||||
|
||||
u32 pass_count() const
|
||||
{
|
||||
if (draw_command_ranges.empty())
|
||||
{
|
||||
verify(HERE), !inline_vertex_array.empty();
|
||||
return 1u;
|
||||
}
|
||||
|
||||
return (u32)draw_command_ranges.size();
|
||||
}
|
||||
|
||||
void reset(rsx::primitive_type type)
|
||||
{
|
||||
current_range_index = -1u;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue