[mutter] egl: Introduce meta_egl_create_dmabuf_image
- From: Jonas Ådahl <jadahl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [mutter] egl: Introduce meta_egl_create_dmabuf_image
- Date: Wed, 10 Jul 2019 08:38:47 +0000 (UTC)
commit 9cd3b07472b6f98a6558ae0377d0e18a982e2a22
Author: Pekka Paalanen <pekka paalanen collabora com>
Date: Mon Jun 10 17:07:55 2019 +0300
egl: Introduce meta_egl_create_dmabuf_image
This bit of code was more or less duplicated in meta-renderer-native-gles3.c
and meta-wayland-dma-buf.c. Start consolidating the two implementations by
moving the *-gles3.c function into meta-egl.c and generalizing it so it could
also accommodate the meta-wayland-dma-buf.c usage.
The workaround in the *-gles3.c implementation is moved to the caller. It is
the caller's responsibility to check for the existence of the appropriate EGL
extensions.
Commit 6f59e4858e24c828e3ab0e611d36dfaaded1b272 worked around the lack of
EGL_EXT_image_dma_buf_import_modifiers with the assumption that if the modifier
is linear, there is no need to pass it into EGL. The problem is that not
passing a modifier explicitly to EGL invokes implementation-defined behaviour,
so we should not have that workaround in meta-egl.c.
This patch intends to be pure refactoring, no behavioral changes. The one
change is the addition of g_assert to catch overwriting arbitrary memory.
https://gitlab.gnome.org/GNOME/mutter/merge_requests/615
src/backends/meta-egl.c | 94 ++++++++++++++++-
src/backends/meta-egl.h | 13 +++
src/backends/native/meta-renderer-native-gles3.c | 125 ++++-------------------
3 files changed, 127 insertions(+), 105 deletions(-)
---
diff --git a/src/backends/meta-egl.c b/src/backends/meta-egl.c
index 8b953449a..6554be935 100644
--- a/src/backends/meta-egl.c
+++ b/src/backends/meta-egl.c
@@ -1,7 +1,8 @@
/* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
/*
- * Copyright (C) 2016 Red Hat Inc.
+ * Copyright (C) 2016, 2017 Red Hat Inc.
+ * Copyright (C) 2018, 2019 DisplayLink (UK) Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
@@ -574,6 +575,97 @@ meta_egl_destroy_image (MetaEgl *egl,
return TRUE;
}
+EGLImageKHR
+meta_egl_create_dmabuf_image (MetaEgl *egl,
+ EGLDisplay egl_display,
+ unsigned int width,
+ unsigned int height,
+ uint32_t drm_format,
+ uint32_t n_planes,
+ const int *fds,
+ const uint32_t *strides,
+ const uint32_t *offsets,
+ const uint64_t *modifiers,
+ GError **error)
+{
+ EGLint attribs[37];
+ int atti = 0;
+
+ /* This requires the Mesa commit in
+ * Mesa 10.3 (08264e5dad4df448e7718e782ad9077902089a07) or
+ * Mesa 10.2.7 (55d28925e6109a4afd61f109e845a8a51bd17652).
+ * Otherwise Mesa closes the fd behind our back and re-importing
+ * will fail.
+ * https://bugs.freedesktop.org/show_bug.cgi?id=76188
+ */
+
+ attribs[atti++] = EGL_WIDTH;
+ attribs[atti++] = width;
+ attribs[atti++] = EGL_HEIGHT;
+ attribs[atti++] = height;
+ attribs[atti++] = EGL_LINUX_DRM_FOURCC_EXT;
+ attribs[atti++] = drm_format;
+
+ if (n_planes > 0)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE0_FD_EXT;
+ attribs[atti++] = fds[0];
+ attribs[atti++] = EGL_DMA_BUF_PLANE0_OFFSET_EXT;
+ attribs[atti++] = offsets[0];
+ attribs[atti++] = EGL_DMA_BUF_PLANE0_PITCH_EXT;
+ attribs[atti++] = strides[0];
+ if (modifiers)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE0_MODIFIER_LO_EXT;
+ attribs[atti++] = modifiers[0] & 0xFFFFFFFF;
+ attribs[atti++] = EGL_DMA_BUF_PLANE0_MODIFIER_HI_EXT;
+ attribs[atti++] = modifiers[0] >> 32;
+ }
+ }
+
+ if (n_planes > 1)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE1_FD_EXT;
+ attribs[atti++] = fds[1];
+ attribs[atti++] = EGL_DMA_BUF_PLANE1_OFFSET_EXT;
+ attribs[atti++] = offsets[1];
+ attribs[atti++] = EGL_DMA_BUF_PLANE1_PITCH_EXT;
+ attribs[atti++] = strides[1];
+ if (modifiers)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE1_MODIFIER_LO_EXT;
+ attribs[atti++] = modifiers[1] & 0xFFFFFFFF;
+ attribs[atti++] = EGL_DMA_BUF_PLANE1_MODIFIER_HI_EXT;
+ attribs[atti++] = modifiers[1] >> 32;
+ }
+ }
+
+ if (n_planes > 2)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE2_FD_EXT;
+ attribs[atti++] = fds[2];
+ attribs[atti++] = EGL_DMA_BUF_PLANE2_OFFSET_EXT;
+ attribs[atti++] = offsets[2];
+ attribs[atti++] = EGL_DMA_BUF_PLANE2_PITCH_EXT;
+ attribs[atti++] = strides[2];
+ if (modifiers)
+ {
+ attribs[atti++] = EGL_DMA_BUF_PLANE2_MODIFIER_LO_EXT;
+ attribs[atti++] = modifiers[2] & 0xFFFFFFFF;
+ attribs[atti++] = EGL_DMA_BUF_PLANE2_MODIFIER_HI_EXT;
+ attribs[atti++] = modifiers[2] >> 32;
+ }
+ }
+
+ attribs[atti++] = EGL_NONE;
+ g_assert (atti <= G_N_ELEMENTS (attribs));
+
+ return meta_egl_create_image (egl, egl_display, EGL_NO_CONTEXT,
+ EGL_LINUX_DMA_BUF_EXT, NULL,
+ attribs,
+ error);
+}
+
gboolean
meta_egl_make_current (MetaEgl *egl,
EGLDisplay display,
diff --git a/src/backends/meta-egl.h b/src/backends/meta-egl.h
index ff37f124f..f2a816445 100644
--- a/src/backends/meta-egl.h
+++ b/src/backends/meta-egl.h
@@ -2,6 +2,7 @@
/*
* Copyright (C) 2016 Red Hat Inc.
+ * Copyright (C) 2019 DisplayLink (UK) Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
@@ -100,6 +101,18 @@ gboolean meta_egl_destroy_image (MetaEgl *egl,
EGLImageKHR image,
GError **error);
+EGLImageKHR meta_egl_create_dmabuf_image (MetaEgl *egl,
+ EGLDisplay egl_display,
+ unsigned int width,
+ unsigned int height,
+ uint32_t drm_format,
+ uint32_t n_planes,
+ const int *fds,
+ const uint32_t *strides,
+ const uint32_t *offsets,
+ const uint64_t *modifiers,
+ GError **error);
+
EGLSurface meta_egl_create_window_surface (MetaEgl *egl,
EGLDisplay display,
EGLConfig config,
diff --git a/src/backends/native/meta-renderer-native-gles3.c
b/src/backends/native/meta-renderer-native-gles3.c
index 7afea8648..740b52ef6 100644
--- a/src/backends/native/meta-renderer-native-gles3.c
+++ b/src/backends/native/meta-renderer-native-gles3.c
@@ -45,101 +45,6 @@
#error "Somehow included OpenGL headers when we shouldn't have"
#endif
-static EGLImageKHR
-create_egl_image (MetaEgl *egl,
- EGLDisplay egl_display,
- EGLContext egl_context,
- unsigned int width,
- unsigned int height,
- uint32_t n_planes,
- uint32_t *strides,
- uint32_t *offsets,
- uint64_t *modifiers,
- uint32_t format,
- int fd,
- GError **error)
-{
- EGLint attribs[37];
- int atti = 0;
- gboolean has_modifier;
-
- /* This requires the Mesa commit in
- * Mesa 10.3 (08264e5dad4df448e7718e782ad9077902089a07) or
- * Mesa 10.2.7 (55d28925e6109a4afd61f109e845a8a51bd17652).
- * Otherwise Mesa closes the fd behind our back and re-importing
- * will fail.
- * https://bugs.freedesktop.org/show_bug.cgi?id=76188
- */
-
- attribs[atti++] = EGL_WIDTH;
- attribs[atti++] = width;
- attribs[atti++] = EGL_HEIGHT;
- attribs[atti++] = height;
- attribs[atti++] = EGL_LINUX_DRM_FOURCC_EXT;
- attribs[atti++] = format;
-
- has_modifier = (modifiers[0] != DRM_FORMAT_MOD_INVALID &&
- modifiers[0] != DRM_FORMAT_MOD_LINEAR);
-
- if (n_planes > 0)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE0_FD_EXT;
- attribs[atti++] = fd;
- attribs[atti++] = EGL_DMA_BUF_PLANE0_OFFSET_EXT;
- attribs[atti++] = offsets[0];
- attribs[atti++] = EGL_DMA_BUF_PLANE0_PITCH_EXT;
- attribs[atti++] = strides[0];
- if (has_modifier)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE0_MODIFIER_LO_EXT;
- attribs[atti++] = modifiers[0] & 0xFFFFFFFF;
- attribs[atti++] = EGL_DMA_BUF_PLANE0_MODIFIER_HI_EXT;
- attribs[atti++] = modifiers[0] >> 32;
- }
- }
-
- if (n_planes > 1)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE1_FD_EXT;
- attribs[atti++] = fd;
- attribs[atti++] = EGL_DMA_BUF_PLANE1_OFFSET_EXT;
- attribs[atti++] = offsets[1];
- attribs[atti++] = EGL_DMA_BUF_PLANE1_PITCH_EXT;
- attribs[atti++] = strides[1];
- if (has_modifier)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE1_MODIFIER_LO_EXT;
- attribs[atti++] = modifiers[1] & 0xFFFFFFFF;
- attribs[atti++] = EGL_DMA_BUF_PLANE1_MODIFIER_HI_EXT;
- attribs[atti++] = modifiers[1] >> 32;
- }
- }
-
- if (n_planes > 2)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE2_FD_EXT;
- attribs[atti++] = fd;
- attribs[atti++] = EGL_DMA_BUF_PLANE2_OFFSET_EXT;
- attribs[atti++] = offsets[2];
- attribs[atti++] = EGL_DMA_BUF_PLANE2_PITCH_EXT;
- attribs[atti++] = strides[2];
- if (has_modifier)
- {
- attribs[atti++] = EGL_DMA_BUF_PLANE2_MODIFIER_LO_EXT;
- attribs[atti++] = modifiers[2] & 0xFFFFFFFF;
- attribs[atti++] = EGL_DMA_BUF_PLANE2_MODIFIER_HI_EXT;
- attribs[atti++] = modifiers[2] >> 32;
- }
- }
-
- attribs[atti++] = EGL_NONE;
-
- return meta_egl_create_image (egl, egl_display, EGL_NO_CONTEXT,
- EGL_LINUX_DMA_BUF_EXT, NULL,
- attribs,
- error);
-}
-
static void
paint_egl_image (MetaGles3 *gles3,
EGLImageKHR egl_image,
@@ -195,8 +100,10 @@ meta_renderer_native_gles3_blit_shared_bo (MetaEgl *egl,
uint32_t strides[4] = { 0 };
uint32_t offsets[4] = { 0 };
uint64_t modifiers[4] = { 0 };
+ int fds[4] = { -1, -1, -1, -1 };
uint32_t format;
EGLImageKHR egl_image;
+ gboolean use_modifiers;
shared_bo_fd = gbm_bo_get_fd (shared_bo);
if (shared_bo_fd < 0)
@@ -216,17 +123,27 @@ meta_renderer_native_gles3_blit_shared_bo (MetaEgl *egl,
strides[i] = gbm_bo_get_stride_for_plane (shared_bo, i);
offsets[i] = gbm_bo_get_offset (shared_bo, i);
modifiers[i] = gbm_bo_get_modifier (shared_bo);
+ fds[i] = shared_bo_fd;
}
- egl_image = create_egl_image (egl,
- egl_display,
- egl_context,
- width, height,
- n_planes,
- strides, offsets,
- modifiers, format,
- shared_bo_fd,
- error);
+ /* Workaround for https://gitlab.gnome.org/GNOME/mutter/issues/18 */
+ if (modifiers[0] == DRM_FORMAT_MOD_LINEAR ||
+ modifiers[0] == DRM_FORMAT_MOD_INVALID)
+ use_modifiers = FALSE;
+ else
+ use_modifiers = TRUE;
+
+ egl_image = meta_egl_create_dmabuf_image (egl,
+ egl_display,
+ width,
+ height,
+ format,
+ n_planes,
+ fds,
+ strides,
+ offsets,
+ use_modifiers ? modifiers : NULL,
+ error);
close (shared_bo_fd);
if (!egl_image)
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]