diff options
-rw-r--r-- | src/compositor/meta-multi-texture-format.c | 97 | ||||
-rw-r--r-- | src/meta/meta-multi-texture-format.h | 3 | ||||
-rw-r--r-- | src/wayland/meta-wayland-dma-buf.c | 94 |
3 files changed, 132 insertions, 62 deletions
diff --git a/src/compositor/meta-multi-texture-format.c b/src/compositor/meta-multi-texture-format.c index 4e19111d3..f06bc71c7 100644 --- a/src/compositor/meta-multi-texture-format.c +++ b/src/compositor/meta-multi-texture-format.c @@ -89,6 +89,7 @@ static const char y_u_v_to_rgb_shader[] = typedef struct _MetaMultiTextureFormatInfo { MetaMultiTextureFormat multi_format; + const char *name; uint8_t n_planes; /* Per plane-information */ @@ -107,6 +108,7 @@ typedef struct _MetaMultiTextureFormatInfo static MetaMultiTextureFormatInfo multi_format_table[] = { /* Simple */ { + .name = "", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -116,7 +118,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shader = NULL, }, /* Packed YUV */ - { /* YUYV */ + { + .name = "YUYV", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -125,7 +128,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = YUV_TO_RGB_FUNC, .rgb_shader = yuv_to_rgb_shader, }, - { /* YVYU */ + { + .name = "YVYU", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -134,7 +138,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = YUV_TO_RGB_FUNC, .rgb_shader = yuv_to_rgb_shader, }, - { /* UYVY */ + { + .name = "UYVY", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -143,7 +148,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = YUV_TO_RGB_FUNC, .rgb_shader = yuv_to_rgb_shader, }, - { /* VYUY */ + { + .name = "VYUY", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -152,7 +158,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = YUV_TO_RGB_FUNC, .rgb_shader = yuv_to_rgb_shader, }, - { /* AYUV */ + { + .name = "AYUV", .n_planes = 1, .bpp = { 4 }, .hsub = { 1 }, @@ -162,7 +169,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shader = yuv_to_rgb_shader, }, /* 2 plane RGB + A */ - { /* XRGB8888_A8 */ + { + .name = "XRGB8888_A8", .n_planes = 2, .bpp = { 4, 1 }, .hsub = { 1, 1 }, @@ -171,7 +179,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* XBGR8888_A8 */ + { + .name = "XBGR8888_A8", .n_planes = 2, .bpp = { 4, 1 }, .hsub = { 1, 1 }, @@ -180,7 +189,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* RGBX8888_A8 */ + { + .name = "RGBX8888_A8", .n_planes = 2, .bpp = { 4, 1 }, .hsub = { 1, 1 }, @@ -189,7 +199,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* BGRX8888_A8 */ + { + .name = "BGRX8888_A8", .n_planes = 2, .bpp = { 4, 1 }, .hsub = { 1, 1 }, @@ -198,7 +209,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* RGB888_A8 */ + { + .name = "RGB888_A8", .n_planes = 2, .bpp = { 3, 1 }, .hsub = { 1, 1 }, @@ -207,7 +219,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* BGR888_A8 */ + { + .name = "BGR888_A8", .n_planes = 2, .bpp = { 3, 1 }, .hsub = { 1, 1 }, @@ -216,7 +229,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* RGB565_A8 */ + { + .name = "RGB565_A8", .n_planes = 2, .bpp = { 2, 1 }, .hsub = { 1, 1 }, @@ -225,7 +239,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = NULL, .rgb_shader = NULL, }, - { /* BGR565_A8 */ + { + .name = "BGR565_A8", .n_planes = 2, .bpp = { 2, 1 }, .hsub = { 1, 1 }, @@ -235,7 +250,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shader = NULL, }, /* 2 plane YUV */ - { /* NV12 */ + { + .name = "NV12", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 2 }, @@ -244,7 +260,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_UV_TO_RGB_FUNC, .rgb_shader = y_uv_to_rgb_shader, }, - { /* NV21 */ + { + .name = "NV21", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 2 }, @@ -253,7 +270,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_UV_TO_RGB_FUNC, .rgb_shader = y_uv_to_rgb_shader, }, - { /* NV16 */ + { + .name = "NV16", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 2 }, @@ -262,7 +280,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_UV_TO_RGB_FUNC, .rgb_shader = y_uv_to_rgb_shader, }, - { /* NV61 */ + { + .name = "NV61", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 2 }, @@ -271,7 +290,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_UV_TO_RGB_FUNC, .rgb_shader = y_uv_to_rgb_shader, }, - { /* NV24 */ + { + .name = "NV24", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 1 }, @@ -280,7 +300,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_UV_TO_RGB_FUNC, .rgb_shader = y_uv_to_rgb_shader, }, - { /* NV42 */ + { + .name = "NV42", .n_planes = 2, .bpp = { 1, 2 }, .hsub = { 1, 1 }, @@ -290,7 +311,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shader = y_uv_to_rgb_shader, }, /* 3 plane YUV */ - { /* YUV410 */ + { + .name = "YUV410", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 4, 4 }, @@ -299,7 +321,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YVU410 */ + { + .name = "YVU410", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 4, 4 }, @@ -308,7 +331,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YUV411 */ + { + .name = "YUV411", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 4, 4 }, @@ -317,7 +341,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YVU411 */ + { + .name = "YVU411", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 4, 4 }, @@ -326,7 +351,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YUV420 */ + { + .name = "YUV420", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 2, 2 }, @@ -335,7 +361,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YVU420 */ + { + .name = "YVU420", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 2, 2 }, @@ -344,7 +371,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YUV422 */ + { + .name = "YUV422", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 2, 2 }, @@ -353,7 +381,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YVU422 */ + { + .name = "YVU422", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 2, 2 }, @@ -362,7 +391,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YUV444 */ + { + .name = "YUV444", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 1, 1 }, @@ -371,7 +401,8 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { .rgb_shaderfunc = Y_U_V_TO_RGB_FUNC, .rgb_shader = y_u_v_to_rgb_shader, }, - { /* YVU444 */ + { + .name = "YVU444", .n_planes = 3, .bpp = { 1, 1, 1 }, .hsub = { 1, 1, 1 }, @@ -382,6 +413,14 @@ static MetaMultiTextureFormatInfo multi_format_table[] = { }, }; +const char * +meta_multi_texture_format_to_string (MetaMultiTextureFormat format) +{ + g_return_val_if_fail (format < G_N_ELEMENTS (multi_format_table), NULL); + + return multi_format_table[format].name; +} + void meta_multi_texture_format_get_bytes_per_pixel (MetaMultiTextureFormat format, uint8_t *bpp_out) diff --git a/src/meta/meta-multi-texture-format.h b/src/meta/meta-multi-texture-format.h index bb0b5fc17..ea1f94c1a 100644 --- a/src/meta/meta-multi-texture-format.h +++ b/src/meta/meta-multi-texture-format.h @@ -109,6 +109,9 @@ typedef enum _MetaMultiTextureFormat } MetaMultiTextureFormat; META_EXPORT +const char * meta_multi_texture_format_to_string (MetaMultiTextureFormat format); + +META_EXPORT void meta_multi_texture_format_get_bytes_per_pixel (MetaMultiTextureFormat format, uint8_t *bpp_out); diff --git a/src/wayland/meta-wayland-dma-buf.c b/src/wayland/meta-wayland-dma-buf.c index 943a338e2..ae23777f1 100644 --- a/src/wayland/meta-wayland-dma-buf.c +++ b/src/wayland/meta-wayland-dma-buf.c @@ -91,13 +91,13 @@ meta_wayland_dma_buf_realize_texture (MetaWaylandBuffer *buffer, CoglContext *cogl_context = clutter_backend_get_cogl_context (clutter_backend); EGLDisplay egl_display = cogl_egl_context_get_egl_display (cogl_context); MetaWaylandDmaBufBuffer *dma_buf = buffer->dma_buf.dma_buf; - uint32_t n_planes; + uint32_t i, n_planes; uint64_t modifiers[META_WAYLAND_DMA_BUF_MAX_FDS]; - CoglPixelFormat cogl_format; - EGLImageKHR egl_image; - CoglEglImageFlags flags; - CoglTexture2D *cogl_texture; + MetaMultiTextureFormat multi_format = META_MULTI_TEXTURE_FORMAT_SIMPLE; + CoglPixelFormat cogl_format = COGL_PIXEL_FORMAT_ANY; MetaDrmFormatBuf format_buf; + GPtrArray *planes; + if (buffer->dma_buf.texture) return TRUE; @@ -134,6 +134,9 @@ meta_wayland_dma_buf_realize_texture (MetaWaylandBuffer *buffer, case DRM_FORMAT_ARGB16161616F: cogl_format = COGL_PIXEL_FORMAT_ARGB_FP_16161616_PRE; break; + case DRM_FORMAT_NV12: + multi_format = META_MULTI_TEXTURE_FORMAT_NV12; + break; default: g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, @@ -142,9 +145,11 @@ meta_wayland_dma_buf_realize_texture (MetaWaylandBuffer *buffer, } meta_topic (META_DEBUG_WAYLAND, - "[dma-buf] wl_buffer@%u DRM format %s -> CoglPixelFormat %s", + "[dma-buf] wl_buffer@%u DRM format %s " + "-> MetaMultiTextureFormat %s / CoglPixelFormat %s", wl_resource_get_id (meta_wayland_buffer_get_resource (buffer)), meta_drm_format_to_string (&format_buf, dma_buf->drm_format), + meta_multi_texture_format_to_string (multi_format), cogl_pixel_format_to_string (cogl_format)); for (n_planes = 0; n_planes < META_WAYLAND_DMA_BUF_MAX_FDS; n_planes++) @@ -155,38 +160,56 @@ meta_wayland_dma_buf_realize_texture (MetaWaylandBuffer *buffer, modifiers[n_planes] = dma_buf->drm_modifier; } - egl_image = meta_egl_create_dmabuf_image (egl, - egl_display, - dma_buf->width, - dma_buf->height, - dma_buf->drm_format, - n_planes, - dma_buf->fds, - dma_buf->strides, - dma_buf->offsets, - modifiers, - error); - if (egl_image == EGL_NO_IMAGE_KHR) - return FALSE; - - flags = COGL_EGL_IMAGE_FLAG_NO_GET_DATA; - cogl_texture = cogl_egl_texture_2d_new_from_image (cogl_context, - dma_buf->width, - dma_buf->height, - cogl_format, - egl_image, - flags, - error); - - meta_egl_destroy_image (egl, egl_display, egl_image, NULL); + /* Each EGLImage is a plane in the final CoglMultiPlaneTexture */ + planes = g_ptr_array_new_full (n_planes, cogl_object_unref); - if (!cogl_texture) - return FALSE; + for (i = 0; i < n_planes; i++) + { + EGLImageKHR egl_image; + CoglEglImageFlags flags; + CoglTexture2D *cogl_texture; + + egl_image = meta_egl_create_dmabuf_image (egl, + egl_display, + dma_buf->width, + dma_buf->height, + dma_buf->drm_format, + n_planes, + dma_buf->fds, + dma_buf->strides, + dma_buf->offsets, + modifiers, + error); + if (egl_image == EGL_NO_IMAGE_KHR) + goto on_error; + + flags = COGL_EGL_IMAGE_FLAG_NO_GET_DATA; + cogl_texture = cogl_egl_texture_2d_new_from_image (cogl_context, + dma_buf->width, + dma_buf->height, + cogl_format, + egl_image, + flags, + error); + + meta_egl_destroy_image (egl, egl_display, egl_image, NULL); + + if (!cogl_texture) + goto on_error; + + g_ptr_array_add (planes, cogl_texture); + } - buffer->dma_buf.texture = meta_multi_texture_new_simple (COGL_TEXTURE (cogl_texture)); + buffer->dma_buf.texture = meta_multi_texture_new (multi_format, + g_ptr_array_free (planes, FALSE), + n_planes); buffer->is_y_inverted = dma_buf->is_y_inverted; return TRUE; + +on_error: + g_ptr_array_free (planes, TRUE); + return FALSE; } gboolean @@ -604,6 +627,8 @@ should_send_modifiers (MetaBackend *backend) { MetaSettings *settings = meta_backend_get_settings (backend); + return TRUE; + #ifdef HAVE_NATIVE_BACKEND if (META_IS_BACKEND_NATIVE (backend)) { @@ -639,6 +664,7 @@ send_modifiers (struct wl_resource *resource, if (wl_resource_get_version (resource) < ZWP_LINUX_DMABUF_V1_MODIFIER_SINCE_VERSION) return; + g_warning ("should_send_modfiers() == %d", should_send_modifiers(backend)); if (!should_send_modifiers (backend)) { zwp_linux_dmabuf_v1_send_modifier (resource, format, @@ -706,6 +732,8 @@ dma_buf_bind (struct wl_client *client, send_modifiers (resource, DRM_FORMAT_XBGR16161616F); send_modifiers (resource, DRM_FORMAT_XRGB16161616F); send_modifiers (resource, DRM_FORMAT_ARGB16161616F); + /* XXX add more */ + send_modifiers (resource, DRM_FORMAT_NV12); } /** |