[mutter] backends/screen-cast-stream-src: Set correct stride when using dmabufs



commit ab3931fec8d2a585910733b696f26312a6bb0894
Author: Pascal Nowack <Pascal Nowack gmx de>
Date:   Wed Jul 13 16:40:11 2022 +0200

    backends/screen-cast-stream-src: Set correct stride when using dmabufs
    
    Currently, mutter hardcodes the stride of all recorded images in a
    screencast to width * 4.
    While this stride is valid for general memory buffers, it is not
    necessarily valid for dmabuf buffers, as the driver may need a specific
    alignment of the stride.
    This can currently result into import failures, e.g. when using the AMD
    driver.
    
    To fix this issue, retrieve the actual dmabuf stride, when using dmabuf
    screencasts, and set it as the stride value in the PipeWire buffer.
    
    Fixes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1913
    Fixes: https://gitlab.gnome.org/GNOME/gnome-remote-desktop/-/issues/101
    Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2513>

 src/backends/meta-screen-cast-stream-src.c | 26 ++++++++++++++++++++++++--
 1 file changed, 24 insertions(+), 2 deletions(-)
---
diff --git a/src/backends/meta-screen-cast-stream-src.c b/src/backends/meta-screen-cast-stream-src.c
index 0d8bc17514..806fa806c1 100644
--- a/src/backends/meta-screen-cast-stream-src.c
+++ b/src/backends/meta-screen-cast-stream-src.c
@@ -569,6 +569,26 @@ maybe_schedule_follow_up_frame (MetaScreenCastStreamSrc *src,
                                                    src);
 }
 
+static int32_t
+meta_screen_cast_stream_src_calculate_stride (MetaScreenCastStreamSrc *src,
+                                              struct spa_data         *spa_data)
+{
+  MetaScreenCastStreamSrcPrivate *priv =
+    meta_screen_cast_stream_src_get_instance_private (src);
+  CoglDmaBufHandle *dmabuf_handle = NULL;
+
+  if (spa_data->type == SPA_DATA_DmaBuf)
+    {
+      dmabuf_handle = g_hash_table_lookup (priv->dmabuf_handles,
+                                           GINT_TO_POINTER (spa_data->fd));
+    }
+
+  if (dmabuf_handle)
+    return cogl_dma_buf_handle_get_stride (dmabuf_handle);
+  else
+    return priv->video_stride;
+}
+
 void
 meta_screen_cast_stream_src_maybe_record_frame (MetaScreenCastStreamSrc  *src,
                                                 MetaScreenCastRecordFlag  flags)
@@ -631,10 +651,12 @@ meta_screen_cast_stream_src_maybe_record_frame (MetaScreenCastStreamSrc  *src,
       g_clear_handle_id (&priv->follow_up_frame_source_id, g_source_remove);
       if (do_record_frame (src, flags, spa_buffer, data, &error))
         {
+          struct spa_data *spa_data = &spa_buffer->datas[0];
           struct spa_meta_region *spa_meta_video_crop;
 
-          spa_buffer->datas[0].chunk->size = spa_buffer->datas[0].maxsize;
-          spa_buffer->datas[0].chunk->stride = priv->video_stride;
+          spa_data->chunk->size = spa_data->maxsize;
+          spa_data->chunk->stride =
+            meta_screen_cast_stream_src_calculate_stride (src, spa_data);
 
           /* Update VideoCrop if needed */
           spa_meta_video_crop =


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]