From a1d14a6176bf7e3e37a9d092e3392a22bcf582cb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonas=20=C3=85dahl?= Date: Wed, 16 Nov 2022 16:32:24 +0100 Subject: [PATCH] cursor-renderer/native: Don't put opaque buffers in cursor plane Cursor planes tend to be ARGB8888 and support no other format (ideally we should not hard code this, but un-hard-coding that is for another day), and if we put e.g. a XRGB8888 buffer in there, it'll either result in the gbm_bo allocation failing (it doesn't allow USE_CURSOR with any other format) or mode setting failing if using dumb buffers directly. In the former case, we'll fall back to OpenGL indefinitely, and in the latter, we'll have failed mode sets as long as we try to set the invalid cursor buffer as the cursor plane. Change things to process all buffers that are not ARGB8888 using the scale/rotate machinery we already have, turning XRGB8888 into ARGB8888. Related: https://gitlab.gnome.org/GNOME/mutter/-/issues/2477 Part-of: --- .../native/meta-cursor-renderer-native.c | 26 ++++++++++++++++--- 1 file changed, 23 insertions(+), 3 deletions(-) diff --git a/src/backends/native/meta-cursor-renderer-native.c b/src/backends/native/meta-cursor-renderer-native.c index f4b42c56c..fcd81f89a 100644 --- a/src/backends/native/meta-cursor-renderer-native.c +++ b/src/backends/native/meta-cursor-renderer-native.c @@ -1464,6 +1464,7 @@ is_cursor_scale_and_transform_valid (MetaCursorRenderer *renderer, static cairo_surface_t * scale_and_transform_cursor_sprite_cpu (uint8_t *pixels, + cairo_format_t pixel_format, int width, int height, int rowstride, @@ -1521,7 +1522,7 @@ scale_and_transform_cursor_sprite_cpu (uint8_t *pixels, cairo_scale (cr, scale, scale); source_surface = cairo_image_surface_create_for_data (pixels, - CAIRO_FORMAT_ARGB32, + pixel_format, width, height, rowstride); @@ -1534,6 +1535,21 @@ scale_and_transform_cursor_sprite_cpu (uint8_t *pixels, return target_surface; } +static cairo_format_t +gbm_format_to_cairo_format (uint32_t gbm_format) +{ + switch (gbm_format) + { + case GBM_FORMAT_XRGB8888: + return CAIRO_FORMAT_RGB24; + default: + g_warn_if_reached (); + G_GNUC_FALLTHROUGH; + case GBM_FORMAT_ARGB8888: + return CAIRO_FORMAT_ARGB32; + } +} + static void load_scaled_and_transformed_cursor_sprite (MetaCursorRendererNative *native, MetaGpuKms *gpu_kms, @@ -1547,11 +1563,15 @@ load_scaled_and_transformed_cursor_sprite (MetaCursorRendererNative *native, uint32_t gbm_format) { if (!G_APPROX_VALUE (relative_scale, 1.f, FLT_EPSILON) || - relative_transform != META_MONITOR_TRANSFORM_NORMAL) + relative_transform != META_MONITOR_TRANSFORM_NORMAL || + gbm_format != GBM_FORMAT_ARGB8888) { cairo_surface_t *surface; + cairo_format_t cairo_format; + cairo_format = gbm_format_to_cairo_format (gbm_format), surface = scale_and_transform_cursor_sprite_cpu (data, + cairo_format, width, height, rowstride, @@ -1565,7 +1585,7 @@ load_scaled_and_transformed_cursor_sprite (MetaCursorRendererNative *native, cairo_image_surface_get_width (surface), cairo_image_surface_get_width (surface), cairo_image_surface_get_stride (surface), - gbm_format); + GBM_FORMAT_ARGB8888); cairo_surface_destroy (surface); }