<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Tue, Nov 7, 2017 at 6:48 AM, Chad Versace <span dir="ltr"><<a href="mailto:chadversary@chromium.org" target="_blank">chadversary@chromium.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Incremental implementation of VK_EXT_image_drm_format_<wbr>modifier.<br>
---<br>
 src/intel/vulkan/anv_formats.c | 144 ++++++++++++++++++++++++++++++<wbr>+++++++----<br>
 1 file changed, 132 insertions(+), 12 deletions(-)<br>
<br>
diff --git a/src/intel/vulkan/anv_<wbr>formats.c b/src/intel/vulkan/anv_<wbr>formats.c<br>
index 0dd990bb9a8..dc46fdb5425 100644<br>
--- a/src/intel/vulkan/anv_<wbr>formats.c<br>
+++ b/src/intel/vulkan/anv_<wbr>formats.c<br>
@@ -21,6 +21,8 @@<br>
  * IN THE SOFTWARE.<br>
  */<br>
<br>
+#include <drm_fourcc.h><br>
+<br>
 #include "anv_private.h"<br>
 #include "vk_enum_to_str.h"<br>
 #include "vk_format_info.h"<br>
@@ -425,6 +427,9 @@ anv_get_format_plane(const struct gen_device_info *devinfo, VkFormat vk_format,<br>
       return unsupported;<br>
<br>
    if (aspect & (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT)) {<br>
+      if (tiling == VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT)<br>
+         return unsupported;<br>
+<br>
       assert(vk_format_aspects(vk_<wbr>format) &<br>
              (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT));<br>
       return plane_format;<br>
@@ -435,6 +440,18 @@ anv_get_format_plane(const struct gen_device_info *devinfo, VkFormat vk_format,<br>
    const struct isl_format_layout *isl_layout =<br>
       isl_format_get_layout(plane_<wbr>format.isl_format);<br>
<br>
+   /* For VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT, the image's driver-internal<br>
+    * format must be the user-facing VkFormat. Modifying the VkFormat in any<br>
+    * way, including swizzling, is illegal.<br>
+    */<br></blockquote><div><br></div><div>What are you doing with this comment?  There's no code to go with it.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+<br>
+   /* For now, for no reason other than FUD, we decline to support texture<br>
+    * compression with modifiers. <br></blockquote><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+    */<br>
+   if (tiling == VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT &&<br>
+       isl_layout->txc != ISL_TXC_NONE)<br>
+      return unsupported;<br>
+<br>
    if (tiling == VK_IMAGE_TILING_OPTIMAL &&<br>
        !util_is_power_of_two(isl_<wbr>layout->bpb)) {<br>
       /* Tiled formats *must* be power-of-two because we need up upload<br>
@@ -456,7 +473,8 @@ anv_get_format_plane(const struct gen_device_info *devinfo, VkFormat vk_format,<br>
    /* The B4G4R4A4 format isn't available prior to Broadwell so we have to fall<br>
     * back to a format with a more complex swizzle.<br>
     */<br>
-   if (vk_format == VK_FORMAT_B4G4R4A4_UNORM_<wbr>PACK16 && devinfo->gen < 8) {<br>
+   if (tiling != VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT &&<br>
+       vk_format == VK_FORMAT_B4G4R4A4_UNORM_<wbr>PACK16 && devinfo->gen < 8) {<br></blockquote><div><br></div><div>This is not the only way you can get swizzling.  This one is just a special case because it's gen-dependent.  Instead, we should just have a thing at the end which checks whether or not it's a swizzled format and bails.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
       plane_format.isl_format = ISL_FORMAT_B4G4R4A4_UNORM;<br>
       plane_format.swizzle = ISL_SWIZZLE(GREEN, RED, ALPHA, BLUE);<br>
    }<br>
@@ -466,21 +484,29 @@ anv_get_format_plane(const struct gen_device_info *devinfo, VkFormat vk_format,<br>
<br>
 // Format capabilities<br>
<br>
+/**<br>
+ * Parameter drm_format_mod must be DRM_FORMAT_MOD_INVALID unless vk_tiling is<br>
+ * VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT.<br>
+ */<br>
 static VkFormatFeatureFlags<br>
 get_image_format_features(<wbr>const struct gen_device_info *devinfo,<br>
                           VkFormat vk_format,<br>
                           const struct anv_format *anv_format,<br>
-                          VkImageTiling vk_tiling)<br>
+                          VkImageTiling vk_tiling,<br>
+                          uint64_t drm_format_mod)<br>
 {<br>
    VkFormatFeatureFlags flags = 0;<br>
<br>
+   if (vk_tiling != VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT)<br>
+      assert(drm_format_mod == DRM_FORMAT_MOD_INVALID);<br>
+<br>
    if (anv_format == NULL)<br>
       return 0;<br>
<br>
    const VkImageAspectFlags aspects = vk_format_aspects(vk_format);<br>
<br>
    if (aspects & (VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT)) {<br>
-      if (vk_tiling == VK_IMAGE_TILING_LINEAR)<br>
+      if (vk_tiling != VK_IMAGE_TILING_OPTIMAL)<br>
          return 0;<br>
<br>
       flags |= VK_FORMAT_FEATURE_DEPTH_<wbr>STENCIL_ATTACHMENT_BIT;<br>
@@ -503,6 +529,17 @@ get_image_format_features(<wbr>const struct gen_device_info *devinfo,<br>
    if (plane_format.isl_format == ISL_FORMAT_UNSUPPORTED)<br>
       return 0;<br>
<br>
+   const struct isl_format_layout *isl_layout =<br>
+      isl_format_get_layout(plane_<wbr>format.isl_format);<br>
+<br>
+   if (vk_tiling == VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT)<br>
+      assert(isl_layout->txc == ISL_TXC_NONE);<br>
+<br>
+   /* For VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT, the base format and<br>
+    * non-base format must be the same, because the image's driver-internal<br>
+    * format must be the user-facing VkFormat. Modifying the VkFormat in any<br>
+    * way, including swizzling, is illegal.<br>
+    */<br></blockquote><div><br></div><div>Again, this comment seems to be dangling.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
    struct anv_format_plane base_plane_format = plane_format;<br>
    if (vk_tiling == VK_IMAGE_TILING_OPTIMAL) {<br>
       base_plane_format = anv_get_format_plane(devinfo, vk_format,<br>
@@ -513,8 +550,8 @@ get_image_format_features(<wbr>const struct gen_device_info *devinfo,<br>
    enum isl_format base_isl_format = base_plane_format.isl_format;<br>
<br>
    /* ASTC textures must be in Y-tiled memory */<br>
-   if (vk_tiling == VK_IMAGE_TILING_LINEAR &&<br>
-       isl_format_get_layout(plane_<wbr>format.isl_format)->txc == ISL_TXC_ASTC)<br>
+   if (vk_tiling != VK_IMAGE_TILING_OPTIMAL &&<br>
+       isl_layout->txc == ISL_TXC_ASTC)<br>
       return 0;<br>
<br>
    if (isl_format_supports_sampling(<wbr>devinfo, plane_format.isl_format)) {<br>
@@ -569,6 +606,11 @@ get_image_format_features(<wbr>const struct gen_device_info *devinfo,<br>
    }<br>
<br>
    if (anv_format->can_ycbcr) {<br>
+      if (vk_tiling == VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT) {<br>
+         /* FINISHME(chadv): Support YUV with DRM format modifiers. */<br>
+         return 0;<br>
+      }<br>
+<br>
       /* The sampler doesn't have support for mid point when it handles YUV on<br>
        * its own.<br>
        */<br>
@@ -608,6 +650,22 @@ get_image_format_features(<wbr>const struct gen_device_info *devinfo,<br>
       flags &= ~disallowed_ycbcr_image_<wbr>features;<br>
    }<br>
<br>
+   if (vk_tiling == VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT) {<br>
+      switch (drm_format_mod) {<br>
+      default:<br>
+         unreachable("bad DRM format modifier");<br>
+      case DRM_FORMAT_MOD_LINEAR:<br>
+         break;<br>
+      case I915_FORMAT_MOD_X_TILED:<br>
+         /* TODO(chadv): Should we support X-tiled storage images? */<br></blockquote><div><br></div><div>Storaage images should work fine X-tiled.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+         flags &= ~VK_FORMAT_FEATURE_STORAGE_<wbr>IMAGE_BIT;<br>
+         flags &= ~VK_FORMAT_FEATURE_STORAGE_<wbr>IMAGE_ATOMIC_BIT;<br>
+         break;<br>
+      case I915_FORMAT_MOD_Y_TILED:<br>
+         break;<br>
+      }<br>
+   }<br>
+<br>
    return flags;<br>
 }<br>
<br>
@@ -651,6 +709,60 @@ get_buffer_format_features(<wbr>const struct gen_device_info *devinfo,<br>
    return flags;<br>
 }<br>
<br>
+/**<br>
+ * Fill the VkDrmFormatModifierPropertiesE<wbr>XT struct if the VkFormat supports<br>
+ * the DRM format modifier, and return true.  On failure, the output struct<br>
+ * has undefined content.<br>
+ */<br>
+static bool<br>
+get_drm_format_modifier_<wbr>properties(const struct anv_physical_device *physical_device,<br>
+                                   VkFormat vk_format,<br>
+                                   const struct anv_format *anv_format,<br>
+                                   uint64_t drm_format_mod,<br>
+                                   VkDrmFormatModifierPropertiesE<wbr>XT *props)<br>
+{<br>
+   const struct gen_device_info *devinfo = &physical_device->info;<br>
+<br>
+   *props = (<wbr>VkDrmFormatModifierPropertiesE<wbr>XT) {<br>
+      .drmFormatModifier = drm_format_mod,<br>
+      .drmFormatModifierPlaneCount = anv_format->n_planes,<br>
+      .<wbr>drmFormatModifierTilingFeature<wbr>s =<br>
+         get_image_format_features(<wbr>devinfo, vk_format, anv_format,<br>
+                                   VK_IMAGE_TILING_DRM_FORMAT_<wbr>MODIFIER_EXT,<br>
+                                   drm_format_mod),<br>
+   };<br>
+<br>
+   if (props-><wbr>drmFormatModifierTilingFeature<wbr>s == 0)<br>
+      return false;<br>
+<br>
+   return true;<br>
+}<br>
+<br>
+static void<br>
+get_drm_format_modifier_<wbr>properties_list(const struct anv_physical_device *physical_device,<br>
+                                        VkFormat vk_format,<br>
+                                        VkDrmFormatModifierPropertiesL<wbr>istEXT *drm_list)<br></blockquote><div><br></div><div>This is exactly the kind of function I was hoping you'd make so we can expose it to WSI. :-)<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+{<br>
+   const struct anv_format *anv_format = anv_get_format(vk_format);<br>
+<br>
+   VK_OUTARRAY_MAKE(out, drm_list-><wbr>pDrmFormatModifierProperties,<br>
+                    &drm_list-><wbr>drmFormatModifierCount);<br>
+<br>
+   #define TRY_MOD(mod) ({ \<br>
+      VkDrmFormatModifierPropertiesE<wbr>XT tmp_props; \<br>
+      if (get_drm_format_modifier_<wbr>properties(physical_device, vk_format, \<br>
+                                             anv_format, (mod), &tmp_props)) { \<br>
+         vk_outarray_append(&out, drm_props) { *drm_props = tmp_props; }; \<br>
+      } \<br>
+   })<br>
+<br>
+   TRY_MOD(I915_FORMAT_MOD_Y_<wbr>TILED);<br>
+   TRY_MOD(I915_FORMAT_MOD_X_<wbr>TILED);<br>
+   TRY_MOD(DRM_FORMAT_MOD_LINEAR)<wbr>;<br>
+<br>
+   #undef TRY_MOD<br>
+}<br>
+<br>
 void anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies(<br>
     VkPhysicalDevice                            physicalDevice,<br>
     VkFormat                                    vk_format,<br>
@@ -663,10 +775,12 @@ void anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies(<br>
    *pFormatProperties = (VkFormatProperties) {<br>
       .linearTilingFeatures =<br>
          get_image_format_features(<wbr>devinfo, vk_format, anv_format,<br>
-                                   VK_IMAGE_TILING_LINEAR),<br>
+                                   VK_IMAGE_TILING_LINEAR,<br>
+                                   DRM_FORMAT_MOD_INVALID),<br>
       .optimalTilingFeatures =<br>
          get_image_format_features(<wbr>devinfo, vk_format, anv_format,<br>
-                                   VK_IMAGE_TILING_OPTIMAL),<br>
+                                   VK_IMAGE_TILING_OPTIMAL,<br>
+                                   DRM_FORMAT_MOD_INVALID),<br>
       .bufferFeatures =<br>
          get_buffer_format_features(<wbr>devinfo, vk_format, anv_format),<br>
    };<br>
@@ -674,14 +788,20 @@ void anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies(<br>
<br>
 void anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies2KHR(<br>
     VkPhysicalDevice                            physicalDevice,<br>
-    VkFormat                                    format,<br>
+    VkFormat                                    vk_format,<br>
     VkFormatProperties2KHR*                     pFormatProperties)<br>
 {<br>
-   anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies(physicalDevice, format,<br>
+   ANV_FROM_HANDLE(anv_physical_<wbr>device, physical_device, physicalDevice);<br>
+<br>
+   anv_<wbr>GetPhysicalDeviceFormatPropert<wbr>ies(physicalDevice, vk_format,<br>
                                          &pFormatProperties-><wbr>formatProperties);<br>
<br>
    vk_foreach_struct(ext, pFormatProperties->pNext) {<br>
       switch (ext->sType) {<br>
+      case VK_STRUCTURE_TYPE_DRM_FORMAT_<wbr>MODIFIER_PROPERTIES_LIST_EXT:<br>
+         get_drm_format_modifier_<wbr>properties_list(physical_<wbr>device, vk_format,<br>
+            (<wbr>VkDrmFormatModifierPropertiesL<wbr>istEXT *)ext);<br>
+         break;<br>
       default:<br>
          anv_debug_ignored_stype(ext-><wbr>sType);<br>
          break;<br>
@@ -696,7 +816,6 @@ anv_get_image_format_<wbr>properties(<br>
    VkImageFormatProperties *pImageFormatProperties,<br>
    VkSamplerYcbcrConversionImageF<wbr>ormatPropertiesKHR *pYcbcrImageFormatProperties)<br>
 {<br>
-   VkFormatFeatureFlags format_feature_flags;<br>
    VkExtent3D maxExtent;<br>
    uint32_t maxMipLevels;<br>
    uint32_t maxArraySize;<br>
@@ -707,8 +826,9 @@ anv_get_image_format_<wbr>properties(<br>
    if (format == NULL)<br>
       goto unsupported;<br>
<br>
-   format_feature_flags = get_image_format_features(<wbr>devinfo, info->format,<br>
-                                                    format, info->tiling);<br>
+   VkFormatFeatureFlags format_feature_flags =<br>
+      get_image_format_features(<wbr>devinfo, info->format, format, info->tiling,<br>
+                                DRM_FORMAT_MOD_INVALID);<br>
<br>
    switch (info->type) {<br>
    default:<br>
<span class="HOEnZb"><font color="#888888">--<br>
2.13.0<br>
<br>
______________________________<wbr>_________________<br>
mesa-dev mailing list<br>
<a href="mailto:mesa-dev@lists.freedesktop.org">mesa-dev@lists.freedesktop.org</a><br>
<a href="https://lists.freedesktop.org/mailman/listinfo/mesa-dev" rel="noreferrer" target="_blank">https://lists.freedesktop.org/<wbr>mailman/listinfo/mesa-dev</a><br>
</font></span></blockquote></div><br></div></div>