Sync fix for clear texture
Make pre and post barriers non-conditional on format, as there are cases where pending operations in the GENERAL layout hazarding with clear.
This commit is contained in:
parent
9a9f667818
commit
5191a8e9db
1 changed files with 16 additions and 12 deletions
|
@ -2932,16 +2932,22 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
|
||||
VkCommandBuffer command_buffer = p_sync_with_draw ? frames[frame].draw_command_buffer : frames[frame].setup_command_buffer;
|
||||
|
||||
VkImageLayout layout = src_tex->layout;
|
||||
VkImageLayout clear_layout = (src_tex->layout == VK_IMAGE_LAYOUT_GENERAL) ? VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||
|
||||
if (src_tex->layout != VK_IMAGE_LAYOUT_GENERAL) { //storage may be in general state
|
||||
// NOTE: Perhaps the valid stages/accesses for a given onwner should be a property of the owner. (Here and places like _get_buffer_from_owner)
|
||||
const VkPipelineStageFlags valid_texture_stages = VK_PIPELINE_STAGE_VERTEX_SHADER_BIT | VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT;
|
||||
constexpr VkAccessFlags read_access = VK_ACCESS_SHADER_READ_BIT;
|
||||
constexpr VkAccessFlags read_write_access = VK_ACCESS_SHADER_READ_BIT | VK_ACCESS_SHADER_WRITE_BIT;
|
||||
const VkAccessFlags valid_texture_access = (src_tex->usage_flags & TEXTURE_USAGE_STORAGE_BIT) ? read_write_access : read_access;
|
||||
|
||||
{ // Barrier from previous access with optional layout change (see clear_layout logic above)
|
||||
VkImageMemoryBarrier image_memory_barrier;
|
||||
image_memory_barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
||||
image_memory_barrier.pNext = nullptr;
|
||||
image_memory_barrier.srcAccessMask = 0;
|
||||
image_memory_barrier.srcAccessMask = valid_texture_access;
|
||||
image_memory_barrier.dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
image_memory_barrier.oldLayout = src_tex->layout;
|
||||
image_memory_barrier.newLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||
image_memory_barrier.oldLayout = clear_layout;
|
||||
|
||||
image_memory_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
|
@ -2952,8 +2958,7 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
image_memory_barrier.subresourceRange.baseArrayLayer = src_tex->base_layer + p_base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = p_layers;
|
||||
|
||||
layout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||
vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
vkCmdPipelineBarrier(command_buffer, valid_texture_stages, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
}
|
||||
|
||||
VkClearColorValue clear_color;
|
||||
|
@ -2969,16 +2974,15 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
range.baseMipLevel = src_tex->base_mipmap + p_base_mipmap;
|
||||
range.levelCount = p_mipmaps;
|
||||
|
||||
vkCmdClearColorImage(command_buffer, src_tex->image, layout, &clear_color, 1, &range);
|
||||
|
||||
if (src_tex->layout != VK_IMAGE_LAYOUT_GENERAL) { //storage may be in general state
|
||||
vkCmdClearColorImage(command_buffer, src_tex->image, clear_layout, &clear_color, 1, &range);
|
||||
|
||||
{ // Barrier to post clear accesses (changing back the layout if needed)
|
||||
VkImageMemoryBarrier image_memory_barrier;
|
||||
image_memory_barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
|
||||
image_memory_barrier.pNext = nullptr;
|
||||
image_memory_barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
|
||||
image_memory_barrier.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
|
||||
image_memory_barrier.oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||
image_memory_barrier.dstAccessMask = valid_texture_access;
|
||||
image_memory_barrier.oldLayout = clear_layout;
|
||||
image_memory_barrier.newLayout = src_tex->layout;
|
||||
|
||||
image_memory_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
|
@ -2990,7 +2994,7 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
image_memory_barrier.subresourceRange.baseArrayLayer = src_tex->base_layer + p_base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = p_layers;
|
||||
|
||||
vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_VERTEX_SHADER_BIT | VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, valid_texture_stages, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
}
|
||||
|
||||
return OK;
|
||||
|
|
Loading…
Reference in a new issue