[RFC PATCH wayland v2 2/4] store wl_object in objects maps instead of proxy

Marek Chalupa mchqwerty at gmail.com
Fri Apr 10 06:45:39 PDT 2015


We can get the proxy/resource by (wl_)container_of macro where needed.
Storing bare wl_object allows us to store even some objects
that do not have assigned proxy or resource and thus make some
reasoning about objects on lower level (like when we demarshal
the connection)

Signed-off-by: Marek Chalupa <mchqwerty at gmail.com>
---
 src/wayland-client.c | 18 ++++++++++++------
 src/wayland-server.c | 26 ++++++++++++++++++++------
 2 files changed, 32 insertions(+), 12 deletions(-)

diff --git a/src/wayland-client.c b/src/wayland-client.c
index ff2b61a..92256a1 100644
--- a/src/wayland-client.c
+++ b/src/wayland-client.c
@@ -103,6 +103,13 @@ struct wl_display {
 
 static int debug_client = 0;
 
+static struct wl_proxy *
+wl_map_lookup_proxy(struct wl_map *objects, uint32_t id)
+{
+	struct wl_object *object = wl_map_lookup(objects, id);
+	return container_of(object, struct wl_proxy, object);
+}
+
 /**
  * This helper function wakes up all threads that are
  * waiting for display->reader_cond (i. e. when reading is done,
@@ -331,7 +338,7 @@ proxy_create(struct wl_proxy *factory, const struct wl_interface *interface)
 	proxy->queue = factory->queue;
 	proxy->refcount = 1;
 
-	proxy->object.id = wl_map_insert_new(&display->objects, 0, proxy);
+	proxy->object.id = wl_map_insert_new(&display->objects, 0, &proxy->object);
 
 	return proxy;
 }
@@ -388,7 +395,7 @@ wl_proxy_create_for_id(struct wl_proxy *factory,
 	proxy->queue = factory->queue;
 	proxy->refcount = 1;
 
-	wl_map_insert_at(&display->objects, 0, id, proxy);
+	wl_map_insert_at(&display->objects, 0, id, &proxy->object);
 
 	return proxy;
 }
@@ -716,8 +723,7 @@ display_handle_delete_id(void *data, struct wl_display *display, uint32_t id)
 
 	pthread_mutex_lock(&display->mutex);
 
-	proxy = wl_map_lookup(&display->objects, id);
-
+	proxy = wl_map_lookup_proxy(&display->objects, id);
 	if (!proxy)
 		wl_log("error: received delete_id for unknown id (%u)\n", id);
 
@@ -828,7 +834,7 @@ wl_display_connect_to_fd(int fd)
 
 	display->proxy.object.interface = &wl_display_interface;
 	display->proxy.object.id =
-		wl_map_insert_new(&display->objects, 0, display);
+		wl_map_insert_new(&display->objects, 0, &display->proxy.object);
 	display->proxy.object.flags = 0;
 	display->proxy.display = display;
 	display->proxy.object.implementation = (void(**)(void)) &display_listener;
@@ -1079,7 +1085,7 @@ queue_event(struct wl_display *display, int len)
 	if (len < size)
 		return 0;
 
-	proxy = wl_map_lookup(&display->objects, id);
+	proxy = wl_map_lookup_proxy(&display->objects, id);
 	if (proxy == WL_ZOMBIE_OBJECT) {
 		wl_connection_consume(display->connection, size);
 		return size;
diff --git a/src/wayland-server.c b/src/wayland-server.c
index ecbae68..d34e07c 100644
--- a/src/wayland-server.c
+++ b/src/wayland-server.c
@@ -120,6 +120,13 @@ struct wl_resource {
 
 static int debug_server = 0;
 
+static struct wl_resource *
+wl_map_lookup_resource(struct wl_map *objects, uint32_t id)
+{
+	struct wl_object *object = wl_map_lookup(objects, id);
+	return container_of(object, struct wl_resource, object);
+}
+
 WL_EXPORT void
 wl_resource_post_event_array(struct wl_resource *resource, uint32_t opcode,
 			     union wl_argument *args)
@@ -273,7 +280,7 @@ wl_client_connection_data(int fd, uint32_t mask, void *data)
 		if (len < size)
 			break;
 
-		resource = wl_map_lookup(&client->objects, p[0]);
+		resource = wl_map_lookup_resource(&client->objects, p[0]);
 		resource_flags = wl_map_lookup_flags(&client->objects, p[0]);
 		if (resource == NULL) {
 			wl_resource_post_error(client->display_resource,
@@ -502,7 +509,7 @@ wl_client_get_credentials(struct wl_client *client,
 WL_EXPORT struct wl_resource *
 wl_client_get_object(struct wl_client *client, uint32_t id)
 {
-	return wl_map_lookup(&client->objects, id);
+	return wl_map_lookup_resource(&client->objects, id);
 }
 
 WL_EXPORT void
@@ -536,6 +543,13 @@ destroy_resource(void *element, void *data)
 		free(resource);
 }
 
+static inline void
+destroy_resource_for_object(void *element, void *data)
+{
+	/* element is of type wl_object * */
+	destroy_resource(container_of(element, struct wl_resource, object), data);
+}
+
 WL_EXPORT void
 wl_resource_destroy(struct wl_resource *resource)
 {
@@ -668,7 +682,7 @@ wl_client_destroy(struct wl_client *client)
 	wl_signal_emit(&client->destroy_signal, client);
 
 	wl_client_flush(client);
-	wl_map_for_each(&client->objects, destroy_resource, &serial);
+	wl_map_for_each(&client->objects, destroy_resource_for_object, &serial);
 	wl_map_release(&client->objects);
 	wl_event_source_remove(client->source);
 	close(wl_connection_destroy(client->connection));
@@ -1314,7 +1328,7 @@ wl_resource_create(struct wl_client *client,
 	resource->version = version;
 	resource->dispatcher = NULL;
 
-	if (wl_map_insert_at(&client->objects, 0, id, resource) < 0) {
+	if (wl_map_insert_at(&client->objects, 0, id, &resource->object) < 0) {
 		wl_resource_post_error(client->display_resource,
 				       WL_DISPLAY_ERROR_INVALID_OBJECT,
 				       "invalid new id %d", id);
@@ -1396,9 +1410,9 @@ wl_client_add_resource(struct wl_client *client,
 	if (resource->object.id == 0) {
 		resource->object.id =
 			wl_map_insert_new(&client->objects,
-					  WL_MAP_ENTRY_LEGACY, resource);
+					  WL_MAP_ENTRY_LEGACY, &resource->object);
 	} else if (wl_map_insert_at(&client->objects, WL_MAP_ENTRY_LEGACY,
-				  resource->object.id, resource) < 0) {
+				  resource->object.id, &resource->object) < 0) {
 		wl_resource_post_error(client->display_resource,
 				       WL_DISPLAY_ERROR_INVALID_OBJECT,
 				       "invalid new id %d",
-- 
2.1.0



More information about the wayland-devel mailing list