vk: Fix a few incorrectly calculated scratch buffer sizes

This commit is contained in:
kd-11 2021-07-29 19:21:24 +03:00 committed by kd-11
parent 658b4f70ef
commit f6e4cc14a2
5 changed files with 28 additions and 12 deletions

View file

@ -81,6 +81,7 @@ namespace vk
//Other texture management helpers
void copy_image_to_buffer(VkCommandBuffer cmd, const vk::image* src, const vk::buffer* dst, const VkBufferImageCopy& region, bool swap_bytes = false);
void copy_buffer_to_image(VkCommandBuffer cmd, const vk::buffer* src, const vk::image* dst, const VkBufferImageCopy& region);
u64 calculate_working_buffer_size(u64 base_size, VkImageAspectFlags aspect);
void copy_image_typeless(const command_buffer &cmd, image *src, image *dst, const areai& src_rect, const areai& dst_rect,
u32 mipmaps, VkImageAspectFlags src_transfer_mask = 0xFF, VkImageAspectFlags dst_transfer_mask = 0xFF);

View file

@ -33,6 +33,22 @@ namespace vk
}
}
u64 calculate_working_buffer_size(u64 base_size, VkImageAspectFlags aspect)
{
if (aspect & VK_IMAGE_ASPECT_STENCIL_BIT)
{
return (base_size * 9) / 4;
}
else if (aspect & VK_IMAGE_ASPECT_DEPTH_BIT)
{
return base_size * 2;
}
else
{
return base_size;
}
}
void copy_image_to_buffer(VkCommandBuffer cmd, const vk::image* src, const vk::buffer* dst, const VkBufferImageCopy& region, bool swap_bytes)
{
// Always validate
@ -328,15 +344,7 @@ namespace vk
const auto src_texel_size = vk::get_format_texel_width(src->info.format);
const auto src_length = src_texel_size * src_copy.imageExtent.width * src_copy.imageExtent.height;
u32 min_scratch_size = src_length;
// Check for DS manipulation which will affect scratch memory requirements
if (const VkFlags combined_aspect = src->aspect() | dst->aspect();
(combined_aspect & VK_IMAGE_ASPECT_STENCIL_BIT) != 0)
{
// At least one depth-stencil merge/extract required; requirements change to 2(w*h*bpp) + (w*h)
min_scratch_size = (src_length * 2) + (src_length / src_texel_size);
}
const auto min_scratch_size = calculate_working_buffer_size(src_length, src->aspect() | dst->aspect());
// Initialize scratch memory
auto scratch_buf = vk::get_scratch_buffer(min_scratch_size);
@ -977,6 +985,12 @@ namespace vk
scratch_buf_size += scratch_buf_size;
}
if (requires_depth_processing)
{
// D-S aspect requires a load section that can fit a separated block => D(4) + S(1)
scratch_buf_size += dst_image->width() * dst_image->height() * 5;
}
scratch_buf = vk::get_scratch_buffer(scratch_buf_size);
buffer_copies.reserve(subresource_layout.size());
}

View file

@ -43,8 +43,9 @@ namespace vk
const auto section_length = valid_range.length();
const auto transfer_pitch = real_pitch;
const auto task_length = transfer_pitch * src_area.height();
const auto working_buffer_length = calculate_working_buffer_size(task_length, src->aspect());
auto working_buffer = vk::get_scratch_buffer(task_length);
auto working_buffer = vk::get_scratch_buffer(working_buffer_length);
auto final_mapping = vk::map_dma(valid_range.start, section_length);
VkBufferImageCopy region = {};

View file

@ -151,7 +151,7 @@ namespace vk
return ptr.get();
}
vk::buffer* get_scratch_buffer(u32 min_required_size)
vk::buffer* get_scratch_buffer(u64 min_required_size)
{
auto& scratch_buffer = g_scratch_buffers_pool[0 /*TODO: Replace with Queue Family ID*/].get_buf();

View file

@ -6,7 +6,7 @@ namespace vk
VkSampler null_sampler();
image_view* null_image_view(command_buffer&, VkImageViewType type);
image* get_typeless_helper(VkFormat format, rsx::format_class format_class, u32 requested_width, u32 requested_height);
buffer* get_scratch_buffer(u32 min_required_size);
buffer* get_scratch_buffer(u64 min_required_size);
void clear_scratch_resources();
}