]> git.ipfire.org Git - thirdparty/plymouth.git/commitdiff
drm: Store and keep all the outputs in the backend
authorHans de Goede <hdegoede@redhat.com>
Tue, 15 Jan 2019 07:58:45 +0000 (08:58 +0100)
committerHans de Goede <hdegoede@redhat.com>
Wed, 16 Jan 2019 15:56:52 +0000 (16:56 +0100)
Put all outputs in the outputs array instead of just the connected ones
and store the outputs array and the controller_id-to-head hashtable in the
backend object instead of temporarily allocating them during enumeration.

Also add new heads to the heads list and to the controller_id-to-head
hashtable in ply_renderer_head_new where this really belongs. This
allows nicely balancing these 2 with removing the head from the list
and hash_table in the ply_renderer_head_remove function which is added
in a follow-up commit.

This is a preparation patch for adding support for hotplugging
monitors while plymouth is running.

Signed-off-by: Hans de Goede <hdegoede@redhat.com>
src/plugins/renderers/drm/plugin.c

index da56fe48e02fba3776c1774a8ebd9b1645ff3aa0..a66cd675bef0b8004680424037bc59527ca1a994 100644 (file)
@@ -138,10 +138,14 @@ struct _ply_renderer_backend
 
         ply_renderer_input_source_t      input_source;
         ply_list_t                      *heads;
-        ply_hashtable_t                 *heads_by_connector_id;
+        ply_hashtable_t                 *heads_by_controller_id;
 
         ply_hashtable_t                 *output_buffers;
 
+        ply_output_t                    *outputs;
+        int                              outputs_len;
+        int                              connected_count;
+
         int32_t                          dither_red;
         int32_t                          dither_green;
         int32_t                          dither_blue;
@@ -546,6 +550,10 @@ ply_renderer_head_new (ply_renderer_backend_t     *backend,
                 backend->panel_scale = output->device_scale;
         }
 
+        ply_list_append_data (backend->heads, head);
+        ply_hashtable_insert (backend->heads_by_controller_id,
+                              (void *) (intptr_t) output->controller_id,
+                              head);
         return head;
 }
 
@@ -808,6 +816,7 @@ create_backend (const char     *device_name,
         backend->requires_explicit_flushing = true;
         backend->output_buffers = ply_hashtable_new (ply_hashtable_direct_hash,
                                                      ply_hashtable_direct_compare);
+        backend->heads_by_controller_id = ply_hashtable_new (NULL, NULL);
         backend->use_preferred_mode = should_use_preferred_mode ();
 
         return backend;
@@ -827,9 +836,11 @@ destroy_backend (ply_renderer_backend_t *backend)
 
         free (backend->device_name);
         ply_hashtable_free (backend->output_buffers);
+        ply_hashtable_free (backend->heads_by_controller_id);
 
         drmModeFreeResources (backend->resources);
 
+        free (backend->outputs);
         free (backend);
 }
 
@@ -1194,9 +1205,9 @@ setup_outputs (ply_renderer_backend_t *backend,
         best_count = count_setup_controllers (outputs, outputs_len);
         best_outputs = outputs;
 
-        for (i = 0; i < outputs_len && best_count < outputs_len; i++) {
-                /* Already assigned? */
-                if (outputs[i].controller_id)
+        for (i = 0; i < outputs_len && best_count < backend->connected_count; i++) {
+                /* Not connected or already assigned? */
+                if (!outputs[i].connected || outputs[i].controller_id)
                         continue;
 
                 /* Assign controller for connector i */
@@ -1238,24 +1249,21 @@ setup_outputs (ply_renderer_backend_t *backend,
 static bool
 create_heads_for_active_connectors (ply_renderer_backend_t *backend)
 {
-        ply_hashtable_t *heads_by_controller_id;
+        int i, j, number_of_setup_outputs, outputs_len;
         ply_output_t *outputs;
-        int i, j, found, number_of_setup_outputs, outputs_len;
-
-        heads_by_controller_id = ply_hashtable_new (NULL, NULL);
 
         outputs = calloc (backend->resources->count_connectors, sizeof(*outputs));
+        outputs_len = backend->resources->count_connectors;
 
         /* Step 1:
          * Build a list of connected outputs and get pre-configured controllers.
          */
-        found = 0;
-        for (i = 0; i < backend->resources->count_connectors; i++) {
-                get_output_info (backend, backend->resources->connectors[i], &outputs[found]);
-                if (outputs[found].connected)
-                        found++;
+        backend->connected_count = 0;
+        for (i = 0; i < outputs_len; i++) {
+                get_output_info (backend, backend->resources->connectors[i], &outputs[i]);
+                if (outputs[i].connected)
+                        backend->connected_count++;
         }
-        outputs_len = found; /* outputs now contains found valid entries */
 
         /* Step 2:
          * Drop controllers for clones for which we've picked different modes.
@@ -1282,13 +1290,13 @@ create_heads_for_active_connectors (ply_renderer_backend_t *backend)
          * Assign controllers to outputs without a controller
          */
         number_of_setup_outputs = count_setup_controllers (outputs, outputs_len);
-        if (number_of_setup_outputs != outputs_len) {
+        if (number_of_setup_outputs != backend->connected_count) {
                 /* First try, try to assign controllers to outputs without one */
                 ply_trace ("Some outputs don't have controllers, picking controllers");
                 outputs = setup_outputs (backend, outputs, outputs_len);
                 number_of_setup_outputs = count_setup_controllers (outputs, outputs_len);
         }
-        if (number_of_setup_outputs != outputs_len) {
+        if (number_of_setup_outputs != backend->connected_count) {
                 /* Second try, re-assing controller for all outputs */
                 ply_trace ("Some outputs still don't have controllers, re-assigning controllers for all outputs");
                 for (i = 0; i < outputs_len; i++)
@@ -1309,6 +1317,9 @@ create_heads_for_active_connectors (ply_renderer_backend_t *backend)
                 uint32_t console_buffer_id;
                 int gamma_size;
 
+                if (!outputs[i].controller_id)
+                        continue;
+
                 controller = drmModeGetCrtc (backend->device_fd, outputs[i].controller_id);
                 if (!controller)
                         continue;
@@ -1318,27 +1329,21 @@ create_heads_for_active_connectors (ply_renderer_backend_t *backend)
                 gamma_size = controller->gamma_size;
                 drmModeFreeCrtc (controller);
 
-                head = ply_hashtable_lookup (heads_by_controller_id,
+                head = ply_hashtable_lookup (backend->heads_by_controller_id,
                                              (void *) (intptr_t) controller_id);
 
                 if (head == NULL) {
                         head = ply_renderer_head_new (backend, &outputs[i],
                                                       console_buffer_id,
                                                       gamma_size);
-
-                        ply_list_append_data (backend->heads, head);
-
-                        ply_hashtable_insert (heads_by_controller_id,
-                                              (void *) (intptr_t) controller_id,
-                                              head);
                 } else {
                         if (!ply_renderer_head_add_connector (head, &outputs[i]))
                                 ply_trace ("couldn't connect monitor to existing head");
                 }
         }
 
-        ply_hashtable_free (heads_by_controller_id);
-        free (outputs);
+        backend->outputs_len = outputs_len;
+        backend->outputs = outputs;
 
         return ply_list_get_length (backend->heads) > 0;
 }