From c5e1515b7a5e24e0e95402595f64a42b3e1bb16b Mon Sep 17 00:00:00 2001 From: Wim Taymans Date: Sun, 21 May 2023 15:36:00 +0200 Subject: [PATCH] context: add method to add/remove context listener --- src/modules/module-profiler.c | 27 ++++---------------- src/pipewire/context.c | 47 +++++++++++++++++++++++++++++++++++ src/pipewire/private.h | 7 ++++++ src/pipewire/stream.c | 5 ++-- 4 files changed, 62 insertions(+), 24 deletions(-) diff --git a/src/modules/module-profiler.c b/src/modules/module-profiler.c index 8a45f2b2d..0e731ef75 100644 --- a/src/modules/module-profiler.c +++ b/src/modules/module-profiler.c @@ -275,19 +275,11 @@ static const struct pw_context_driver_events context_events = { .complete = context_do_profile, }; -static int do_stop(struct spa_loop *loop, - bool async, uint32_t seq, const void *data, size_t size, void *user_data) -{ - struct impl *impl = user_data; - spa_hook_remove(&impl->context_listener); - return 0; -} - static void stop_listener(struct impl *impl) { if (impl->listening) { - pw_loop_invoke(impl->data_loop, - do_stop, SPA_ID_INVALID, NULL, 0, true, impl); + pw_context_driver_remove_listener(impl->context, + &impl->context_listener); impl->listening = false; } } @@ -306,16 +298,6 @@ static const struct pw_resource_events resource_events = { .destroy = resource_destroy, }; -static int -do_start(struct spa_loop *loop, - bool async, uint32_t seq, const void *data, size_t size, void *user_data) -{ - struct impl *impl = user_data; - spa_hook_list_append(&impl->context->driver_listener_list, - &impl->context_listener, - &context_events, impl); - return 0; -} static int global_bind(void *object, struct pw_impl_client *client, uint32_t permissions, uint32_t version, uint32_t id) @@ -340,8 +322,9 @@ global_bind(void *object, struct pw_impl_client *client, uint32_t permissions, if (++impl->busy == 1) { pw_log_info("%p: starting profiler", impl); - pw_loop_invoke(impl->data_loop, - do_start, SPA_ID_INVALID, NULL, 0, false, impl); + pw_context_driver_add_listener(impl->context, + &impl->context_listener, + &context_events, impl); impl->listening = true; } return 0; diff --git a/src/pipewire/context.c b/src/pipewire/context.c index 4fa44db6b..95f70eff4 100644 --- a/src/pipewire/context.c +++ b/src/pipewire/context.c @@ -478,6 +478,53 @@ void pw_context_add_listener(struct pw_context *context, spa_hook_list_append(&context->listener_list, listener, events, data); } +struct listener_data { + struct spa_hook *listener; + const struct pw_context_driver_events *events; + void *data; +}; + +static int +do_add_listener(struct spa_loop *loop, + bool async, uint32_t seq, const void *data, size_t size, void *user_data) +{ + struct pw_context *context = user_data; + const struct listener_data *d = data; + spa_hook_list_append(&context->driver_listener_list, + d->listener, d->events, d->data); + return 0; +} + +SPA_EXPORT +void pw_context_driver_add_listener(struct pw_context *context, + struct spa_hook *listener, + const struct pw_context_driver_events *events, + void *data) +{ + struct listener_data d = { + .listener = listener, + .events = events, + .data = data }; + pw_loop_invoke(context->data_loop, + do_add_listener, SPA_ID_INVALID, &d, sizeof(d), false, context); +} + +static int do_remove_listener(struct spa_loop *loop, + bool async, uint32_t seq, const void *data, size_t size, void *user_data) +{ + struct spa_hook *listener = user_data; + spa_hook_remove(listener); + return 0; +} + +SPA_EXPORT +void pw_context_driver_remove_listener(struct pw_context *context, + struct spa_hook *listener) +{ + pw_loop_invoke(context->data_loop, + do_remove_listener, SPA_ID_INVALID, NULL, 0, true, listener); +} + SPA_EXPORT const struct spa_support *pw_context_get_support(struct pw_context *context, uint32_t *n_support) { diff --git a/src/pipewire/private.h b/src/pipewire/private.h index 541d4c426..5dfe157bf 100644 --- a/src/pipewire/private.h +++ b/src/pipewire/private.h @@ -423,6 +423,13 @@ struct pw_context_driver_events { void (*complete) (void *data, struct pw_impl_node *node); }; +void pw_context_driver_add_listener(struct pw_context *context, + struct spa_hook *listener, + const struct pw_context_driver_events *events, + void *data); +void pw_context_driver_remove_listener(struct pw_context *context, + struct spa_hook *listener); + #define pw_registry_resource(r,m,v,...) pw_resource_call(r, struct pw_registry_events,m,v,##__VA_ARGS__) #define pw_registry_resource_global(r,...) pw_registry_resource(r,global,0,__VA_ARGS__) #define pw_registry_resource_global_remove(r,...) pw_registry_resource(r,global_remove,0,__VA_ARGS__) diff --git a/src/pipewire/stream.c b/src/pipewire/stream.c index 7a078c6fe..1a5c42713 100644 --- a/src/pipewire/stream.c +++ b/src/pipewire/stream.c @@ -1515,7 +1515,7 @@ stream_new(struct pw_context *context, const char *name, impl->allow_mlock = context->settings.mem_allow_mlock; impl->warn_mlock = context->settings.mem_warn_mlock; - spa_hook_list_append(&impl->context->driver_listener_list, + pw_context_driver_add_listener(impl->context, &impl->context_listener, &context_events, impl); return impl; @@ -1683,7 +1683,8 @@ void pw_stream_destroy(struct pw_stream *stream) spa_hook_list_clean(&impl->hooks); spa_hook_list_clean(&stream->listener_list); - spa_hook_remove(&impl->context_listener); + pw_context_driver_remove_listener(impl->context, + &impl->context_listener); if (impl->data.context) pw_context_destroy(impl->data.context);