[PATCH weston v6 13/73] libweston: add compositor list of heads

Pekka Paalanen ppaalanen at gmail.com
Fri Feb 16 14:56:58 UTC 2018


From: Pekka Paalanen <pekka.paalanen at collabora.co.uk>

weston_compositor needs to maintain a list of all available heads, so
that a compositor can pick and choose which heads to take into or out of
use at arbitrary times. The heads may be on or off, and connected or
disconnected.

Signed-off-by: Pekka Paalanen <pekka.paalanen at collabora.co.uk>
Reviewed-by: Derek Foreman <derekf at osg.samsung.com>
---
 libweston/compositor.c | 75 ++++++++++++++++++++++++++++++++++++++++++++++++++
 libweston/compositor.h |  8 ++++++
 2 files changed, 83 insertions(+)

diff --git a/libweston/compositor.c b/libweston/compositor.c
index d1cfc109..cc71a18e 100644
--- a/libweston/compositor.c
+++ b/libweston/compositor.c
@@ -4433,11 +4433,79 @@ weston_head_init(struct weston_head *head, const char *name)
 	 */
 	memset(head, 0, sizeof *head);
 
+	wl_list_init(&head->compositor_link);
 	wl_list_init(&head->output_link);
 	wl_list_init(&head->resource_list);
 	head->name = strdup(name);
 }
 
+/** Register a new head
+ *
+ * \param compositor The compositor.
+ * \param head The head to register, must not be already registered.
+ *
+ * This signals the core that a new head has become available.
+ *
+ * \memberof weston_compositor
+ * \internal
+ */
+static void
+weston_compositor_add_head(struct weston_compositor *compositor,
+			   struct weston_head *head)
+{
+	assert(wl_list_empty(&head->compositor_link));
+	assert(head->name);
+
+	wl_list_insert(compositor->head_list.prev, &head->compositor_link);
+	head->compositor = compositor;
+}
+
+/** Iterate over available heads
+ *
+ * \param compositor The compositor.
+ * \param item The iterator, or NULL for start.
+ * \return The next available head in the list.
+ *
+ * Returns all available heads, regardless of being connected or enabled.
+ *
+ * You can iterate over all heads as follows:
+ * \code
+ * struct weston_head *head = NULL;
+ *
+ * while ((head = weston_compositor_iterate_heads(compositor, head))) {
+ * 	...
+ * }
+ * \endcode
+ *
+ *  If you cause \c iter to be removed from the list, you cannot use it to
+ * continue iterating. Removing any other item is safe.
+ *
+ * \memberof weston_compositor
+ */
+WL_EXPORT struct weston_head *
+weston_compositor_iterate_heads(struct weston_compositor *compositor,
+				struct weston_head *iter)
+{
+	struct wl_list *list = &compositor->head_list;
+	struct wl_list *node;
+
+	assert(compositor);
+	assert(!iter || iter->compositor == compositor);
+
+	if (iter)
+		node = iter->compositor_link.next;
+	else
+		node = list->next;
+
+	assert(node);
+	assert(!iter || node != &iter->compositor_link);
+
+	if (node == list)
+		return NULL;
+
+	return container_of(node, struct weston_head, compositor_link);
+}
+
 /** Attach a head to an inactive output
  *
  * \param output The output to attach to.
@@ -4512,6 +4580,8 @@ weston_head_release(struct weston_head *head)
 	free(head->model);
 	free(head->serial_number);
 	free(head->name);
+
+	wl_list_remove(&head->compositor_link);
 }
 
 /** Store monitor make, model and serial number
@@ -5084,6 +5154,7 @@ weston_output_init(struct weston_output *output,
 
 	weston_head_init(&output->head, name);
 	weston_head_set_connection_status(&output->head, true);
+	weston_compositor_add_head(compositor, &output->head);
 
 	/* Add some (in)sane defaults which can be used
 	 * for checking if an output was properly configured
@@ -5707,6 +5778,7 @@ weston_compositor_create(struct wl_display *display, void *user_data)
 	wl_list_init(&ec->seat_list);
 	wl_list_init(&ec->pending_output_list);
 	wl_list_init(&ec->output_list);
+	wl_list_init(&ec->head_list);
 	wl_list_init(&ec->key_binding_list);
 	wl_list_init(&ec->modifier_binding_list);
 	wl_list_init(&ec->button_binding_list);
@@ -5982,6 +6054,9 @@ weston_compositor_destroy(struct weston_compositor *compositor)
 	if (compositor->backend)
 		compositor->backend->destroy(compositor);
 
+	/* The backend is responsible for destroying the heads. */
+	assert(wl_list_empty(&compositor->head_list));
+
 	weston_plugin_api_destroy_list(compositor);
 
 	free(compositor);
diff --git a/libweston/compositor.h b/libweston/compositor.h
index bad73599..7c95b454 100644
--- a/libweston/compositor.h
+++ b/libweston/compositor.h
@@ -153,6 +153,9 @@ enum dpms_enum {
  * (windowed nested backends).
  */
 struct weston_head {
+	struct weston_compositor *compositor;	/**< owning compositor */
+	struct wl_list compositor_link;	/**< in weston_compositor::head_list */
+
 	struct weston_output *output;	/**< the output driving this head */
 	struct wl_list output_link;	/**< in weston_output::head_list */
 
@@ -914,6 +917,7 @@ struct weston_compositor {
 
 	struct wl_list pending_output_list;
 	struct wl_list output_list;
+	struct wl_list head_list;	/* struct weston_head::compositor_link */
 	struct wl_list seat_list;
 	struct wl_list layer_list;	/* struct weston_layer::link */
 	struct wl_list view_list;	/* struct weston_view::link */
@@ -1977,6 +1981,10 @@ weston_head_is_connected(struct weston_head *head);
 bool
 weston_head_is_enabled(struct weston_head *head);
 
+struct weston_head *
+weston_compositor_iterate_heads(struct weston_compositor *compositor,
+				struct weston_head *iter);
+
 void
 weston_output_set_scale(struct weston_output *output,
 			int32_t scale);
-- 
2.13.6



More information about the wayland-devel mailing list