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

Author: Adam Jackson <[email protected]>
Date:   Thu Sep  1 17:48:34 2022 -0400

wsi/x11: Fix the is-visual-supported check

This was sort of well intentioned, but wrong. bits_per_rgb_value is the
number of significant bits in the color (channel) specification, not the
number of bits used to name that color within the pixel. If you have a
depth 24 visual but the colormap is 11 bits deep then each of those
channels selects one of 256 11-bit color values in the output ramp.

The open source drivers mostly don't expose anything like that, but
nvidia does, and we refuse to work. That's silly. Practically speaking
we can probably render to any TrueColor or DirectColor visual that your
X server exposes, since it is probably not going to have visuals for
non-color-renderable formats. Just check the visual class instead.

Likewise when matching formats to visuals, count the bits in the rgb
masks in the visual.

Closes: https://gitlab.freedesktop.org/mesa/mesa/-/issues/6995
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/18381>

---

 src/vulkan/wsi/wsi_common_x11.c | 7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/src/vulkan/wsi/wsi_common_x11.c b/src/vulkan/wsi/wsi_common_x11.c
index b24a98322f9..2c9534c7f64 100644
--- a/src/vulkan/wsi/wsi_common_x11.c
+++ b/src/vulkan/wsi/wsi_common_x11.c
@@ -539,7 +539,8 @@ visual_supported(xcb_visualtype_t *visual)
    if (!visual)
       return false;
 
-   return visual->bits_per_rgb_value == 8 || visual->bits_per_rgb_value == 10;
+   return visual->_class == XCB_VISUAL_CLASS_TRUE_COLOR ||
+          visual->_class == XCB_VISUAL_CLASS_DIRECT_COLOR;
 }
 
 VKAPI_ATTR VkBool32 VKAPI_CALL
@@ -759,7 +760,9 @@ get_sorted_vk_formats(VkIcdSurfaceBase *surface, struct 
wsi_device *wsi_device,
 
    *count = 0;
    for (unsigned i = 0; i < ARRAY_SIZE(formats); i++) {
-      if (formats[i].bits_per_rgb == visual->bits_per_rgb_value)
+      if (formats[i].bits_per_rgb == util_bitcount(visual->red_mask) &&
+          formats[i].bits_per_rgb == util_bitcount(visual->green_mask) &&
+          formats[i].bits_per_rgb == util_bitcount(visual->blue_mask))
          sorted_formats[(*count)++] = formats[i].format;
    }
 

Reply via email to