summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWim Taymans <wtaymans@redhat.com>2019-11-28 11:50:17 +0100
committerWim Taymans <wtaymans@redhat.com>2019-11-29 13:34:00 +0100
commitf56e4dbc4d4d9b401c03629b79ca0c6953199420 (patch)
tree9c245b23abee0657b10b8c35eec6ea99e9b4d003
parentb264ef07721cf2bfbc2fd40debc9c5559c079dd4 (diff)
interfaces: add event to notify of global bound id
Make it possible to know when a proxy is bound to a global id before the global shows up in the registry. This makes it possible to match locally created objects to the one appearing in the registry and possibly avoid a second bind.
-rw-r--r--src/modules/module-protocol-native/protocol-native.c31
-rw-r--r--src/pipewire/interfaces.h19
-rw-r--r--src/pipewire/private.h2
-rw-r--r--src/pipewire/proxy.h3
-rw-r--r--src/pipewire/remote.c12
-rw-r--r--src/pipewire/resource.c12
-rw-r--r--src/pipewire/resource.h3
-rw-r--r--src/tests/test-interfaces.c2
8 files changed, 81 insertions, 3 deletions
diff --git a/src/modules/module-protocol-native/protocol-native.c b/src/modules/module-protocol-native/protocol-native.c
index 8cbffe3d..befbdd15 100644
--- a/src/modules/module-protocol-native/protocol-native.c
+++ b/src/modules/module-protocol-native/protocol-native.c
@@ -337,6 +337,21 @@ static int core_event_demarshal_remove_id(void *object, const struct pw_protocol
return pw_proxy_notify(proxy, struct pw_core_proxy_events, remove_id, 0, id);
}
+static int core_event_demarshal_bound_id(void *object, const struct pw_protocol_native_message *msg)
+{
+ struct pw_proxy *proxy = object;
+ struct spa_pod_parser prs;
+ uint32_t id, global_id;
+
+ spa_pod_parser_init(&prs, msg->data, msg->size);
+ if (spa_pod_parser_get_struct(&prs,
+ SPA_POD_Int(&id),
+ SPA_POD_Int(&global_id)) < 0)
+ return -EINVAL;
+
+ return pw_proxy_notify(proxy, struct pw_core_proxy_events, bound_id, 0, id, global_id);
+}
+
static int core_event_demarshal_add_mem(void *object, const struct pw_protocol_native_message *msg)
{
struct pw_proxy *proxy = object;
@@ -454,6 +469,20 @@ static void core_event_marshal_remove_id(void *object, uint32_t id)
pw_protocol_native_end_resource(resource, b);
}
+static void core_event_marshal_bound_id(void *object, uint32_t id, uint32_t global_id)
+{
+ struct pw_resource *resource = object;
+ struct spa_pod_builder *b;
+
+ b = pw_protocol_native_begin_resource(resource, PW_CORE_PROXY_EVENT_BOUND_ID, NULL);
+
+ spa_pod_builder_add_struct(b,
+ SPA_POD_Int(id),
+ SPA_POD_Int(global_id));
+
+ pw_protocol_native_end_resource(resource, b);
+}
+
static void core_event_marshal_add_mem(void *object, uint32_t id, uint32_t type, int fd, uint32_t flags)
{
struct pw_resource *resource = object;
@@ -1894,6 +1923,7 @@ static const struct pw_core_proxy_events pw_protocol_native_core_event_marshal =
.ping = &core_event_marshal_ping,
.error = &core_event_marshal_error,
.remove_id = &core_event_marshal_remove_id,
+ .bound_id = &core_event_marshal_bound_id,
.add_mem = &core_event_marshal_add_mem,
.remove_mem = &core_event_marshal_remove_mem,
};
@@ -1906,6 +1936,7 @@ pw_protocol_native_core_event_demarshal[PW_CORE_PROXY_EVENT_NUM] =
[PW_CORE_PROXY_EVENT_PING] = { &core_event_demarshal_ping, 0, },
[PW_CORE_PROXY_EVENT_ERROR] = { &core_event_demarshal_error, 0, },
[PW_CORE_PROXY_EVENT_REMOVE_ID] = { &core_event_demarshal_remove_id, 0, },
+ [PW_CORE_PROXY_EVENT_BOUND_ID] = { &core_event_demarshal_bound_id, 0, },
[PW_CORE_PROXY_EVENT_ADD_MEM] = { &core_event_demarshal_add_mem, 0, },
[PW_CORE_PROXY_EVENT_REMOVE_MEM] = { &core_event_demarshal_remove_mem, 0, },
};
diff --git a/src/pipewire/interfaces.h b/src/pipewire/interfaces.h
index 5c5042ed..40e826e6 100644
--- a/src/pipewire/interfaces.h
+++ b/src/pipewire/interfaces.h
@@ -83,9 +83,10 @@ struct pw_link_proxy { struct spa_interface iface; };
#define PW_CORE_PROXY_EVENT_PING 2
#define PW_CORE_PROXY_EVENT_ERROR 3
#define PW_CORE_PROXY_EVENT_REMOVE_ID 4
-#define PW_CORE_PROXY_EVENT_ADD_MEM 5
-#define PW_CORE_PROXY_EVENT_REMOVE_MEM 6
-#define PW_CORE_PROXY_EVENT_NUM 7
+#define PW_CORE_PROXY_EVENT_BOUND_ID 5
+#define PW_CORE_PROXY_EVENT_ADD_MEM 6
+#define PW_CORE_PROXY_EVENT_REMOVE_MEM 7
+#define PW_CORE_PROXY_EVENT_NUM 8
/** \struct pw_core_proxy_events
* \brief Core events
@@ -153,6 +154,18 @@ struct pw_core_proxy_events {
void (*remove_id) (void *object, uint32_t id);
/**
+ * Notify an object binding
+ *
+ * This event is emited when a local object ID is bound to a
+ * global ID. It is emited before the global becomes visible in the
+ * registry.
+ *
+ * \param id bound object ID
+ * \param global_id the global id bound to
+ */
+ void (*bound_id) (void *object, uint32_t id, uint32_t global_id);
+
+ /**
* Add memory for a client
*
* Memory is given to a client as \a fd of a certain
diff --git a/src/pipewire/private.h b/src/pipewire/private.h
index 77b46b3a..b1a0c40c 100644
--- a/src/pipewire/private.h
+++ b/src/pipewire/private.h
@@ -180,6 +180,7 @@ struct pw_global {
#define pw_core_resource_ping(r,...) pw_core_resource(r,ping,0,__VA_ARGS__)
#define pw_core_resource_error(r,...) pw_core_resource(r,error,0,__VA_ARGS__)
#define pw_core_resource_remove_id(r,...) pw_core_resource(r,remove_id,0,__VA_ARGS__)
+#define pw_core_resource_bound_id(r,...) pw_core_resource(r,bound_id,0,__VA_ARGS__)
#define pw_core_resource_add_mem(r,...) pw_core_resource(r,add_mem,0,__VA_ARGS__)
#define pw_core_resource_remove_mem(r,...) pw_core_resource(r,remove_mem,0,__VA_ARGS__)
@@ -705,6 +706,7 @@ struct pw_resource {
#define pw_proxy_emit(o,m,v,...) spa_hook_list_call(&o->listener_list, struct pw_proxy_events, m, v, ##__VA_ARGS__)
#define pw_proxy_emit_destroy(p) pw_proxy_emit(p, destroy, 0)
+#define pw_proxy_emit_bound(p,g) pw_proxy_emit(p, bound, 0, g)
#define pw_proxy_emit_done(p,s) pw_proxy_emit(p, done, 0, s)
#define pw_proxy_emit_error(p,s,r,m) pw_proxy_emit(p, error, 0, s, r, m)
diff --git a/src/pipewire/proxy.h b/src/pipewire/proxy.h
index 1a25959e..6abea884 100644
--- a/src/pipewire/proxy.h
+++ b/src/pipewire/proxy.h
@@ -111,6 +111,9 @@ struct pw_proxy_events {
/** The proxy is destroyed */
void (*destroy) (void *data);
+ /** a proxy is bound to a global id */
+ void (*bound) (void *data, uint32_t global_id);
+
/** a reply to a sync method completed */
void (*done) (void *data, int seq);
diff --git a/src/pipewire/remote.c b/src/pipewire/remote.c
index bb715383..99d82aaa 100644
--- a/src/pipewire/remote.c
+++ b/src/pipewire/remote.c
@@ -145,6 +145,17 @@ static void core_event_remove_id(void *data, uint32_t id)
}
}
+static void core_event_bound_id(void *data, uint32_t id, uint32_t global_id)
+{
+ struct pw_remote *this = data;
+ struct pw_proxy *proxy;
+
+ pw_log_debug(NAME" %p: proxy %u bound %u", this, id, global_id);
+ if ((proxy = pw_map_lookup(&this->objects, id)) != NULL) {
+ pw_proxy_emit_bound(proxy, global_id);
+ }
+}
+
static void core_event_add_mem(void *data, uint32_t id, uint32_t type, int fd, uint32_t flags)
{
struct pw_remote *this = data;
@@ -173,6 +184,7 @@ static const struct pw_core_proxy_events core_events = {
.ping = core_event_ping,
.done = core_event_done,
.remove_id = core_event_remove_id,
+ .bound_id = core_event_bound_id,
.add_mem = core_event_add_mem,
.remove_mem = core_event_remove_mem,
};
diff --git a/src/pipewire/resource.c b/src/pipewire/resource.c
index 550b9554..87a9ca67 100644
--- a/src/pipewire/resource.c
+++ b/src/pipewire/resource.c
@@ -208,6 +208,18 @@ int pw_resource_ping(struct pw_resource *resource, int seq)
}
SPA_EXPORT
+int pw_resource_bound_id(struct pw_resource *resource, uint32_t global_id)
+{
+ struct pw_client *client = resource->client;
+
+ if (client->core_resource != NULL) {
+ pw_log_debug(NAME" %p: %u global_id:%u", resource, resource->id, global_id);
+ pw_core_resource_bound_id(client->core_resource, resource->id, global_id);
+ }
+ return 0;
+}
+
+SPA_EXPORT
void pw_resource_errorf(struct pw_resource *resource, int res, const char *error, ...)
{
va_list ap;
diff --git a/src/pipewire/resource.h b/src/pipewire/resource.h
index 1882fda1..b4e2eef5 100644
--- a/src/pipewire/resource.h
+++ b/src/pipewire/resource.h
@@ -121,6 +121,9 @@ void pw_resource_add_object_listener(struct pw_resource *resource,
* with the same \a sequence number in the return value. */
int pw_resource_ping(struct pw_resource *resource, int seq);
+/** Notify global id this resource is bound to */
+int pw_resource_bound_id(struct pw_resource *resource, uint32_t global_id);
+
/** Generate an error for a resource */
void pw_resource_error(struct pw_resource *resource, int res, const char *error);
void pw_resource_errorf(struct pw_resource *resource, int res, const char *error, ...) SPA_PRINTF_FUNC(3, 4);
diff --git a/src/tests/test-interfaces.c b/src/tests/test-interfaces.c
index f8f046c9..4062db9d 100644
--- a/src/tests/test-interfaces.c
+++ b/src/tests/test-interfaces.c
@@ -62,6 +62,7 @@ static void test_core_abi(void)
void (*ping) (void *object, uint32_t id, int seq);
void (*error) (void *object, uint32_t id, int seq, int res, const char *error);
void (*remove_id) (void *object, uint32_t id);
+ void (*bound_id) (void *object, uint32_t id, uint32_t global_id);
void (*add_mem) (void *object, uint32_t id, uint32_t type, int fd, uint32_t flags);
void (*remove_mem) (void *object, uint32_t id);
} events = { PW_VERSION_CORE_PROXY_EVENTS, };
@@ -84,6 +85,7 @@ static void test_core_abi(void)
TEST_FUNC(e, events, ping);
TEST_FUNC(e, events, error);
TEST_FUNC(e, events, remove_id);
+ TEST_FUNC(e, events, bound_id);
TEST_FUNC(e, events, add_mem);
TEST_FUNC(e, events, remove_mem);
spa_assert(PW_VERSION_CORE_PROXY_EVENTS == 0);