From 0d558597fad3a19d3ad77a351a065ee4bc5c52f8 Mon Sep 17 00:00:00 2001 From: Seunghun Lee Date: Thu, 4 Jul 2024 16:45:54 +0900 Subject: [PATCH] compositor,video_shell: Use ds_surface's sync mechanism Change-Id: I4adb7568c16f80fd9b2e37b1c9301648ca5bbfc8 --- configure.ac | 2 +- src/bin/server/e_compositor.c | 224 ++++++++++++++++------------------- src/bin/server/e_compositor_intern.h | 6 +- src/bin/server/e_video_shell.c | 63 +++++----- 4 files changed, 136 insertions(+), 159 deletions(-) diff --git a/configure.ac b/configure.ac index 9262b1e..112fa32 100755 --- a/configure.ac +++ b/configure.ac @@ -288,7 +288,7 @@ e_requires="\ libtdm >= "1.0.0" \ glib-2.0 \ gobject-2.0 \ - libds \ + libds >= 0.1.7 \ libds-xdg-shell-v6 \ libds-tizen \ " diff --git a/src/bin/server/e_compositor.c b/src/bin/server/e_compositor.c index 176e008..2f7cda1 100644 --- a/src/bin/server/e_compositor.c +++ b/src/bin/server/e_compositor.c @@ -43,6 +43,9 @@ struct _E_Surface E_Client_Hook *client_del_hook; struct wl_listener destroy; + struct wl_listener precommit_to_cache; + struct wl_listener precommit_from_cache; + struct wl_listener precommit_from_pending; struct wl_listener commit; struct wl_listener new_subsurface; @@ -50,6 +53,9 @@ struct _E_Surface { struct wl_signal destroy; struct wl_signal parent_destroy; + struct wl_signal precommit_to_cache; + struct wl_signal precommit_from_cache; + struct wl_signal precommit_from_pending; struct wl_signal commit; } events; }; @@ -71,17 +77,11 @@ struct _E_Subsurface struct wl_listener destroy; struct wl_listener surface_destroy; struct wl_listener parent_surface_destroy; - struct wl_listener cached; - struct wl_listener sync_precommit; - struct wl_listener desync_precommit; struct wl_listener request_move; struct { struct wl_signal destroy; - struct wl_signal cached; - struct wl_signal sync_precommit; - struct wl_signal desync_precommit; } events; Eina_Bool internal; @@ -104,6 +104,9 @@ static void _e_surface_destroy(E_Surface *surface); static void _e_surface_ds_surface_set(E_Surface *surface, struct ds_surface *ds_surface); static void _e_surface_cb_client_del(void *data, E_Client *ec); static void _e_surface_cb_destroy(struct wl_listener *listener, void *data); +static void _e_surface_cb_precommit_to_cache(struct wl_listener *listener, void *data); +static void _e_surface_cb_precommit_from_cache(struct wl_listener *listener, void *data); +static void _e_surface_cb_precommit_from_pending(struct wl_listener *listener, void *data); static void _e_surface_cb_commit(struct wl_listener *listener, void *data); static void _e_surface_cb_new_subsurface(struct wl_listener *listener, void *data); @@ -114,10 +117,8 @@ static E_Subsurface *_e_subsurface_from_ds_subsurface(struct ds_subsurface *ds_s static void _e_subsurface_destroy(E_Subsurface *sub); static void _e_subsurface_commit(E_Subsurface *sub); static void _e_subsurface_place_below_parent(E_Subsurface *sub); +static Eina_Bool _e_subsurface_synchronized_check(E_Subsurface *sub); static void _e_subsurface_cb_destroy(struct wl_listener *listener, void *data); -static void _e_subsurface_cb_cached(struct wl_listener *listener, void *data); -static void _e_subsurface_cb_sync_precommit(struct wl_listener *listener, void *data); -static void _e_subsurface_cb_desync_precommit(struct wl_listener *listener, void *data); static void _e_subsurface_cb_request_move(struct wl_listener *listener, void *data); static void _e_subsurface_cb_surface_destroy(struct wl_listener *listener, void *data); static void _e_subsurface_cb_parent_surface_destroy(struct wl_listener *listener, void *data); @@ -369,6 +370,23 @@ e_surface_parent_destroy_listener_add(E_Surface *surface, struct wl_listener *li } EINTERN void +e_surface_precommit_to_cache_listener_add(E_Surface *surface, struct wl_listener *listener) +{ + wl_signal_add(&surface->events.precommit_to_cache, listener); +} + +EINTERN void +e_surface_precommit_from_cache_listener_add(E_Surface *surface, struct wl_listener *listener) +{ + wl_signal_add(&surface->events.precommit_from_cache, listener); +} +EINTERN void +e_surface_precommit_from_pending_listener_add(E_Surface *surface, struct wl_listener *listener) +{ + wl_signal_add(&surface->events.precommit_from_pending, listener); +} + +EINTERN void e_surface_commit_listener_add(E_Surface *surface, struct wl_listener *listener) { wl_signal_add(&surface->events.commit, listener); @@ -853,6 +871,9 @@ _e_surface_create(E_Client *ec) wl_signal_init(&surface->events.destroy); wl_signal_init(&surface->events.parent_destroy); + wl_signal_init(&surface->events.precommit_to_cache); + wl_signal_init(&surface->events.precommit_from_cache); + wl_signal_init(&surface->events.precommit_from_pending); wl_signal_init(&surface->events.commit); wl_signal_init(&surface->base.destroy_signal); wl_signal_init(&surface->base.apply_viewport_signal); @@ -954,6 +975,15 @@ _e_surface_ds_surface_set(E_Surface *surface, struct ds_surface *ds_surface) surface->destroy.notify = _e_surface_cb_destroy; ds_surface_add_destroy_listener(ds_surface, &surface->destroy); + surface->precommit_to_cache.notify = _e_surface_cb_precommit_to_cache; + ds_surface_add_precommit_to_cache_listener(ds_surface, &surface->precommit_to_cache); + + surface->precommit_from_cache.notify = _e_surface_cb_precommit_from_cache; + ds_surface_add_precommit_from_cache_listener(ds_surface, &surface->precommit_from_cache); + + surface->precommit_from_pending.notify = _e_surface_cb_precommit_from_pending; + ds_surface_add_precommit_from_pending_listener(ds_surface, &surface->precommit_from_pending); + surface->commit.notify = _e_surface_cb_commit; ds_surface_add_commit_listener(ds_surface, &surface->commit); @@ -1427,6 +1457,9 @@ _e_surface_cb_destroy(struct wl_listener *listener, void *data) wl_signal_emit(&surface->events.destroy, surface); wl_list_remove(&surface->destroy.link); + wl_list_remove(&surface->precommit_to_cache.link); + wl_list_remove(&surface->precommit_from_cache.link); + wl_list_remove(&surface->precommit_from_pending.link); wl_list_remove(&surface->commit.link); wl_list_remove(&surface->new_subsurface.link); surface->ds_surface = NULL; @@ -1435,6 +1468,68 @@ _e_surface_cb_destroy(struct wl_listener *listener, void *data) } static void +_e_surface_cb_precommit_to_cache(struct wl_listener *listener, void *data) +{ + E_Surface *surface; + E_Subsurface *subsurface; + + surface = wl_container_of(listener, surface, precommit_to_cache); + subsurface = _e_subsurface_from_surface(surface); + + wl_signal_emit(&surface->events.precommit_to_cache, surface); + + e_presentation_time_container_feedback_discard(&subsurface->base.cached.presentation_container); + e_presentation_time_container_feedback_merge(&subsurface->base.cached.presentation_container, + &surface->base.pending.presentation_container); + + subsurface->base.cached.has_data = EINA_TRUE; + + e_comp_wl_hook_call(E_COMP_WL_HOOK_SUBSURFACE_COMMIT_TO_CACHE, surface->ec); +} + +static void +_e_surface_cb_precommit_from_cache(struct wl_listener *listener, void *data) +{ + E_Surface *surface; + E_Subsurface *subsurface; + + surface = wl_container_of(listener, surface, precommit_from_cache); + subsurface = _e_subsurface_from_surface(surface); + + wl_signal_emit(&surface->events.precommit_from_cache, surface); + + if (subsurface->base.cached.has_data) + { + e_presentation_time_container_feedback_discard(&surface->base.presentation_container); + e_presentation_time_container_feedback_merge(&surface->base.presentation_container, + &subsurface->base.cached.presentation_container); + subsurface->base.cached.has_data = EINA_FALSE; + } + + // The _e_subsurface_synchronized_check() should be called, because this + // callback could be called due to the wl_subsurface.set_desync() + if (_e_subsurface_synchronized_check(subsurface)) + { + e_comp_wl_hook_call(E_COMP_WL_HOOK_SUBSURFACE_SYNCHRONIZED_COMMIT, + surface->ec); + } +} + +static void +_e_surface_cb_precommit_from_pending(struct wl_listener *listener, void *data) +{ + E_Surface *surface; + + surface = wl_container_of(listener, surface, precommit_from_pending); + + wl_signal_emit(&surface->events.precommit_from_pending, surface); + + e_presentation_time_container_feedback_discard(&surface->base.presentation_container); + e_presentation_time_container_feedback_merge(&surface->base.presentation_container, + &surface->base.pending.presentation_container); +} + +static void _e_surface_cb_commit(struct wl_listener *listener, void *data) { E_Surface *surface; @@ -1519,23 +1614,11 @@ _e_subsurface_create(struct ds_subsurface *ds_subsurface, E_Surface *parent_surf } wl_signal_init(&sub->events.destroy); - wl_signal_init(&sub->events.cached); - wl_signal_init(&sub->events.sync_precommit); - wl_signal_init(&sub->events.desync_precommit); sub->ds_subsurface = ds_subsurface; sub->destroy.notify = _e_subsurface_cb_destroy; wl_signal_add(&ds_subsurface->events.destroy, &sub->destroy); - sub->cached.notify = _e_subsurface_cb_cached; - wl_signal_add(&ds_subsurface->events.cached, &sub->cached); - - sub->sync_precommit.notify = _e_subsurface_cb_sync_precommit; - ds_surface_add_sync_precommit_listener(ds_subsurface->surface, &sub->sync_precommit); - - sub->desync_precommit.notify = _e_subsurface_cb_desync_precommit; - ds_surface_add_desync_precommit_listener(ds_subsurface->surface, &sub->desync_precommit); - sub->request_move.notify = _e_subsurface_cb_request_move; wl_signal_add(&ds_subsurface->events.request_move, &sub->request_move); @@ -1570,11 +1653,8 @@ _e_subsurface_destroy(E_Subsurface *sub) _e_subsurface_view_finish(&sub->view); e_comp_wl_client_subsurface_finish(sub->surface->ec); - wl_list_remove(&sub->desync_precommit.link); - wl_list_remove(&sub->sync_precommit.link); wl_list_remove(&sub->request_move.link); wl_list_remove(&sub->parent_surface_destroy.link); - wl_list_remove(&sub->cached.link); wl_list_remove(&sub->surface_destroy.link); wl_list_remove(&sub->destroy.link); free(sub); @@ -1683,78 +1763,6 @@ _e_subsurface_cb_destroy(struct wl_listener *listener, void *data) } static void -_e_subsurface_cb_cached(struct wl_listener *listener, void *data) -{ - E_Subsurface *sub; - - sub = wl_container_of(listener, sub, cached); - - wl_signal_emit(&sub->events.cached, sub); - - e_presentation_time_container_feedback_discard(&sub->base.cached.presentation_container); - e_presentation_time_container_feedback_merge(&sub->base.cached.presentation_container, - &sub->surface->base.pending.presentation_container); - - sub->base.cached.has_data = EINA_TRUE; - - e_comp_wl_hook_call(E_COMP_WL_HOOK_SUBSURFACE_COMMIT_TO_CACHE, sub->surface->ec); -} - -static void -_e_subsurface_cb_sync_precommit(struct wl_listener *listener, void *data) -{ - E_Subsurface *sub; - - sub = wl_container_of(listener, sub, sync_precommit); - - wl_signal_emit(&sub->events.sync_precommit, sub); - - if (sub->base.cached.has_data) - { - e_presentation_time_container_feedback_discard(&sub->surface->base.presentation_container); - e_presentation_time_container_feedback_merge(&sub->surface->base.presentation_container, - &sub->base.cached.presentation_container); - sub->base.cached.has_data = EINA_FALSE; - } - - // The _e_subsurface_synchronized_check() should be called, because this - // callback could be called due to the wl_subsurface.set_desync() - if (_e_subsurface_synchronized_check(sub)) - { - e_comp_wl_hook_call(E_COMP_WL_HOOK_SUBSURFACE_SYNCHRONIZED_COMMIT, - sub->surface->ec); - } -} - -static void -_e_subsurface_cb_desync_precommit(struct wl_listener *listener, void *data) -{ - E_Subsurface *sub; - - sub = wl_container_of(listener, sub, desync_precommit); - - wl_signal_emit(&sub->events.desync_precommit, sub); - - if (sub->base.cached.has_data) - { - e_presentation_time_container_feedback_discard(&sub->base.cached.presentation_container); - e_presentation_time_container_feedback_merge(&sub->base.cached.presentation_container, - &sub->surface->base.pending.presentation_container); - - e_presentation_time_container_feedback_discard(&sub->surface->base.presentation_container); - e_presentation_time_container_feedback_merge(&sub->surface->base.presentation_container, - &sub->base.cached.presentation_container); - sub->base.cached.has_data = EINA_FALSE; - } - else - { - e_presentation_time_container_feedback_discard(&sub->surface->base.presentation_container); - e_presentation_time_container_feedback_merge(&sub->surface->base.presentation_container, - &sub->surface->base.pending.presentation_container); - } -} - -static void _e_subsurface_cb_request_move(struct wl_listener *listener, void *data) { E_Subsurface *sub; @@ -1888,30 +1896,6 @@ e_subsurface_destroy_listener_add(E_Subsurface *subsurface, struct wl_listener * } EINTERN void -e_subsurface_cached_listener_add(E_Subsurface *subsurface, struct wl_listener *listener) -{ - EINA_SAFETY_ON_NULL_RETURN(subsurface); - assert(!subsurface->internal); - wl_signal_add(&subsurface->events.cached, listener); -} - -EINTERN void -e_subsurface_sync_precommit_listener_add(E_Subsurface *subsurface, struct wl_listener *listener) -{ - EINA_SAFETY_ON_NULL_RETURN(subsurface); - assert(!subsurface->internal); - wl_signal_add(&subsurface->events.sync_precommit, listener); -} - -EINTERN void -e_subsurface_desync_precommit_listener_add(E_Subsurface *subsurface, struct wl_listener *listener) -{ - EINA_SAFETY_ON_NULL_RETURN(subsurface); - assert(!subsurface->internal); - wl_signal_add(&subsurface->events.desync_precommit, listener); -} - -EINTERN void e_subsurface_coord_get(E_Subsurface *subsurface, int *x, int *y) { E_Subsurface *iter = subsurface; diff --git a/src/bin/server/e_compositor_intern.h b/src/bin/server/e_compositor_intern.h index 7c9b941..21dcec0 100644 --- a/src/bin/server/e_compositor_intern.h +++ b/src/bin/server/e_compositor_intern.h @@ -15,6 +15,9 @@ EINTERN E_Client *e_compositor_util_client_from_surface_resource(struct wl_resou EINTERN E_Surface *e_surface_from_resource(struct wl_resource *surface_resource); EINTERN void e_surface_destroy_listener_add(E_Surface *surface, struct wl_listener *listener); EINTERN void e_surface_parent_destroy_listener_add(E_Surface *surface, struct wl_listener *listener); +EINTERN void e_surface_precommit_to_cache_listener_add(E_Surface *surface, struct wl_listener *listener); +EINTERN void e_surface_precommit_from_cache_listener_add(E_Surface *surface, struct wl_listener *listener); +EINTERN void e_surface_precommit_from_pending_listener_add(E_Surface *surface, struct wl_listener *listener); EINTERN void e_surface_commit_listener_add(E_Surface *surface, struct wl_listener *listener); EINTERN void e_surface_map_listener_add(E_Surface *surface, struct wl_listener *listener); EINTERN void e_surface_unmap_listener_add(E_Surface *surface, struct wl_listener *listener); @@ -42,9 +45,6 @@ EINTERN E_Subsurface *e_subsurface_from_surface(E_Surface *surface); EINTERN E_Subsurface *e_subsurface_from_ec(E_Client *ec); EINTERN Eina_Bool e_subsurface_position_set(E_Subsurface *subsurface, int x, int y); EINTERN void e_subsurface_destroy_listener_add(E_Subsurface *subsurface, struct wl_listener *listener); -EINTERN void e_subsurface_cached_listener_add(E_Subsurface *subsurface, struct wl_listener *listener); -EINTERN void e_subsurface_sync_precommit_listener_add(E_Subsurface *subsurface, struct wl_listener *listener); -EINTERN void e_subsurface_desync_precommit_listener_add(E_Subsurface *subsurface, struct wl_listener *listener); EINTERN void e_subsurface_stand_alone_mode_set(E_Subsurface *sub); EINTERN void e_subsurface_stand_alone_mode_unset(E_Subsurface *sub); EINTERN void e_subsurface_coord_get(E_Subsurface *subsurface, int *x, int *y); diff --git a/src/bin/server/e_video_shell.c b/src/bin/server/e_video_shell.c index e4cc724..d5eb3ed 100644 --- a/src/bin/server/e_video_shell.c +++ b/src/bin/server/e_video_shell.c @@ -75,9 +75,9 @@ typedef struct uuid_t handle; struct wl_listener destroy; - struct wl_listener cached; - struct wl_listener sync_precommit; - struct wl_listener desync_precommit; + struct wl_listener precommit_to_cache; + struct wl_listener precommit_from_cache; + struct wl_listener precommit_from_pending; struct wl_listener parent_map; struct wl_listener parent_unmap; struct wl_listener source_destroy; @@ -347,9 +347,9 @@ _viewport_destroy(E_Video_Viewport *viewport) wl_resource_set_user_data(viewport->resource, NULL); wl_list_remove(&viewport->parent_map.link); wl_list_remove(&viewport->parent_unmap.link); - wl_list_remove(&viewport->sync_precommit.link); - wl_list_remove(&viewport->desync_precommit.link); - wl_list_remove(&viewport->cached.link); + wl_list_remove(&viewport->precommit_from_cache.link); + wl_list_remove(&viewport->precommit_from_pending.link); + wl_list_remove(&viewport->precommit_to_cache.link); wl_list_remove(&viewport->destroy.link); free(viewport); } @@ -443,45 +443,37 @@ _viewport_state_commit(E_Video_Viewport *viewport, E_Video_Viewport_State *next) } static void -_viewport_cb_cached(struct wl_listener *listener, void *data) +_viewport_cb_precommit_to_cache(struct wl_listener *listener, void *data) { - E_Video_Viewport *viewport = wl_container_of(listener, viewport, cached); + E_Video_Viewport *viewport = wl_container_of(listener, viewport, precommit_to_cache); - _viewport_state_move(&viewport->cache, &viewport->pending); + VS_INF("VIEWPORT %p| Precommit to cache (pending.committed:%d, cache.committed:%d)", + viewport, viewport->pending.committed, viewport->cache.committed); - VS_INF("VIEWPORT %p| Commit to cache(cache.committed:%d)", - viewport, viewport->cache.committed); + _viewport_state_move(&viewport->cache, &viewport->pending); } static void -_viewport_cb_sync_precommit(struct wl_listener *listener, void *data) +_viewport_cb_precommit_from_cache(struct wl_listener *listener, void *data) { - E_Video_Viewport *viewport = wl_container_of(listener, viewport, sync_precommit); + E_Video_Viewport *viewport = wl_container_of(listener, viewport, precommit_from_cache); - VS_INF("VIEWPORT %p| Sync Commit (pending.committed:%d, cache.committed:%d)", - viewport, viewport->pending.committed, viewport->cache.committed); + VS_INF("VIEWPORT %p| Precommit from cache (cache.committed:%d)", + viewport, viewport->cache.committed); if (viewport->cache.committed != E_VIDEO_VIEWPORT_STATE_CLEAN) _viewport_state_commit(viewport, &viewport->cache); } static void -_viewport_cb_desync_precommit(struct wl_listener *listener, void *data) +_viewport_cb_precommit_from_pending(struct wl_listener *listener, void *data) { - E_Video_Viewport *viewport = wl_container_of(listener, viewport, desync_precommit); + E_Video_Viewport *viewport = wl_container_of(listener, viewport, precommit_from_pending); - VS_INF("VIEWPORT %p| Desync Commit (pending.committed:%d, cache.committed:%d)", - viewport, viewport->pending.committed, viewport->cache.committed); + VS_INF("VIEWPORT %p| Precommit from pending (pending.committed:%d)", + viewport, viewport->pending.committed); - if (viewport->cache.committed != E_VIDEO_VIEWPORT_STATE_CLEAN) - { - _viewport_state_move(&viewport->cache, &viewport->pending); - _viewport_state_commit(viewport, &viewport->cache); - } - else - { - _viewport_state_commit(viewport, &viewport->pending); - } + _viewport_state_commit(viewport, &viewport->pending); } static void @@ -531,7 +523,7 @@ static void _video_shell_cb_export_viewport(struct wl_client *client, struct wl_resource *resource, uint32_t id, struct wl_resource *subsurface_resource) { E_Video_Viewport *viewport; - E_Surface *parent_surface; + E_Surface *surface, *parent_surface; viewport = calloc(1, sizeof(*viewport)); if (!viewport) @@ -558,14 +550,15 @@ _video_shell_cb_export_viewport(struct wl_client *client, struct wl_resource *re viewport->destroy.notify = _viewport_cb_subsurface_destroy; e_subsurface_destroy_listener_add(viewport->subsurface, &viewport->destroy); - viewport->cached.notify = _viewport_cb_cached; - e_subsurface_cached_listener_add(viewport->subsurface, &viewport->cached); + surface = e_subsurface_surface_get(viewport->subsurface); + viewport->precommit_to_cache.notify = _viewport_cb_precommit_to_cache; + e_surface_precommit_to_cache_listener_add(surface, &viewport->precommit_to_cache); - viewport->sync_precommit.notify = _viewport_cb_sync_precommit; - e_subsurface_sync_precommit_listener_add(viewport->subsurface, &viewport->sync_precommit); + viewport->precommit_from_cache.notify = _viewport_cb_precommit_from_cache; + e_surface_precommit_from_cache_listener_add(surface, &viewport->precommit_from_cache); - viewport->desync_precommit.notify = _viewport_cb_desync_precommit; - e_subsurface_desync_precommit_listener_add(viewport->subsurface, &viewport->desync_precommit); + viewport->precommit_from_pending.notify = _viewport_cb_precommit_from_pending; + e_surface_precommit_from_pending_listener_add(surface, &viewport->precommit_from_pending); parent_surface = e_subsurface_parent_get(viewport->subsurface); -- 2.7.4