backends: Split monitor manager creation into create and setup

The monitor manager instance was created and setup in one step; at
construction. This is problematic if, in the future, the monitor manager
creation can fail, as the monitor manager is created quite late.

To make it possible to in the future fail creating a monitor manager,
create the instance very early when initiating the backend, then on
post init backend setup, "setup" the monitor manager state, i.e. read
the current state and setup the stage.

https://bugzilla.gnome.org/show_bug.cgi?id=785381
This commit is contained in:
Jonas Ådahl 2017-07-05 18:06:06 +08:00
parent 547ace3cf8
commit 518fb9fb5e
4 changed files with 55 additions and 46 deletions

View File

@ -355,15 +355,6 @@ on_device_removed (ClutterDeviceManager *device_manager,
}
}
static MetaMonitorManager *
create_monitor_manager (MetaBackend *backend)
{
if (g_getenv ("META_DUMMY_MONITORS"))
return g_object_new (META_TYPE_MONITOR_MANAGER_DUMMY, NULL);
return META_BACKEND_GET_CLASS (backend)->create_monitor_manager (backend);
}
static void
create_device_monitors (MetaBackend *backend,
ClutterDeviceManager *device_manager)
@ -441,7 +432,7 @@ meta_backend_real_post_init (MetaBackend *backend)
clutter_actor_realize (priv->stage);
META_BACKEND_GET_CLASS (backend)->select_stage_events (backend);
priv->monitor_manager = create_monitor_manager (backend);
meta_monitor_manager_setup (priv->monitor_manager);
meta_backend_sync_screen_size (backend);
@ -579,6 +570,15 @@ experimental_features_changed (MetaSettings *settings,
#endif /* HAVE_REMOTE_DESKTOP */
}
static MetaMonitorManager *
meta_backend_create_monitor_manager (MetaBackend *backend)
{
if (g_getenv ("META_DUMMY_MONITORS"))
return g_object_new (META_TYPE_MONITOR_MANAGER_DUMMY, NULL);
return META_BACKEND_GET_CLASS (backend)->create_monitor_manager (backend);
}
static MetaRenderer *
meta_backend_create_renderer (MetaBackend *backend,
GError **error)
@ -601,16 +601,18 @@ meta_backend_initable_init (GInitable *initable,
priv->egl = g_object_new (META_TYPE_EGL, NULL);
priv->orientation_manager = g_object_new (META_TYPE_ORIENTATION_MANAGER, NULL);
priv->renderer = meta_backend_create_renderer (backend, error);
if (!priv->renderer)
return FALSE;
priv->monitor_manager = meta_backend_create_monitor_manager (backend);
priv->cursor_tracker = g_object_new (META_TYPE_CURSOR_TRACKER, NULL);
priv->dnd = g_object_new (META_TYPE_DND, NULL);
priv->orientation_manager = g_object_new (META_TYPE_ORIENTATION_MANAGER, NULL);
return TRUE;
}

View File

@ -259,6 +259,8 @@ struct _MetaMonitorManagerClass
MetaLogicalMonitorLayoutMode (*get_default_layout_mode) (MetaMonitorManager *);
};
void meta_monitor_manager_setup (MetaMonitorManager *manager);
void meta_monitor_manager_rebuild (MetaMonitorManager *manager,
MetaMonitorsConfig *config);
void meta_monitor_manager_rebuild_derived (MetaMonitorManager *manager,

View File

@ -676,6 +676,20 @@ experimental_features_changed (MetaSettings *settings,
meta_settings_update_ui_scaling_factor (settings);
}
void
meta_monitor_manager_setup (MetaMonitorManager *manager)
{
manager->in_init = TRUE;
manager->config_manager = meta_monitor_config_manager_new (manager);
meta_monitor_manager_read_current_state (manager);
meta_monitor_manager_ensure_initial_config (manager);
manager->in_init = FALSE;
}
static void
meta_monitor_manager_constructed (GObject *object)
{
@ -707,17 +721,8 @@ meta_monitor_manager_constructed (GObject *object)
manager, 0);
manager->current_switch_config = META_MONITOR_SWITCH_CONFIG_UNKNOWN;
manager->in_init = TRUE;
manager->config_manager = meta_monitor_config_manager_new (manager);
meta_monitor_manager_read_current_state (manager);
meta_monitor_manager_ensure_initial_config (manager);
initialize_dbus_interface (manager);
manager->in_init = FALSE;
}
static void

View File

@ -798,31 +798,6 @@ meta_monitor_manager_kms_resume (MetaMonitorManagerKms *manager_kms)
handle_hotplug_event (manager);
}
static void
meta_monitor_manager_kms_init (MetaMonitorManagerKms *manager_kms)
{
MetaBackend *backend = meta_get_backend ();
MetaRenderer *renderer = meta_backend_get_renderer (backend);
MetaRendererNative *renderer_native = META_RENDERER_NATIVE (renderer);
GSource *source;
manager_kms->fd = meta_renderer_native_get_kms_fd (renderer_native);
drmSetClientCap (manager_kms->fd, DRM_CLIENT_CAP_UNIVERSAL_PLANES, 1);
const char *subsystems[2] = { "drm", NULL };
manager_kms->udev = g_udev_client_new (subsystems);
meta_monitor_manager_kms_connect_uevent_handler (manager_kms);
source = g_source_new (&kms_event_funcs, sizeof (MetaKmsSource));
manager_kms->source = (MetaKmsSource *) source;
manager_kms->source->fd_tag = g_source_add_unix_fd (source,
manager_kms->fd,
G_IO_IN | G_IO_ERR);
manager_kms->source->manager_kms = manager_kms;
g_source_attach (source, NULL);
}
static void
get_crtc_connectors (MetaMonitorManager *manager,
MetaCrtc *crtc,
@ -1122,6 +1097,31 @@ meta_monitor_manager_kms_finalize (GObject *object)
G_OBJECT_CLASS (meta_monitor_manager_kms_parent_class)->finalize (object);
}
static void
meta_monitor_manager_kms_init (MetaMonitorManagerKms *manager_kms)
{
MetaBackend *backend = meta_get_backend ();
MetaRenderer *renderer = meta_backend_get_renderer (backend);
MetaRendererNative *renderer_native = META_RENDERER_NATIVE (renderer);
GSource *source;
manager_kms->fd = meta_renderer_native_get_kms_fd (renderer_native);
drmSetClientCap (manager_kms->fd, DRM_CLIENT_CAP_UNIVERSAL_PLANES, 1);
const char *subsystems[2] = { "drm", NULL };
manager_kms->udev = g_udev_client_new (subsystems);
meta_monitor_manager_kms_connect_uevent_handler (manager_kms);
source = g_source_new (&kms_event_funcs, sizeof (MetaKmsSource));
manager_kms->source = (MetaKmsSource *) source;
manager_kms->source->fd_tag = g_source_add_unix_fd (source,
manager_kms->fd,
G_IO_IN | G_IO_ERR);
manager_kms->source->manager_kms = manager_kms;
g_source_attach (source, NULL);
}
static void
meta_monitor_manager_kms_class_init (MetaMonitorManagerKmsClass *klass)
{