lavapipe: add descriptor sets bindings for planar images
authorDave Airlie <airlied@redhat.com>
Fri, 6 Oct 2023 06:22:51 +0000 (16:22 +1000)
committerMarge Bot <emma+marge@anholt.net>
Tue, 10 Oct 2023 04:37:07 +0000 (04:37 +0000)
This adds strided descriptor bindings that are used to handle
planar image/samplers.

Reviewed-by: Roland Scheidegger <sroland@vmware.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/25609>

src/gallium/frontends/lavapipe/lvp_descriptor_set.c
src/gallium/frontends/lavapipe/lvp_private.h

index 6685670..41d02af 100644 (file)
 #include "util/u_math.h"
 #include "util/u_inlines.h"
 
+static bool
+binding_has_immutable_samplers(const VkDescriptorSetLayoutBinding *binding)
+{
+   switch (binding->descriptorType) {
+   case VK_DESCRIPTOR_TYPE_SAMPLER:
+   case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
+      return binding->pImmutableSamplers != NULL;
+
+   default:
+      return false;
+   }
+}
+
 static void
 lvp_descriptor_set_layout_destroy(struct vk_device *_device, struct vk_descriptor_set_layout *_layout)
 {
@@ -64,10 +77,7 @@ VKAPI_ATTR VkResult VKAPI_CALL lvp_CreateDescriptorSetLayout(
        * We need to be careful here and only parse pImmutableSamplers if we
        * have one of the right descriptor types.
        */
-      VkDescriptorType desc_type = pCreateInfo->pBindings[j].descriptorType;
-      if ((desc_type == VK_DESCRIPTOR_TYPE_SAMPLER ||
-           desc_type == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER) &&
-          pCreateInfo->pBindings[j].pImmutableSamplers)
+      if (binding_has_immutable_samplers(&pCreateInfo->pBindings[j]))
          immutable_sampler_count += pCreateInfo->pBindings[j].descriptorCount;
    }
 
@@ -115,33 +125,30 @@ VKAPI_ATTR VkResult VKAPI_CALL lvp_CreateDescriptorSetLayout(
       set_layout->binding[b].uniform_block_offset = 0;
       set_layout->binding[b].uniform_block_size = 0;
 
-      set_layout->size += descriptor_count;
-
       if (binding->descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC ||
           binding->descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC) {
          set_layout->binding[b].dynamic_index = dynamic_offset_count;
          dynamic_offset_count += binding->descriptorCount;
       }
-      switch (binding->descriptorType) {
-      case VK_DESCRIPTOR_TYPE_SAMPLER:
-      case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
-         if (binding->pImmutableSamplers) {
-            set_layout->binding[b].immutable_samplers = samplers;
-            samplers += binding->descriptorCount;
-
-            for (uint32_t i = 0; i < binding->descriptorCount; i++) {
-               if (binding->pImmutableSamplers[i])
-                  set_layout->binding[b].immutable_samplers[i] =
-                     lvp_sampler_from_handle(binding->pImmutableSamplers[i]);
-               else
-                  set_layout->binding[b].immutable_samplers[i] = NULL;
-            }
+
+      uint8_t max_plane_count = 1;
+      if (binding_has_immutable_samplers(binding)) {
+         set_layout->binding[b].immutable_samplers = samplers;
+         samplers += binding->descriptorCount;
+
+         for (uint32_t i = 0; i < binding->descriptorCount; i++) {
+            VK_FROM_HANDLE(lvp_sampler, sampler, binding->pImmutableSamplers[i]);
+            set_layout->binding[b].immutable_samplers[i] = sampler;
+            const uint8_t sampler_plane_count = sampler->vk.ycbcr_conversion ?
+               vk_format_get_plane_count(sampler->vk.ycbcr_conversion->state.format) : 1;
+            if (max_plane_count < sampler_plane_count)
+               max_plane_count = sampler_plane_count;
          }
-         break;
-      default:
-         break;
       }
 
+      set_layout->binding[b].stride = max_plane_count;
+      set_layout->size += descriptor_count * max_plane_count;
+
       switch (binding->descriptorType) {
       case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER:
       case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
@@ -350,8 +357,12 @@ lvp_descriptor_set_create(struct lvp_device *device,
       desc += bind_layout->descriptor_index;
 
       for (uint32_t sampler_index = 0; sampler_index < bind_layout->array_size; sampler_index++) {
-         if (bind_layout->immutable_samplers[sampler_index])
-            desc[sampler_index] = bind_layout->immutable_samplers[sampler_index]->desc;
+         if (bind_layout->immutable_samplers[sampler_index]) {
+            for (uint32_t s = 0; s < bind_layout->stride; s++)  {
+               int idx = sampler_index * bind_layout->stride + s;
+               desc[idx] = bind_layout->immutable_samplers[sampler_index]->desc;
+            }
+         }
       }
    }
 
@@ -445,16 +456,19 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
       }
 
       struct lp_descriptor *desc = set->map;
-      desc += bind_layout->descriptor_index + write->dstArrayElement;
+      desc += bind_layout->descriptor_index + (write->dstArrayElement * bind_layout->stride);
 
       switch (write->descriptorType) {
       case VK_DESCRIPTOR_TYPE_SAMPLER:
          if (!bind_layout->immutable_samplers) {
             for (uint32_t j = 0; j < write->descriptorCount; j++) {
                LVP_FROM_HANDLE(lvp_sampler, sampler, write->pImageInfo[j].sampler);
+               uint32_t didx = j * bind_layout->stride;
 
-               desc[j].sampler = sampler->desc.sampler;
-               desc[j].sampler_index = sampler->desc.sampler_index;
+               for (unsigned k = 0; k < bind_layout->stride; k++) {
+                  desc[didx + k].sampler = sampler->desc.sampler;
+                  desc[didx + k].sampler_index = sampler->desc.sampler_index;
+               }
             }
          }
          break;
@@ -463,20 +477,29 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_image_view, iview,
                             write->pImageInfo[j].imageView);
+            uint32_t didx = j * bind_layout->stride;
             if (iview) {
-               lp_jit_texture_from_pipe(&desc[j].texture, iview->planes[0].sv);
-               desc[j].functions = iview->planes[0].texture_handle->functions;
+               unsigned plane_count = iview->plane_count;
+
+               for (unsigned p = 0; p < plane_count; p++) {
+                  lp_jit_texture_from_pipe(&desc[didx + p].texture, iview->planes[p].sv);
+                  desc[didx + p].functions = iview->planes[p].texture_handle->functions;
+               }
 
                if (!bind_layout->immutable_samplers) {
                   LVP_FROM_HANDLE(lvp_sampler, sampler,
                                   write->pImageInfo[j].sampler);
 
-                  desc[j].sampler = sampler->desc.sampler;
-                  desc[j].sampler_index = sampler->desc.sampler_index;
+                  for (unsigned p = 0; p < plane_count; p++) {
+                     desc[didx + p].sampler = sampler->desc.sampler;
+                     desc[didx + p].sampler_index = sampler->desc.sampler_index;
+                  }
                }
             } else {
-               desc[j].functions = device->null_texture_handle->functions;
-               desc[j].sampler_index = 0;
+               for (unsigned k = 0; k < bind_layout->stride; k++) {
+                  desc[didx + k].functions = device->null_texture_handle->functions;
+                  desc[didx + k].sampler_index = 0;
+               }
             }
          }
          break;
@@ -485,13 +508,19 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_image_view, iview,
                             write->pImageInfo[j].imageView);
-
+            uint32_t didx = j * bind_layout->stride;
             if (iview) {
-               lp_jit_texture_from_pipe(&desc[j].texture, iview->planes[0].sv);
-               desc[j].functions = iview->planes[0].texture_handle->functions;
+               unsigned plane_count = iview->plane_count;
+
+               for (unsigned p = 0; p < plane_count; p++) {
+                  lp_jit_texture_from_pipe(&desc[didx + p].texture, iview->planes[p].sv);
+                  desc[didx + p].functions = iview->planes[p].texture_handle->functions;
+               }
             } else {
-               desc[j].functions = device->null_texture_handle->functions;
-               desc[j].sampler_index = 0;
+               for (unsigned k = 0; k < bind_layout->stride; k++) {
+                  desc[didx + k].functions = device->null_texture_handle->functions;
+                  desc[didx + k].sampler_index = 0;
+               }
             }
          }
          break;
@@ -500,12 +529,17 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_image_view, iview,
                             write->pImageInfo[j].imageView);
-
+            uint32_t didx = j * bind_layout->stride;
             if (iview) {
-               lp_jit_image_from_pipe(&desc[j].image, &iview->planes[0].iv);
-               desc[j].functions = iview->planes[0].image_handle->functions;
+               unsigned plane_count = iview->plane_count;
+
+               for (unsigned p = 0; p < plane_count; p++) {
+                  lp_jit_image_from_pipe(&desc[didx + p].image, &iview->planes[p].iv);
+                  desc[didx + p].functions = iview->planes[p].image_handle->functions;
+               }
             } else {
-               desc[j].functions = device->null_image_handle->functions;
+               for (unsigned k = 0; k < bind_layout->stride; k++)
+                  desc[didx + k].functions = device->null_image_handle->functions;
             }
          }
          break;
@@ -514,7 +548,7 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_buffer_view, bview,
                             write->pTexelBufferView[j]);
-
+            assert(bind_layout->stride == 1);
             if (bview) {
                lp_jit_texture_from_pipe(&desc[j].texture, bview->sv);
                desc[j].functions = bview->texture_handle->functions;
@@ -529,7 +563,7 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_buffer_view, bview,
                             write->pTexelBufferView[j]);
-
+            assert(bind_layout->stride == 1);
             if (bview) {
                lp_jit_image_from_pipe(&desc[j].image, &bview->iv);
                desc[j].functions = bview->image_handle->functions;
@@ -543,7 +577,7 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
       case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC:
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_buffer, buffer, write->pBufferInfo[j].buffer);
-
+            assert(bind_layout->stride == 1);
             if (buffer) {
                struct pipe_constant_buffer ubo = {
                   .buffer = buffer->bo,
@@ -565,7 +599,7 @@ VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSets(
       case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC:
          for (uint32_t j = 0; j < write->descriptorCount; j++) {
             LVP_FROM_HANDLE(lvp_buffer, buffer, write->pBufferInfo[j].buffer);
-
+            assert(bind_layout->stride == 1);
             if (buffer) {
                struct pipe_shader_buffer ubo = {
                   .buffer = buffer->bo,
@@ -808,13 +842,17 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
 
       for (j = 0; j < entry->descriptorCount; ++j) {
          unsigned idx = j + entry->dstArrayElement;
+
+         idx *= bind_layout->stride;
          switch (entry->descriptorType) {
          case VK_DESCRIPTOR_TYPE_SAMPLER: {
             LVP_FROM_HANDLE(lvp_sampler, sampler,
                             *(VkSampler *)pSrc);
 
-            desc[idx].sampler = sampler->desc.sampler;
-            desc[idx].sampler_index = sampler->desc.sampler_index;
+            for (unsigned k = 0; k < bind_layout->stride; k++) {
+               desc[idx + k].sampler = sampler->desc.sampler;
+               desc[idx + k].sampler_index = sampler->desc.sampler_index;
+            }
             break;
          }
          case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: {
@@ -822,18 +860,24 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
             LVP_FROM_HANDLE(lvp_image_view, iview, info->imageView);
 
             if (iview) {
-               lp_jit_texture_from_pipe(&desc[idx].texture, iview->planes[0].sv);
-               desc[idx].functions = iview->planes[0].texture_handle->functions;
+               for (unsigned p = 0; p < iview->plane_count; p++) {
+                  lp_jit_texture_from_pipe(&desc[idx + p].texture, iview->planes[p].sv);
+                  desc[idx + p].functions = iview->planes[p].texture_handle->functions;
+               }
 
                if (!bind_layout->immutable_samplers) {
                   LVP_FROM_HANDLE(lvp_sampler, sampler, info->sampler);
 
-                  desc[idx].sampler = sampler->desc.sampler;
-                  desc[idx].sampler_index = sampler->desc.sampler_index;
+                  for (unsigned p = 0; p < iview->plane_count; p++) {
+                     desc[idx + p].sampler = sampler->desc.sampler;
+                     desc[idx + p].sampler_index = sampler->desc.sampler_index;
+                  }
                }
             } else {
-               desc[j].functions = device->null_texture_handle->functions;
-               desc[j].sampler_index = 0;
+               for (unsigned k = 0; k < bind_layout->stride; k++) {
+                  desc[idx + k].functions = device->null_texture_handle->functions;
+                  desc[idx + k].sampler_index = 0;
+               }
             }
             break;
          }
@@ -842,11 +886,15 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
             LVP_FROM_HANDLE(lvp_image_view, iview, info->imageView);
 
             if (iview) {
-               lp_jit_texture_from_pipe(&desc[idx].texture, iview->planes[0].sv);
-               desc[idx].functions = iview->planes[0].texture_handle->functions;
+               for (unsigned p = 0; p < iview->plane_count; p++) {
+                  lp_jit_texture_from_pipe(&desc[idx + p].texture, iview->planes[p].sv);
+                  desc[idx + p].functions = iview->planes[p].texture_handle->functions;
+               }
             } else {
-               desc[j].functions = device->null_texture_handle->functions;
-               desc[j].sampler_index = 0;
+               for (unsigned k = 0; k < bind_layout->stride; k++) {
+                  desc[idx + k].functions = device->null_texture_handle->functions;
+                  desc[idx + k].sampler_index = 0;
+               }
             }
             break;
          }
@@ -856,17 +904,20 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
                             ((VkDescriptorImageInfo *)pSrc)->imageView);
 
             if (iview) {
-               lp_jit_image_from_pipe(&desc[idx].image, &iview->planes[0].iv);
-               desc[idx].functions = iview->planes[0].image_handle->functions;
+               for (unsigned p = 0; p < iview->plane_count; p++) {
+                  lp_jit_image_from_pipe(&desc[idx + p].image, &iview->planes[p].iv);
+                  desc[idx + p].functions = iview->planes[p].image_handle->functions;
+               }
             } else {
-               desc[idx].functions = device->null_image_handle->functions;
+               for (unsigned k = 0; k < bind_layout->stride; k++)
+                  desc[idx + k].functions = device->null_image_handle->functions;
             }
             break;
          }
          case VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER: {
             LVP_FROM_HANDLE(lvp_buffer_view, bview,
                             *(VkBufferView *)pSrc);
-
+            assert(bind_layout->stride == 1);
             if (bview) {
                lp_jit_texture_from_pipe(&desc[idx].texture, bview->sv);
                desc[idx].functions = bview->texture_handle->functions;
@@ -879,7 +930,7 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
          case VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER: {
             LVP_FROM_HANDLE(lvp_buffer_view, bview,
                             *(VkBufferView *)pSrc);
-
+            assert(bind_layout->stride == 1);
             if (bview) {
                lp_jit_image_from_pipe(&desc[idx].image, &bview->iv);
                desc[idx].functions = bview->image_handle->functions;
@@ -893,7 +944,7 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
          case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC: {
             VkDescriptorBufferInfo *info = (VkDescriptorBufferInfo *)pSrc;
             LVP_FROM_HANDLE(lvp_buffer, buffer, info->buffer);
-
+            assert(bind_layout->stride == 1);
             if (buffer) {
                struct pipe_constant_buffer ubo = {
                   .buffer = buffer->bo,
@@ -915,6 +966,7 @@ lvp_descriptor_set_update_with_template(VkDevice _device, VkDescriptorSet descri
          case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC: {
             VkDescriptorBufferInfo *info = (VkDescriptorBufferInfo *)pSrc;
             LVP_FROM_HANDLE(lvp_buffer, buffer, info->buffer);
+            assert(bind_layout->stride == 1);
 
             if (buffer) {
                struct pipe_shader_buffer ubo = {
index 75d7a52..5c6d73a 100644 (file)
@@ -298,6 +298,7 @@ struct lvp_descriptor_set_binding_layout {
    uint32_t descriptor_index;
    /* Number of array elements in this binding */
    VkDescriptorType type;
+   uint32_t stride; /* used for planar samplers */
    uint32_t array_size;
    bool valid;