Mesa (master): v3dv: blit shader clean-ups

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Tue Nov 17 12:17:46 UTC 2020


Module: Mesa
Branch: master
Commit: ba2e979b5ce0e813c2a00c06514a7a1b8b1621d9
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=ba2e979b5ce0e813c2a00c06514a7a1b8b1621d9

Author: Iago Toral Quiroga <itoral at igalia.com>
Date:   Tue Nov 17 09:22:20 2020 +0100

v3dv: blit shader clean-ups

This avoids redundant per-layer operations that are the same across
layers or that only need to do once. Namely:

- The sampler for the blit source is the same for all layers.
- The decision about whether we need to load TLB contents or not only
  needs to be done once.
- Some command buffer state such as the pipeline, the viewport and the
  scissor is the same for all layers and should only be bound once.

Reviewed-by: Alejandro Piñeiro <apinheiro at igalia.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/7651>

---

 src/broadcom/vulkan/v3dv_meta_copy.c | 128 +++++++++++++++++++----------------
 1 file changed, 69 insertions(+), 59 deletions(-)

diff --git a/src/broadcom/vulkan/v3dv_meta_copy.c b/src/broadcom/vulkan/v3dv_meta_copy.c
index 0f0ce58786f..9fde1ee89fb 100644
--- a/src/broadcom/vulkan/v3dv_meta_copy.c
+++ b/src/broadcom/vulkan/v3dv_meta_copy.c
@@ -4802,6 +4802,7 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
             bool dst_is_padded_image)
 {
    bool handled = true;
+   VkResult result;
 
    /* We don't support rendering to linear depth/stencil, this should have
     * been rewritten to a compatible color blit by the caller.
@@ -4959,7 +4960,6 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
       0.0f
    };
 
-
    /* For blits from 3D images we also need to compute the slice coordinate to
     * sample from, which will change for each layer in the destination.
     * Compute the step we should increase for each iteration.
@@ -4981,17 +4981,64 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
    struct v3dv_device *device = cmd_buffer->device;
    assert(device->meta.blit.dslayout);
 
+   VkDevice _device = v3dv_device_to_handle(device);
+   VkCommandBuffer _cmd_buffer = v3dv_cmd_buffer_to_handle(cmd_buffer);
+
+   /* Create sampler for blit source image */
+   VkSamplerCreateInfo sampler_info = {
+      .sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
+      .magFilter = filter,
+      .minFilter = filter,
+      .addressModeU = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
+      .addressModeV = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
+      .addressModeW = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
+      .mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST,
+   };
+   VkSampler sampler;
+   result = v3dv_CreateSampler(_device, &sampler_info, &device->alloc,
+                               &sampler);
+   if (result != VK_SUCCESS)
+      goto fail;
+
+   v3dv_cmd_buffer_add_private_obj(
+      cmd_buffer, (uintptr_t)sampler,
+      (v3dv_cmd_buffer_private_obj_destroy_cb)v3dv_DestroySampler);
+
    /* Push command buffer state before starting meta operation */
    v3dv_cmd_buffer_meta_state_push(cmd_buffer, true);
 
-   /* Setup framebuffer */
-   VkDevice _device = v3dv_device_to_handle(device);
-   VkCommandBuffer _cmd_buffer = v3dv_cmd_buffer_to_handle(cmd_buffer);
+   /* Push state that is common for all layers */
+   v3dv_CmdBindPipeline(_cmd_buffer,
+                        VK_PIPELINE_BIND_POINT_GRAPHICS,
+                        pipeline->pipeline);
 
-   VkResult result;
+   const VkViewport viewport = {
+      .x = dst_x,
+      .y = dst_y,
+      .width = dst_w,
+      .height = dst_h,
+      .minDepth = 0.0f,
+      .maxDepth = 1.0f
+   };
+   v3dv_CmdSetViewport(_cmd_buffer, 0, 1, &viewport);
+
+   const VkRect2D scissor = {
+      .offset = { dst_x, dst_y },
+      .extent = { dst_w, dst_h }
+   };
+   v3dv_CmdSetScissor(_cmd_buffer, 0, 1, &scissor);
+
+   bool can_skip_tlb_load;
+   const VkRect2D render_area = {
+      .offset = { dst_x, dst_y },
+      .extent = { dst_w, dst_h },
+   };
+
+   /* Record per-layer commands */
    uint32_t dirty_dynamic_state = 0;
    VkImageAspectFlags aspects = region.dstSubresource.aspectMask;
    for (uint32_t i = 0; i < layer_count; i++) {
+      /* Setup framebuffer */
       VkImageViewCreateInfo dst_image_view_info = {
          .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
          .image = v3dv_image_to_handle(dst),
@@ -5050,25 +5097,6 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
       if (result != VK_SUCCESS)
          goto fail;
 
-      VkSamplerCreateInfo sampler_info = {
-         .sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
-         .magFilter = filter,
-         .minFilter = filter,
-         .addressModeU = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
-         .addressModeV = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
-         .addressModeW = VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE,
-         .mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST,
-      };
-      VkSampler sampler;
-      result = v3dv_CreateSampler(_device, &sampler_info, &device->alloc,
-                                  &sampler);
-      if (result != VK_SUCCESS)
-         goto fail;
-
-      v3dv_cmd_buffer_add_private_obj(
-         cmd_buffer, (uintptr_t)sampler,
-         (v3dv_cmd_buffer_private_obj_destroy_cb)v3dv_DestroySampler);
-
       VkImageViewCreateInfo src_image_view_info = {
          .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
          .image = v3dv_image_to_handle(src),
@@ -5110,22 +5138,29 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
       };
       v3dv_UpdateDescriptorSets(_device, 1, &write, 0, NULL);
 
+      v3dv_CmdBindDescriptorSets(_cmd_buffer,
+                                 VK_PIPELINE_BIND_POINT_GRAPHICS,
+                                 device->meta.blit.playout,
+                                 0, 1, &set,
+                                 0, NULL);
+
       /* If the region we are about to blit is tile-aligned, then we can
        * use the render pass version that won't pre-load the tile buffer
        * with the dst image contents before the blit. The exception is when we
        * don't have a full color mask, since in that case we need to preserve
        * the original value of some of the color components.
+       *
+       * Since all layers have the same area, we only need to compute this for
+       * the first.
        */
-      const VkRect2D render_area = {
-         .offset = { dst_x, dst_y },
-         .extent = { dst_w, dst_h },
-      };
-      struct v3dv_render_pass *pipeline_pass =
-         v3dv_render_pass_from_handle(pipeline->pass);
-      bool can_skip_tlb_load =
-         cmask == full_cmask &&
-         v3dv_subpass_area_is_tile_aligned(&render_area, framebuffer,
-                                           pipeline_pass, 0);
+      if (i == 0) {
+         struct v3dv_render_pass *pipeline_pass =
+            v3dv_render_pass_from_handle(pipeline->pass);
+         can_skip_tlb_load =
+            cmask == full_cmask &&
+            v3dv_subpass_area_is_tile_aligned(&render_area, framebuffer,
+                                              pipeline_pass, 0);
+      }
 
       /* Record blit */
       VkRenderPassBeginInfo rp_info = {
@@ -5159,31 +5194,6 @@ blit_shader(struct v3dv_cmd_buffer *cmd_buffer,
                             VK_SHADER_STAGE_VERTEX_BIT, 0, 20,
                             &tex_coords);
 
-      v3dv_CmdBindPipeline(_cmd_buffer,
-                           VK_PIPELINE_BIND_POINT_GRAPHICS,
-                           pipeline->pipeline);
-
-      v3dv_CmdBindDescriptorSets(_cmd_buffer,
-                                 VK_PIPELINE_BIND_POINT_GRAPHICS,
-                                 device->meta.blit.playout,
-                                 0, 1, &set,
-                                 0, NULL);
-
-      const VkViewport viewport = {
-         .x = dst_x,
-         .y = dst_y,
-         .width = dst_w,
-         .height = dst_h,
-         .minDepth = 0.0f,
-         .maxDepth = 1.0f
-      };
-      v3dv_CmdSetViewport(_cmd_buffer, 0, 1, &viewport);
-      const VkRect2D scissor = {
-         .offset = { dst_x, dst_y },
-         .extent = { dst_w, dst_h }
-      };
-      v3dv_CmdSetScissor(_cmd_buffer, 0, 1, &scissor);
-
       v3dv_CmdDraw(_cmd_buffer, 4, 1, 0, 0);
 
       v3dv_CmdEndRenderPass(_cmd_buffer);



More information about the mesa-commit mailing list