<div dir="ltr"><div class="gmail_quote"><div dir="ltr">On Fri, Jan 11, 2019 at 2:19 AM Iago Toral <<a href="mailto:itoral@igalia.com">itoral@igalia.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">On Mon, 2019-01-07 at 09:39 -0600, Jason Ekstrand wrote:<br>
> This function is modeled after the aux_op functions except that it<br>
> has a<br>
> lot more parameters because it deals with two images as well as<br>
> source<br>
> and destination regions.<br>
> ---<br>
>  src/intel/vulkan/anv_blorp.c   | 225 ++++++++++++++-----------------<br>
> --<br>
>  src/intel/vulkan/anv_private.h |  14 ++<br>
>  2 files changed, 107 insertions(+), 132 deletions(-)<br>
> <br>
> diff --git a/src/intel/vulkan/anv_blorp.c<br>
> b/src/intel/vulkan/anv_blorp.c<br>
> index eee7a8c3b3c..2f8d502e289 100644<br>
> --- a/src/intel/vulkan/anv_blorp.c<br>
> +++ b/src/intel/vulkan/anv_blorp.c<br>
> @@ -1169,63 +1169,52 @@ enum subpass_stage {<br>
>     SUBPASS_STAGE_RESOLVE,<br>
>  };<br>
>  <br>
> -static void<br>
> -resolve_surface(struct blorp_batch *batch,<br>
> -                struct blorp_surf *src_surf,<br>
> -                uint32_t src_level, uint32_t src_layer,<br>
> -                struct blorp_surf *dst_surf,<br>
> -                uint32_t dst_level, uint32_t dst_layer,<br>
> -                uint32_t src_x, uint32_t src_y, uint32_t dst_x,<br>
> uint32_t dst_y,<br>
> -                uint32_t width, uint32_t height,<br>
> -                enum blorp_filter filter)<br>
> -{<br>
> -   blorp_blit(batch,<br>
> -              src_surf, src_level, src_layer,<br>
> -              ISL_FORMAT_UNSUPPORTED, ISL_SWIZZLE_IDENTITY,<br>
> -              dst_surf, dst_level, dst_layer,<br>
> -              ISL_FORMAT_UNSUPPORTED, ISL_SWIZZLE_IDENTITY,<br>
> -              src_x, src_y, src_x + width, src_y + height,<br>
> -              dst_x, dst_y, dst_x + width, dst_y + height,<br>
> -              filter, false, false);<br>
> -}<br>
> -<br>
> -static void<br>
> -resolve_image(struct anv_device *device,<br>
> -              struct blorp_batch *batch,<br>
> -              const struct anv_image *src_image,<br>
> -              VkImageLayout src_image_layout,<br>
> -              uint32_t src_level, uint32_t src_layer,<br>
> -              const struct anv_image *dst_image,<br>
> -              VkImageLayout dst_image_layout,<br>
> -              uint32_t dst_level, uint32_t dst_layer,<br>
> -              VkImageAspectFlags aspect_mask,<br>
> -              uint32_t src_x, uint32_t src_y, uint32_t dst_x,<br>
> uint32_t dst_y,<br>
> -              uint32_t width, uint32_t height)<br>
> +void<br>
> +anv_image_msaa_resolve(struct anv_cmd_buffer *cmd_buffer,<br>
> +                       const struct anv_image *src_image,<br>
> +                       enum isl_aux_usage src_aux_usage,<br>
> +                       uint32_t src_level, uint32_t src_base_layer,<br>
> +                       const struct anv_image *dst_image,<br>
> +                       enum isl_aux_usage dst_aux_usage,<br>
> +                       uint32_t dst_level, uint32_t dst_base_layer,<br>
> +                       VkImageAspectFlagBits aspect,<br>
> +                       uint32_t src_x, uint32_t src_y,<br>
> +                       uint32_t dst_x, uint32_t dst_y,<br>
> +                       uint32_t width, uint32_t height,<br>
> +                       uint32_t layer_count,<br>
> +                       enum blorp_filter filter)<br>
>  {<br>
> -   struct anv_cmd_buffer *cmd_buffer = batch->driver_batch;<br>
> +   struct blorp_batch batch;<br>
> +   blorp_batch_init(&cmd_buffer->device->blorp, &batch, cmd_buffer,<br>
> 0);<br>
>  <br>
>     assert(src_image->type == VK_IMAGE_TYPE_2D);<br>
>     assert(src_image->samples > 1);<br>
>     assert(dst_image->type == VK_IMAGE_TYPE_2D);<br>
>     assert(dst_image->samples == 1);<br>
>     assert(src_image->n_planes == dst_image->n_planes);<br>
> +   assert(!src_image->format->can_ycbcr);<br>
> +   assert(!dst_image->format->can_ycbcr);<br>
>  <br>
> -   uint32_t aspect_bit;<br>
> -<br>
> -   anv_foreach_image_aspect_bit(aspect_bit, src_image, aspect_mask)<br>
> {<br>
> -      struct blorp_surf src_surf, dst_surf;<br>
> -      get_blorp_surf_for_anv_image(device, src_image, 1UL <<<br>
> aspect_bit,<br>
> -                                   src_image_layout,<br>
> ISL_AUX_USAGE_NONE,<br>
> -                                   &src_surf);<br>
> -      get_blorp_surf_for_anv_image(device, dst_image, 1UL <<<br>
> aspect_bit,<br>
> -                                   dst_image_layout,<br>
> ISL_AUX_USAGE_NONE,<br>
> -                                   &dst_surf);<br>
> -      anv_cmd_buffer_mark_image_written(cmd_buffer, dst_image,<br>
> -                                        1UL << aspect_bit,<br>
> -                                        dst_surf.aux_usage,<br>
> -                                        dst_level, dst_layer, 1);<br>
> -<br>
> -      enum blorp_filter filter;<br>
> +   struct blorp_surf src_surf, dst_surf;<br>
> +   get_blorp_surf_for_anv_image(cmd_buffer->device, src_image,<br>
> aspect,<br>
> +                                ANV_IMAGE_LAYOUT_EXPLICIT_AUX,<br>
> +                                src_aux_usage, &src_surf);<br>
> +   if (src_aux_usage == ISL_AUX_USAGE_MCS) {<br>
> +      src_surf.clear_color_addr = anv_to_blorp_address(<br>
> +         anv_image_get_clear_color_addr(cmd_buffer->device,<br>
> src_image,<br>
> +                                        VK_IMAGE_ASPECT_COLOR_BIT));<br>
> +   }<br>
> +   get_blorp_surf_for_anv_image(cmd_buffer->device, dst_image,<br>
> aspect,<br>
> +                                ANV_IMAGE_LAYOUT_EXPLICIT_AUX,<br>
> +                                dst_aux_usage, &dst_surf);<br>
> +   anv_cmd_buffer_mark_image_written(cmd_buffer, dst_image,<br>
> +                                     aspect, dst_aux_usage,<br>
> +                                     dst_level, dst_base_layer,<br>
> layer_count);<br>
> +<br>
> +   if (filter == BLORP_FILTER_NONE) {<br>
> +      /* If no explicit filter is provided, then it's implied by the<br>
> type of<br>
> +       * the source image.<br>
> +       */<br>
>        if ((src_surf.surf->usage & ISL_SURF_USAGE_DEPTH_BIT) ||<br>
>            (src_surf.surf->usage & ISL_SURF_USAGE_STENCIL_BIT) ||<br>
>            isl_format_has_int_channel(src_surf.surf->format)) {<br>
> @@ -1233,15 +1222,20 @@ resolve_image(struct anv_device *device,<br>
>        } else {<br>
>           filter = BLORP_FILTER_AVERAGE;<br>
>        }<br>
> +   }<br>
>  <br>
> -      assert(!src_image->format->can_ycbcr);<br>
> -      assert(!dst_image->format->can_ycbcr);<br>
> -<br>
> -      resolve_surface(batch,<br>
> -                      &src_surf, src_level, src_layer,<br>
> -                      &dst_surf, dst_level, dst_layer,<br>
> -                      src_x, src_y, dst_x, dst_y, width, height,<br>
> filter);<br>
> +   for (uint32_t l = 0; l < layer_count; l++) {<br>
> +      blorp_blit(&batch,<br>
> +                 &src_surf, src_level, src_base_layer + l,<br>
> +                 ISL_FORMAT_UNSUPPORTED, ISL_SWIZZLE_IDENTITY,<br>
> +                 &dst_surf, dst_level, dst_base_layer + l,<br>
> +                 ISL_FORMAT_UNSUPPORTED, ISL_SWIZZLE_IDENTITY,<br>
> +                 src_x, src_y, src_x + width, src_y + height,<br>
> +                 dst_x, dst_y, dst_x + width, dst_y + height,<br>
> +                 filter, false, false);<br>
>     }<br>
> +<br>
> +   blorp_batch_finish(&batch);<br>
>  }<br>
>  <br>
>  void anv_CmdResolveImage(<br>
> @@ -1257,8 +1251,7 @@ void anv_CmdResolveImage(<br>
>     ANV_FROM_HANDLE(anv_image, src_image, srcImage);<br>
>     ANV_FROM_HANDLE(anv_image, dst_image, dstImage);<br>
>  <br>
> -   struct blorp_batch batch;<br>
> -   blorp_batch_init(&cmd_buffer->device->blorp, &batch, cmd_buffer,<br>
> 0);<br>
> +   assert(!src_image->format->can_ycbcr);<br>
>  <br>
>     for (uint32_t r = 0; r < regionCount; r++) {<br>
>        assert(pRegions[r].srcSubresource.aspectMask ==<br>
> @@ -1269,27 +1262,38 @@ void anv_CmdResolveImage(<br>
>        const uint32_t layer_count =<br>
>           anv_get_layerCount(dst_image, &pRegions[r].dstSubresource);<br>
>  <br>
> -      VkImageAspectFlags src_mask =<br>
> pRegions[r].srcSubresource.aspectMask,<br>
> -         dst_mask = pRegions[r].dstSubresource.aspectMask;<br>
> +      VkImageAspectFlags src_mask =<br>
> pRegions[r].srcSubresource.aspectMask;<br>
> +      VkImageAspectFlags dst_mask =<br>
> pRegions[r].dstSubresource.aspectMask;<br>
>  <br>
>        assert(anv_image_aspects_compatible(src_mask, dst_mask));<br>
>  <br>
> -      for (uint32_t layer = 0; layer < layer_count; layer++) {<br>
> -         resolve_image(cmd_buffer->device, &batch,<br>
> -                       src_image, srcImageLayout,<br>
> -                       pRegions[r].srcSubresource.mipLevel,<br>
> -                       pRegions[r].srcSubresource.baseArrayLayer +<br>
> layer,<br>
> -                       dst_image, dstImageLayout,<br>
> -                       pRegions[r].dstSubresource.mipLevel,<br>
> -                       pRegions[r].dstSubresource.baseArrayLayer +<br>
> layer,<br>
> -                       pRegions[r].dstSubresource.aspectMask,<br>
> -                       pRegions[r].srcOffset.x,<br>
> pRegions[r].srcOffset.y,<br>
> -                       pRegions[r].dstOffset.x,<br>
> pRegions[r].dstOffset.y,<br>
> -                       pRegions[r].extent.width,<br>
> pRegions[r].extent.height);<br>
> +      uint32_t aspect_bit;<br>
> +      anv_foreach_image_aspect_bit(aspect_bit, src_image,<br>
> +                                   pRegions[r].srcSubresource.aspect<br>
> Mask) {<br>
> +         enum isl_aux_usage src_aux_usage =<br>
> +            anv_layout_to_aux_usage(&cmd_buffer->device->info,<br>
> src_image,<br>
> +                                    (1 << aspect_bit),<br>
> srcImageLayout);<br>
> +         enum isl_aux_usage dst_aux_usage =<br>
> +            anv_layout_to_aux_usage(&cmd_buffer->device->info,<br>
> dst_image,<br>
> +                                    (1 << aspect_bit),<br>
> dstImageLayout);<br>
> +<br>
> +         anv_image_msaa_resolve(cmd_buffer,<br>
> +                                src_image, src_aux_usage,<br>
> +                                pRegions[r].srcSubresource.mipLevel,<br>
> +                                pRegions[r].srcSubresource.baseArray<br>
> Layer,<br>
> +                                dst_image, dst_aux_usage,<br>
> +                                pRegions[r].dstSubresource.mipLevel,<br>
> +                                pRegions[r].dstSubresource.baseArray<br>
> Layer,<br>
> +                                (1 << aspect_bit),<br>
> +                                pRegions[r].srcOffset.x,<br>
> +                                pRegions[r].srcOffset.y,<br>
> +                                pRegions[r].dstOffset.x,<br>
> +                                pRegions[r].dstOffset.y,<br>
> +                                pRegions[r].extent.width,<br>
> +                                pRegions[r].extent.height,<br>
> +                                layer_count, BLORP_FILTER_NONE);<br>
>        }<br>
>     }<br>
> -<br>
> -   blorp_batch_finish(&batch);<br>
>  }<br>
>  <br>
>  static enum isl_aux_usage<br>
> @@ -1310,9 +1314,6 @@ anv_cmd_buffer_resolve_subpass(struct<br>
> anv_cmd_buffer *cmd_buffer)<br>
>     struct anv_subpass *subpass = cmd_buffer->state.subpass;<br>
>  <br>
>     if (subpass->has_color_resolve) {<br>
> -      struct blorp_batch batch;<br>
> -      blorp_batch_init(&cmd_buffer->device->blorp, &batch,<br>
> cmd_buffer, 0);<br>
> -<br>
>        /* We are about to do some MSAA resolves.  We need to flush so<br>
> that the<br>
>         * result of writes to the MSAA color attachments show up in<br>
> the sampler<br>
>         * when we blit to the single-sampled resolve target.<br>
> @@ -1345,70 +1346,30 @@ anv_cmd_buffer_resolve_subpass(struct<br>
> anv_cmd_buffer *cmd_buffer)<br>
>           struct anv_image_view *src_iview = fb-<br>
> >attachments[src_att];<br>
>           struct anv_image_view *dst_iview = fb-<br>
> >attachments[dst_att];<br>
>  <br>
> +         const VkRect2D render_area = cmd_buffer->state.render_area;<br>
> +<br>
>           enum isl_aux_usage src_aux_usage =<br>
>              cmd_buffer->state.attachments[src_att].aux_usage;<br>
>           enum isl_aux_usage dst_aux_usage =<br>
>              cmd_buffer->state.attachments[dst_att].aux_usage;<br>
>  <br>
> -         const VkRect2D render_area = cmd_buffer->state.render_area;<br>
> -<br>
>           assert(src_iview->aspect_mask == VK_IMAGE_ASPECT_COLOR_BIT<br>
> &&<br>
>                  dst_iview->aspect_mask ==<br>
> VK_IMAGE_ASPECT_COLOR_BIT);<br>
>  <br>
> -         enum blorp_filter filter;<br>
> -         if (isl_format_has_int_channel(src_iview-<br>
> >planes[0].isl.format)) {<br>
<br>
<br>
This is a bit different from what anv_image_msaa_resolve() does. In the<br>
new helper function we check if the usage is depth or stencil, but this<br>
was checking if the format has any integer channel, which I understand<br>
would be true even for color attachments with integer formats, right?<br>
<br>
Since the average filter seems to require a float type, maybe checking<br>
for integer channels instead of usage in anv_image_msaa_resolve() would<br>
be more correct?<br></blockquote><div><br></div><div>anv_image_msaa_resolve checks usage *and* isl_format_has_int_channel so it does AVERAGE only for color float targets and SAMPLE_0 for everything else.  It's a bit hard to see in the diff but it's there.</div><div><br></div><div>--Jason<br></div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
> -            filter = BLORP_FILTER_SAMPLE_0;<br>
> -         } else {<br>
> -            filter = BLORP_FILTER_AVERAGE;<br>
> -         }<br>
> -<br>
> -         struct blorp_surf src_surf, dst_surf;<br>
> -         get_blorp_surf_for_anv_image(cmd_buffer->device, src_iview-<br>
> >image,<br>
> -                                      VK_IMAGE_ASPECT_COLOR_BIT,<br>
> -                                      ANV_IMAGE_LAYOUT_EXPLICIT_AUX,<br>
> -                                      src_aux_usage, &src_surf);<br>
> -         if (src_aux_usage == ISL_AUX_USAGE_MCS) {<br>
> -            src_surf.clear_color_addr = anv_to_blorp_address(<br>
> -               anv_image_get_clear_color_addr(cmd_buffer->device,<br>
> -                                              src_iview->image,<br>
> -                                              VK_IMAGE_ASPECT_COLOR_<br>
> BIT));<br>
> -         }<br>
> -         get_blorp_surf_for_anv_image(cmd_buffer->device, dst_iview-<br>
> >image,<br>
> -                                      VK_IMAGE_ASPECT_COLOR_BIT,<br>
> -                                      ANV_IMAGE_LAYOUT_EXPLICIT_AUX,<br>
> -                                      dst_aux_usage, &dst_surf);<br>
> -<br>
> -         uint32_t base_src_layer = src_iview-<br>
> >planes[0].isl.base_array_layer;<br>
> -         uint32_t base_dst_layer = dst_iview-<br>
> >planes[0].isl.base_array_layer;<br>
> -<br>
> -         assert(src_iview->planes[0].isl.array_len >= fb->layers);<br>
> -         assert(dst_iview->planes[0].isl.array_len >= fb->layers);<br>
> -<br>
> -         anv_cmd_buffer_mark_image_written(cmd_buffer, dst_iview-<br>
> >image,<br>
> -                                           VK_IMAGE_ASPECT_COLOR_BIT<br>
> ,<br>
> -                                           dst_surf.aux_usage,<br>
> -                                           dst_iview-<br>
> >planes[0].isl.base_level,<br>
> -                                           base_dst_layer, fb-<br>
> >layers);<br>
> -<br>
> -         assert(!src_iview->image->format->can_ycbcr);<br>
> -         assert(!dst_iview->image->format->can_ycbcr);<br>
> -<br>
> -         for (uint32_t i = 0; i < fb->layers; i++) {<br>
> -            resolve_surface(&batch,<br>
> -                            &src_surf,<br>
> -                            src_iview->planes[0].isl.base_level,<br>
> -                            base_src_layer + i,<br>
> -                            &dst_surf,<br>
> -                            dst_iview->planes[0].isl.base_level,<br>
> -                            base_dst_layer + i,<br>
> -                            render_area.offset.x,<br>
> render_area.offset.y,<br>
> -                            render_area.offset.x,<br>
> render_area.offset.y,<br>
> -                            render_area.extent.width,<br>
> render_area.extent.height,<br>
> -                            filter);<br>
> -         }<br>
> +         anv_image_msaa_resolve(cmd_buffer,<br>
> +                                src_iview->image, src_aux_usage,<br>
> +                                src_iview->planes[0].isl.base_level,<br>
> +                                src_iview-<br>
> >planes[0].isl.base_array_layer,<br>
> +                                dst_iview->image, dst_aux_usage,<br>
> +                                dst_iview->planes[0].isl.base_level,<br>
> +                                dst_iview-<br>
> >planes[0].isl.base_array_layer,<br>
> +                                VK_IMAGE_ASPECT_COLOR_BIT,<br>
> +                                render_area.offset.x,<br>
> render_area.offset.y,<br>
> +                                render_area.offset.x,<br>
> render_area.offset.y,<br>
> +                                render_area.extent.width,<br>
> +                                render_area.extent.height,<br>
> +                                fb->layers, BLORP_FILTER_NONE);<br>
>        }<br>
> -<br>
> -      blorp_batch_finish(&batch);<br>
>     }<br>
>  }<br>
>  <br>
> diff --git a/src/intel/vulkan/anv_private.h<br>
> b/src/intel/vulkan/anv_private.h<br>
> index 0b67e7598b4..a064a058822 100644<br>
> --- a/src/intel/vulkan/anv_private.h<br>
> +++ b/src/intel/vulkan/anv_private.h<br>
> @@ -2923,6 +2923,20 @@ anv_image_clear_depth_stencil(struct<br>
> anv_cmd_buffer *cmd_buffer,<br>
>                                VkRect2D area,<br>
>                                float depth_value, uint8_t<br>
> stencil_value);<br>
>  void<br>
> +anv_image_msaa_resolve(struct anv_cmd_buffer *cmd_buffer,<br>
> +                       const struct anv_image *src_image,<br>
> +                       enum isl_aux_usage src_aux_usage,<br>
> +                       uint32_t src_level, uint32_t src_base_layer,<br>
> +                       const struct anv_image *dst_image,<br>
> +                       enum isl_aux_usage dst_aux_usage,<br>
> +                       uint32_t dst_level, uint32_t dst_base_layer,<br>
> +                       VkImageAspectFlagBits aspect,<br>
> +                       uint32_t src_x, uint32_t src_y,<br>
> +                       uint32_t dst_x, uint32_t dst_y,<br>
> +                       uint32_t width, uint32_t height,<br>
> +                       uint32_t layer_count,<br>
> +                       enum blorp_filter filter);<br>
> +void<br>
>  anv_image_hiz_op(struct anv_cmd_buffer *cmd_buffer,<br>
>                   const struct anv_image *image,<br>
>                   VkImageAspectFlagBits aspect, uint32_t level,<br>
<br>
</blockquote></div></div>