mirror of
https://github.com/brl/mutter.git
synced 2024-12-23 11:32:04 +00:00
gpu/kms: Init global mode list from MetaKmsConnectors
Instead of iterating over the available drmModeConnector objects to construct a GPU wide mode list, use the state managed by MetaKmsConnector. This also removes the last user of drmModeRes from MetaGpuKms. https://gitlab.gnome.org/GNOME/mutter/issues/548 https://gitlab.gnome.org/GNOME/mutter/merge_requests/525
This commit is contained in:
parent
f2d9a11013
commit
aba689312f
@ -72,9 +72,6 @@ struct _MetaGpuKms
|
|||||||
|
|
||||||
clockid_t clock_id;
|
clockid_t clock_id;
|
||||||
|
|
||||||
drmModeConnector **connectors;
|
|
||||||
unsigned int n_connectors;
|
|
||||||
|
|
||||||
gboolean resources_init_failed_before;
|
gboolean resources_init_failed_before;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -445,17 +442,6 @@ meta_gpu_kms_is_platform_device (MetaGpuKms *gpu_kms)
|
|||||||
return !!(flags & META_KMS_DEVICE_FLAG_PLATFORM_DEVICE);
|
return !!(flags & META_KMS_DEVICE_FLAG_PLATFORM_DEVICE);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
|
||||||
free_resources (MetaGpuKms *gpu_kms)
|
|
||||||
{
|
|
||||||
unsigned i;
|
|
||||||
|
|
||||||
for (i = 0; i < gpu_kms->n_connectors; i++)
|
|
||||||
drmModeFreeConnector (gpu_kms->connectors[i]);
|
|
||||||
|
|
||||||
g_free (gpu_kms->connectors);
|
|
||||||
}
|
|
||||||
|
|
||||||
static int
|
static int
|
||||||
compare_outputs (gconstpointer one,
|
compare_outputs (gconstpointer one,
|
||||||
gconstpointer two)
|
gconstpointer two)
|
||||||
@ -616,51 +602,32 @@ setup_output_clones (MetaGpu *gpu)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
init_connectors (MetaGpuKms *gpu_kms,
|
init_modes (MetaGpuKms *gpu_kms)
|
||||||
drmModeRes *resources)
|
|
||||||
{
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
gpu_kms->n_connectors = resources->count_connectors;
|
|
||||||
gpu_kms->connectors = g_new (drmModeConnector *, gpu_kms->n_connectors);
|
|
||||||
for (i = 0; i < gpu_kms->n_connectors; i++)
|
|
||||||
{
|
|
||||||
drmModeConnector *drm_connector;
|
|
||||||
|
|
||||||
drm_connector = drmModeGetConnector (gpu_kms->fd,
|
|
||||||
resources->connectors[i]);
|
|
||||||
gpu_kms->connectors[i] = drm_connector;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
init_modes (MetaGpuKms *gpu_kms,
|
|
||||||
drmModeRes *resources)
|
|
||||||
{
|
{
|
||||||
MetaGpu *gpu = META_GPU (gpu_kms);
|
MetaGpu *gpu = META_GPU (gpu_kms);
|
||||||
GHashTable *modes_table;
|
GHashTable *modes_table;
|
||||||
|
GList *l;
|
||||||
GList *modes;
|
GList *modes;
|
||||||
GHashTableIter iter;
|
GHashTableIter iter;
|
||||||
drmModeModeInfo *drm_mode;
|
drmModeModeInfo *drm_mode;
|
||||||
unsigned int i;
|
int i;
|
||||||
long mode_id;
|
long mode_id;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Gather all modes on all connected connectors.
|
* Gather all modes on all connected connectors.
|
||||||
*/
|
*/
|
||||||
modes_table = g_hash_table_new (drm_mode_hash, (GEqualFunc) meta_drm_mode_equal);
|
modes_table = g_hash_table_new (drm_mode_hash, (GEqualFunc) meta_drm_mode_equal);
|
||||||
for (i = 0; i < gpu_kms->n_connectors; i++)
|
for (l = meta_kms_device_get_connectors (gpu_kms->kms_device); l; l = l->next)
|
||||||
{
|
{
|
||||||
drmModeConnector *drm_connector;
|
MetaKmsConnector *kms_connector = l->data;
|
||||||
|
const MetaKmsConnectorState *state;
|
||||||
|
|
||||||
drm_connector = gpu_kms->connectors[i];
|
state = meta_kms_connector_get_current_state (kms_connector);
|
||||||
if (drm_connector && drm_connector->connection == DRM_MODE_CONNECTED)
|
if (!state)
|
||||||
{
|
continue;
|
||||||
unsigned int j;
|
|
||||||
|
|
||||||
for (j = 0; j < (unsigned int) drm_connector->count_modes; j++)
|
for (i = 0; i < state->n_modes; i++)
|
||||||
g_hash_table_add (modes_table, &drm_connector->modes[j]);
|
g_hash_table_add (modes_table, &state->modes[i]);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
modes = NULL;
|
modes = NULL;
|
||||||
@ -742,23 +709,23 @@ init_outputs (MetaGpuKms *gpu_kms)
|
|||||||
MetaGpu *gpu = META_GPU (gpu_kms);
|
MetaGpu *gpu = META_GPU (gpu_kms);
|
||||||
GList *old_outputs;
|
GList *old_outputs;
|
||||||
GList *outputs;
|
GList *outputs;
|
||||||
unsigned int i;
|
|
||||||
GList *l;
|
GList *l;
|
||||||
|
|
||||||
old_outputs = meta_gpu_get_outputs (gpu);
|
old_outputs = meta_gpu_get_outputs (gpu);
|
||||||
|
|
||||||
outputs = NULL;
|
outputs = NULL;
|
||||||
|
|
||||||
i = 0;
|
|
||||||
for (l = meta_kms_device_get_connectors (gpu_kms->kms_device); l; l = l->next)
|
for (l = meta_kms_device_get_connectors (gpu_kms->kms_device); l; l = l->next)
|
||||||
{
|
{
|
||||||
MetaKmsConnector *kms_connector = l->data;
|
MetaKmsConnector *kms_connector = l->data;
|
||||||
MetaOutput *output;
|
MetaOutput *output;
|
||||||
MetaOutput *old_output;
|
MetaOutput *old_output;
|
||||||
GError *error = NULL;
|
GError *error = NULL;
|
||||||
|
uint32_t connector_id;
|
||||||
drmModeConnector *connector;
|
drmModeConnector *connector;
|
||||||
|
|
||||||
connector = gpu_kms->connectors[i++];
|
connector_id = meta_kms_connector_get_id (kms_connector);
|
||||||
|
connector = drmModeGetConnector (gpu_kms->fd, connector_id);
|
||||||
|
|
||||||
if (!connector || connector->connection != DRM_MODE_CONNECTED)
|
if (!connector || connector->connection != DRM_MODE_CONNECTED)
|
||||||
continue;
|
continue;
|
||||||
@ -790,88 +757,40 @@ init_outputs (MetaGpuKms *gpu_kms)
|
|||||||
setup_output_clones (gpu);
|
setup_output_clones (gpu);
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
|
||||||
meta_kms_resources_init (MetaKmsResources *resources,
|
|
||||||
int fd,
|
|
||||||
GError **error)
|
|
||||||
|
|
||||||
{
|
|
||||||
drmModeRes *drm_resources;
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
drm_resources = drmModeGetResources (fd);
|
|
||||||
|
|
||||||
if (!drm_resources)
|
|
||||||
{
|
|
||||||
g_set_error (error,
|
|
||||||
G_IO_ERROR,
|
|
||||||
G_IO_ERROR_FAILED,
|
|
||||||
"Calling drmModeGetResources() failed");
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
resources->resources = drm_resources;
|
|
||||||
|
|
||||||
resources->n_encoders = (unsigned int) drm_resources->count_encoders;
|
|
||||||
resources->encoders = g_new (drmModeEncoder *, resources->n_encoders);
|
|
||||||
for (i = 0; i < resources->n_encoders; i++)
|
|
||||||
resources->encoders[i] = drmModeGetEncoder (fd, drm_resources->encoders[i]);
|
|
||||||
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
meta_kms_resources_release (MetaKmsResources *resources)
|
|
||||||
{
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
for (i = 0; i < resources->n_encoders; i++)
|
|
||||||
drmModeFreeEncoder (resources->encoders[i]);
|
|
||||||
g_free (resources->encoders);
|
|
||||||
|
|
||||||
g_clear_pointer (&resources->resources, drmModeFreeResources);
|
|
||||||
}
|
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
meta_gpu_kms_read_current (MetaGpu *gpu,
|
meta_gpu_kms_read_current (MetaGpu *gpu,
|
||||||
GError **error)
|
GError **error)
|
||||||
{
|
{
|
||||||
MetaGpuKms *gpu_kms = META_GPU_KMS (gpu);
|
MetaGpuKms *gpu_kms = META_GPU_KMS (gpu);
|
||||||
MetaKmsResources resources;
|
|
||||||
g_autoptr (GError) local_error = NULL;
|
|
||||||
|
|
||||||
if (!meta_kms_resources_init (&resources, gpu_kms->fd, &local_error))
|
|
||||||
{
|
|
||||||
if (!gpu_kms->resources_init_failed_before)
|
|
||||||
{
|
|
||||||
g_warning ("meta_kms_resources_init failed: %s, assuming we have no outputs",
|
|
||||||
local_error->message);
|
|
||||||
gpu_kms->resources_init_failed_before = TRUE;
|
|
||||||
}
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Note: we must not free the public structures (output, crtc, monitor
|
/* Note: we must not free the public structures (output, crtc, monitor
|
||||||
mode and monitor info) here, they must be kept alive until the API
|
mode and monitor info) here, they must be kept alive until the API
|
||||||
users are done with them after we emit monitors-changed, and thus
|
users are done with them after we emit monitors-changed, and thus
|
||||||
are freed by the platform-independent layer. */
|
are freed by the platform-independent layer. */
|
||||||
free_resources (gpu_kms);
|
|
||||||
|
|
||||||
init_connectors (gpu_kms, resources.resources);
|
init_modes (gpu_kms);
|
||||||
init_modes (gpu_kms, resources.resources);
|
|
||||||
init_crtcs (gpu_kms);
|
init_crtcs (gpu_kms);
|
||||||
init_outputs (gpu_kms);
|
init_outputs (gpu_kms);
|
||||||
init_frame_clock (gpu_kms);
|
init_frame_clock (gpu_kms);
|
||||||
|
|
||||||
meta_kms_resources_release (&resources);
|
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
gboolean
|
gboolean
|
||||||
meta_gpu_kms_can_have_outputs (MetaGpuKms *gpu_kms)
|
meta_gpu_kms_can_have_outputs (MetaGpuKms *gpu_kms)
|
||||||
{
|
{
|
||||||
return gpu_kms->n_connectors > 0;
|
GList *l;
|
||||||
|
int n_connected_connectors = 0;
|
||||||
|
|
||||||
|
for (l = meta_kms_device_get_connectors (gpu_kms->kms_device); l; l = l->next)
|
||||||
|
{
|
||||||
|
MetaKmsConnector *kms_connector = l->data;
|
||||||
|
|
||||||
|
if (meta_kms_connector_get_current_state (kms_connector))
|
||||||
|
n_connected_connectors++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return n_connected_connectors > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
MetaGpuKms *
|
MetaGpuKms *
|
||||||
@ -915,8 +834,6 @@ meta_gpu_kms_finalize (GObject *object)
|
|||||||
|
|
||||||
g_source_destroy (gpu_kms->source);
|
g_source_destroy (gpu_kms->source);
|
||||||
|
|
||||||
free_resources (gpu_kms);
|
|
||||||
|
|
||||||
G_OBJECT_CLASS (meta_gpu_kms_parent_class)->finalize (object);
|
G_OBJECT_CLASS (meta_gpu_kms_parent_class)->finalize (object);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -35,13 +35,6 @@ G_DECLARE_FINAL_TYPE (MetaGpuKms, meta_gpu_kms, META, GPU_KMS, MetaGpu)
|
|||||||
|
|
||||||
typedef struct _MetaGpuKmsFlipClosureContainer MetaGpuKmsFlipClosureContainer;
|
typedef struct _MetaGpuKmsFlipClosureContainer MetaGpuKmsFlipClosureContainer;
|
||||||
|
|
||||||
typedef struct _MetaKmsResources
|
|
||||||
{
|
|
||||||
drmModeRes *resources;
|
|
||||||
drmModeEncoder **encoders;
|
|
||||||
unsigned int n_encoders;
|
|
||||||
} MetaKmsResources;
|
|
||||||
|
|
||||||
typedef void (*MetaKmsFlipCallback) (void *user_data);
|
typedef void (*MetaKmsFlipCallback) (void *user_data);
|
||||||
|
|
||||||
MetaGpuKms * meta_gpu_kms_new (MetaBackendNative *backend_native,
|
MetaGpuKms * meta_gpu_kms_new (MetaBackendNative *backend_native,
|
||||||
|
Loading…
Reference in New Issue
Block a user