anv: Implement VK_KHR_maintenance3
authorJason Ekstrand <jason.ekstrand@intel.com>
Thu, 5 Oct 2017 23:03:29 +0000 (16:03 -0700)
committerJason Ekstrand <jason.ekstrand@intel.com>
Wed, 7 Mar 2018 20:13:47 +0000 (12:13 -0800)
Reviewed-by: Samuel Iglesias Gonsálvez <siglesias@igalia.com>
src/intel/vulkan/anv_descriptor_set.c
src/intel/vulkan/anv_device.c
src/intel/vulkan/anv_extensions.py
src/intel/vulkan/anv_private.h

index c12937669892f50cb964faed469ef4b32d3b72d7..2a3c496a9f80286e1cb6cc0c45f2ca0ae0f07fb0 100644 (file)
  * Descriptor set layouts.
  */
 
+void anv_GetDescriptorSetLayoutSupport(
+    VkDevice                                    device,
+    const VkDescriptorSetLayoutCreateInfo*      pCreateInfo,
+    VkDescriptorSetLayoutSupport*               pSupport)
+{
+   uint32_t surface_count[MESA_SHADER_STAGES] = { 0, };
+
+   for (uint32_t b = 0; b <= pCreateInfo->bindingCount; b++) {
+      const VkDescriptorSetLayoutBinding *binding = &pCreateInfo->pBindings[b];
+
+      switch (binding->descriptorType) {
+      case VK_DESCRIPTOR_TYPE_SAMPLER:
+         /* There is no real limit on samplers */
+         break;
+
+      case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
+         if (binding->pImmutableSamplers) {
+            for (uint32_t i = 0; i < binding->descriptorCount; i++) {
+               ANV_FROM_HANDLE(anv_sampler, sampler,
+                               binding->pImmutableSamplers[i]);
+               anv_foreach_stage(s, binding->stageFlags)
+                  surface_count[s] += sampler->n_planes;
+            }
+         }
+         break;
+
+      default:
+         anv_foreach_stage(s, binding->stageFlags)
+            surface_count[s] += binding->descriptorCount;
+         break;
+      }
+   }
+
+   bool supported = true;
+   for (unsigned s = 0; s < MESA_SHADER_STAGES; s++) {
+      /* Our maximum binding table size is 250 and we need to reserve 8 for
+       * render targets.  240 is a nice round number.
+       */
+      if (surface_count[s] >= 240)
+         supported = false;
+   }
+
+   pSupport->supported = supported;
+}
+
 VkResult anv_CreateDescriptorSetLayout(
     VkDevice                                    _device,
     const VkDescriptorSetLayoutCreateInfo*      pCreateInfo,
index 5d74b5fb55ce0cc84aa017c0ffc6a990f17dc44f..7b3ccc01ddc024a3eb069b57ad736edf87e2fe09 100644 (file)
@@ -990,6 +990,17 @@ void anv_GetPhysicalDeviceProperties2(
          break;
       }
 
+      case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_3_PROPERTIES: {
+         VkPhysicalDeviceMaintenance3Properties *props =
+            (VkPhysicalDeviceMaintenance3Properties *)ext;
+         /* This value doesn't matter for us today as our per-stage
+          * descriptors are the real limit.
+          */
+         props->maxPerSetDescriptors = 1024;
+         props->maxMemoryAllocationSize = MAX_MEMORY_ALLOCATION_SIZE;
+         break;
+      }
+
       case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTIVIEW_PROPERTIES: {
          VkPhysicalDeviceMultiviewProperties *properties =
             (VkPhysicalDeviceMultiviewProperties *)ext;
@@ -1800,24 +1811,7 @@ VkResult anv_AllocateMemory(
    /* The Vulkan 1.0.33 spec says "allocationSize must be greater than 0". */
    assert(pAllocateInfo->allocationSize > 0);
 
-   /* The kernel relocation API has a limitation of a 32-bit delta value
-    * applied to the address before it is written which, in spite of it being
-    * unsigned, is treated as signed .  Because of the way that this maps to
-    * the Vulkan API, we cannot handle an offset into a buffer that does not
-    * fit into a signed 32 bits.  The only mechanism we have for dealing with
-    * this at the moment is to limit all VkDeviceMemory objects to a maximum
-    * of 2GB each.  The Vulkan spec allows us to do this:
-    *
-    *    "Some platforms may have a limit on the maximum size of a single
-    *    allocation. For example, certain systems may fail to create
-    *    allocations with a size greater than or equal to 4GB. Such a limit is
-    *    implementation-dependent, and if such a failure occurs then the error
-    *    VK_ERROR_OUT_OF_DEVICE_MEMORY should be returned."
-    *
-    * We don't use vk_error here because it's not an error so much as an
-    * indication to the application that the allocation is too large.
-    */
-   if (pAllocateInfo->allocationSize > (1ull << 31))
+   if (pAllocateInfo->allocationSize > MAX_MEMORY_ALLOCATION_SIZE)
       return VK_ERROR_OUT_OF_DEVICE_MEMORY;
 
    /* FINISHME: Fail if allocation request exceeds heap size. */
index ca5100fc5e50a94a8b273a00e2cfbc985725e3a1..df168dc98487fc268bffb3ffb75a1100c9fb12c2 100644 (file)
@@ -88,6 +88,7 @@ EXTENSIONS = [
     Extension('VK_KHR_incremental_present',               1, 'ANV_HAS_SURFACE'),
     Extension('VK_KHR_maintenance1',                      1, True),
     Extension('VK_KHR_maintenance2',                      1, True),
+    Extension('VK_KHR_maintenance3',                      1, True),
     Extension('VK_KHR_push_descriptor',                   1, True),
     Extension('VK_KHR_relaxed_block_layout',              1, True),
     Extension('VK_KHR_sampler_mirror_clamp_to_edge',      1, True),
index 55bdf365014c7a90e5c77edc9fc3f946e7544347..5e384940181a2add4769e47c8e4a830ed158d7a5 100644 (file)
@@ -104,6 +104,25 @@ struct gen_l3_config;
 #define MAX_IMAGES 8
 #define MAX_PUSH_DESCRIPTORS 32 /* Minimum requirement */
 
+/* The kernel relocation API has a limitation of a 32-bit delta value
+ * applied to the address before it is written which, in spite of it being
+ * unsigned, is treated as signed .  Because of the way that this maps to
+ * the Vulkan API, we cannot handle an offset into a buffer that does not
+ * fit into a signed 32 bits.  The only mechanism we have for dealing with
+ * this at the moment is to limit all VkDeviceMemory objects to a maximum
+ * of 2GB each.  The Vulkan spec allows us to do this:
+ *
+ *    "Some platforms may have a limit on the maximum size of a single
+ *    allocation. For example, certain systems may fail to create
+ *    allocations with a size greater than or equal to 4GB. Such a limit is
+ *    implementation-dependent, and if such a failure occurs then the error
+ *    VK_ERROR_OUT_OF_DEVICE_MEMORY should be returned."
+ *
+ * We don't use vk_error here because it's not an error so much as an
+ * indication to the application that the allocation is too large.
+ */
+#define MAX_MEMORY_ALLOCATION_SIZE (1ull << 31)
+
 #define ANV_SVGS_VB_INDEX    MAX_VBS
 #define ANV_DRAWID_VB_INDEX (MAX_VBS + 1)