kms: Have the device impl open device files themself

This changes the way the KMS backends load; if we're headless, we always
use the dummy one and fail otherwise; in other cases, we first try the
atomic backend, and if that fails, fall back on the simple one.

The aim for this is to have the impl device open and close the device
when needed, using the device pool directly.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1828>
This commit is contained in:
Jonas Ådahl 2021-04-06 12:14:24 +02:00
parent f3457b678c
commit e6421dc5da
6 changed files with 289 additions and 213 deletions

View File

@ -230,7 +230,6 @@ meta_kms_device_add_fake_plane_in_impl (MetaKmsDevice *device,
typedef struct _CreateImplDeviceData
{
MetaKmsDevice *device;
MetaDeviceFile *device_file;
const char *path;
MetaKmsDeviceFlag flags;
@ -245,170 +244,70 @@ typedef struct _CreateImplDeviceData
char *out_path;
} CreateImplDeviceData;
static gboolean
is_atomic_allowed (const char *driver_name)
static const char *
impl_device_type_to_string (GType type)
{
const char *atomic_driver_deny_list[] = {
"qxl",
"vmwgfx",
"vboxvideo",
"nvidia-drm",
NULL,
};
return !g_strv_contains (atomic_driver_deny_list, driver_name);
}
static gboolean
get_driver_info (int fd,
char **name,
char **description)
{
drmVersion *drm_version;
drm_version = drmGetVersion (fd);
if (!drm_version)
return FALSE;
*name = g_strndup (drm_version->name,
drm_version->name_len);
*description = g_strndup (drm_version->desc,
drm_version->desc_len);
drmFreeVersion (drm_version);
return TRUE;
if (type == META_TYPE_KMS_IMPL_DEVICE_ATOMIC)
return "atomic modesetting";
else if (type == META_TYPE_KMS_IMPL_DEVICE_SIMPLE)
return "legacy modesetting";
else if (type == META_TYPE_KMS_IMPL_DEVICE_DUMMY)
return "no modesetting";
g_assert_not_reached();
}
static MetaKmsImplDevice *
meta_create_kms_impl_device (MetaKmsDevice *device,
MetaKmsImpl *impl,
MetaDeviceFile *device_file,
const char *path,
MetaKmsDeviceFlag flags,
GError **error)
{
GType impl_device_type;
gboolean supports_atomic_mode_setting;
g_autofree char *driver_name = NULL;
g_autofree char *driver_description = NULL;
const char *atomic_kms_enable_env;
int fd;
g_autoptr (MetaDeviceFile) impl_device_file = NULL;
MetaKmsImplDevice *impl_device;
meta_assert_in_kms_impl (meta_kms_impl_get_kms (impl));
fd = meta_device_file_get_fd (device_file);
if (!get_driver_info (fd, &driver_name, &driver_description))
{
driver_name = g_strdup ("unknown");
driver_description = g_strdup ("Unknown");
}
atomic_kms_enable_env = getenv ("MUTTER_DEBUG_ENABLE_ATOMIC_KMS");
if (flags & META_KMS_DEVICE_FLAG_NO_MODE_SETTING)
{
g_autofree char *render_node_path = NULL;
MetaDevicePool *device_pool;
render_node_path = drmGetRenderDeviceNameFromFd (fd);
if (!render_node_path)
{
g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED,
"Couldn't find render node device for '%s' (%s)",
path, driver_name);
return NULL;
}
device_pool = meta_device_file_get_pool (device_file);
impl_device_file = meta_device_pool_open (device_pool, render_node_path,
META_DEVICE_FILE_FLAG_NONE,
error);
if (!impl_device_file)
return NULL;
g_message ("Adding device '%s' (from '%s', %s) using no mode setting.",
render_node_path, path, driver_name);
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_DUMMY;
}
else if (atomic_kms_enable_env)
{
if (g_strcmp0 (atomic_kms_enable_env, "1") == 0)
{
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_ATOMIC;
if (drmSetClientCap (fd, DRM_CLIENT_CAP_ATOMIC, 1) != 0)
{
g_error ("Failed to force atomic mode setting on '%s' (%s).",
path, driver_name);
}
}
else if (g_strcmp0 (atomic_kms_enable_env, "0") == 0)
{
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_SIMPLE;
}
else
{
g_error ("Invalid value '%s' for MUTTER_DEBUG_ENABLE_ATOMIC_KMS, "
"bailing.",
atomic_kms_enable_env);
}
impl_device_file = meta_device_file_acquire (device_file);
g_message ("Mode setting implementation for '%s' (%s) forced (%s).",
path, driver_name,
impl_device_type == META_TYPE_KMS_IMPL_DEVICE_ATOMIC ?
"atomic" : "non-atomic");
}
else if (!is_atomic_allowed (driver_name))
{
g_message ("Adding device '%s' (%s) using non-atomic mode setting"
" (using atomic mode setting not allowed).",
path, driver_name);
impl_device_file = meta_device_file_acquire (device_file);
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_SIMPLE;
return g_initable_new (META_TYPE_KMS_IMPL_DEVICE_DUMMY,
NULL, error,
"device", device,
"impl", impl,
"path", path,
"flags", flags,
NULL);
}
else
{
int ret;
GType impl_device_types[] = {
META_TYPE_KMS_IMPL_DEVICE_ATOMIC,
META_TYPE_KMS_IMPL_DEVICE_SIMPLE,
};
int i;
ret = drmSetClientCap (fd, DRM_CLIENT_CAP_ATOMIC, 1);
if (ret == 0)
supports_atomic_mode_setting = TRUE;
else
supports_atomic_mode_setting = FALSE;
for (i = 0; i < G_N_ELEMENTS (impl_device_types); i++)
{
MetaKmsImplDevice *impl_device;
g_autoptr (GError) local_error = NULL;
if (supports_atomic_mode_setting)
{
g_message ("Adding device '%s' (%s) using atomic mode setting.",
path, driver_name);
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_ATOMIC;
}
else
{
g_message ("Adding device '%s' (%s) using non-atomic mode setting.",
path, driver_name);
impl_device_type = META_TYPE_KMS_IMPL_DEVICE_SIMPLE;
impl_device = g_initable_new (impl_device_types[i],
NULL, &local_error,
"device", device,
"impl", impl,
"path", path,
"flags", flags,
NULL);
if (impl_device)
return impl_device;
if (local_error->domain != META_KMS_ERROR)
{
g_warning ("Failed to open %s backend: %s",
impl_device_type_to_string (impl_device_types[i]),
local_error->message);
}
}
impl_device_file = meta_device_file_acquire (device_file);
return NULL;
}
impl_device = g_initable_new (impl_device_type, NULL, error,
"device", device,
"impl", impl,
"device-file", impl_device_file,
"flags", flags,
"driver-name", driver_name,
"driver-description", driver_description,
NULL);
if (!impl_device)
return NULL;
return impl_device;
}
static gpointer
@ -421,7 +320,6 @@ create_impl_device_in_impl (MetaKmsImpl *impl,
impl_device = meta_create_kms_impl_device (data->device,
impl,
data->device_file,
data->path,
data->flags,
error);
@ -452,29 +350,14 @@ meta_kms_device_new (MetaKms *kms,
MetaKmsDeviceFlag flags,
GError **error)
{
MetaBackend *backend = meta_kms_get_backend (kms);
MetaBackendNative *backend_native = META_BACKEND_NATIVE (backend);
MetaDevicePool *device_pool =
meta_backend_native_get_device_pool (backend_native);
MetaKmsDevice *device;
CreateImplDeviceData data;
g_autoptr (MetaDeviceFile) device_file = NULL;
MetaDeviceFileFlags device_file_flags;
device_file_flags = META_DEVICE_FILE_FLAG_NONE;
if (!(flags & META_KMS_DEVICE_FLAG_NO_MODE_SETTING))
device_file_flags |= META_DEVICE_FILE_FLAG_TAKE_CONTROL;
device_file = meta_device_pool_open (device_pool, path, flags, error);
if (!device_file)
return NULL;
device = g_object_new (META_TYPE_KMS_DEVICE, NULL);
device->kms = kms;
data = (CreateImplDeviceData) {
.device = device,
.device_file = device_file,
.path = path,
.flags = flags,
};

View File

@ -21,6 +21,7 @@
#include "backends/native/meta-kms-impl-device-atomic.h"
#include "backends/native/meta-backend-native-private.h"
#include "backends/native/meta-kms-connector-private.h"
#include "backends/native/meta-kms-crtc-private.h"
#include "backends/native/meta-kms-device-private.h"
@ -44,6 +45,8 @@ struct _MetaKmsImplDeviceAtomic
GHashTable *page_flip_datas;
};
static GInitableIface *initable_parent_iface;
static void
initable_iface_init (GInitableIface *iface);
@ -1039,14 +1042,83 @@ meta_kms_impl_device_atomic_finalize (GObject *object)
G_OBJECT_CLASS (meta_kms_impl_device_atomic_parent_class)->finalize (object);
}
static MetaDeviceFile *
meta_kms_impl_device_atomic_open_device_file (MetaKmsImplDevice *impl_device,
const char *path,
GError **error)
{
MetaKmsDevice *device = meta_kms_impl_device_get_device (impl_device);
MetaKms *kms = meta_kms_device_get_kms (device);
MetaBackend *backend = meta_kms_get_backend (kms);
MetaDevicePool *device_pool =
meta_backend_native_get_device_pool (META_BACKEND_NATIVE (backend));
g_autoptr (MetaDeviceFile) device_file = NULL;
device_file = meta_device_pool_open (device_pool, path,
META_DEVICE_FILE_FLAG_TAKE_CONTROL,
error);
if (!device_file)
return NULL;
if (drmSetClientCap (meta_device_file_get_fd (device_file),
DRM_CLIENT_CAP_ATOMIC, 1) != 0)
{
g_set_error (error, META_KMS_ERROR, META_KMS_ERROR_NOT_SUPPORTED,
"DRM_CLIENT_CAP_ATOMIC not supported");
return NULL;
}
return g_steal_pointer (&device_file);
}
static gboolean
is_atomic_allowed (const char *driver_name)
{
const char *atomic_driver_deny_list[] = {
"qxl",
"vmwgfx",
"vboxvideo",
"nvidia-drm",
NULL,
};
return !g_strv_contains (atomic_driver_deny_list, driver_name);
}
static gboolean
meta_kms_impl_device_atomic_initable_init (GInitable *initable,
GCancellable *cancellable,
GError **error)
{
MetaKmsImplDevice *impl_device = META_KMS_IMPL_DEVICE (initable);
const char *atomic_kms_enable_env;
return meta_kms_impl_device_init_mode_setting (impl_device, error);
atomic_kms_enable_env = getenv ("MUTTER_DEBUG_ENABLE_ATOMIC_KMS");
if (atomic_kms_enable_env && g_strcmp0 (atomic_kms_enable_env, "1") != 0)
{
g_set_error (error, META_KMS_ERROR, META_KMS_ERROR_USER_INHIBITED,
"Atomic mode setting disable via env var");
return FALSE;
}
if (!initable_parent_iface->init (initable, cancellable, error))
return FALSE;
if (!is_atomic_allowed (meta_kms_impl_device_get_driver_name (impl_device)))
{
g_set_error (error, META_KMS_ERROR, META_KMS_ERROR_DENY_LISTED,
"Atomic mode setting disable via driver deny list");
return FALSE;
}
if (!meta_kms_impl_device_init_mode_setting (impl_device, error))
return FALSE;
g_message ("Added device '%s' (%s) using atomic mode setting.",
meta_kms_impl_device_get_path (impl_device),
meta_kms_impl_device_get_driver_name (impl_device));
return TRUE;
}
static void
@ -1058,6 +1130,8 @@ meta_kms_impl_device_atomic_init (MetaKmsImplDeviceAtomic *impl_device_atomic)
static void
initable_iface_init (GInitableIface *iface)
{
initable_parent_iface = g_type_interface_peek_parent (iface);
iface->init = meta_kms_impl_device_atomic_initable_init;
}
@ -1070,6 +1144,8 @@ meta_kms_impl_device_atomic_class_init (MetaKmsImplDeviceAtomicClass *klass)
object_class->finalize = meta_kms_impl_device_atomic_finalize;
impl_device_class->open_device_file =
meta_kms_impl_device_atomic_open_device_file;
impl_device_class->setup_drm_event_context =
meta_kms_impl_device_atomic_setup_drm_event_context;
impl_device_class->process_update =

View File

@ -21,15 +21,21 @@
#include "backends/native/meta-kms-impl-device-dummy.h"
#include "backends/native/meta-backend-native-private.h"
#include "backends/native/meta-kms.h"
struct _MetaKmsImplDeviceDummy
{
MetaKmsImplDevice parent;
};
static GInitableIface *initable_parent_iface;
static void
initable_iface_init (GInitableIface *iface);
G_DEFINE_TYPE_WITH_CODE (MetaKmsImplDeviceDummy, meta_kms_impl_device_dummy,
G_DEFINE_TYPE_WITH_CODE (MetaKmsImplDeviceDummy,
meta_kms_impl_device_dummy,
META_TYPE_KMS_IMPL_DEVICE,
G_IMPLEMENT_INTERFACE (G_TYPE_INITABLE,
initable_iface_init))
@ -39,9 +45,43 @@ meta_kms_impl_device_dummy_discard_pending_page_flips (MetaKmsImplDevice *impl_d
{
}
static void
meta_kms_impl_device_dummy_init (MetaKmsImplDeviceDummy *impl_device_dummy)
static MetaDeviceFile *
meta_kms_impl_device_dummy_open_device_file (MetaKmsImplDevice *impl_device,
const char *path,
GError **error)
{
MetaKmsDevice *device = meta_kms_impl_device_get_device (impl_device);
MetaKms *kms = meta_kms_device_get_kms (device);
MetaBackend *backend = meta_kms_get_backend (kms);
MetaDevicePool *device_pool =
meta_backend_native_get_device_pool (META_BACKEND_NATIVE (backend));
g_autoptr (MetaDeviceFile) device_file = NULL;
int fd;
g_autofree char *render_node_path = NULL;
device_file = meta_device_pool_open (device_pool, path,
META_DEVICE_FILE_FLAG_NONE,
error);
if (!device_file)
return NULL;
fd = meta_device_file_get_fd (device_file);
render_node_path = drmGetRenderDeviceNameFromFd (fd);
if (!render_node_path)
{
g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED,
"Couldn't find render node device for '%s' (%s)",
meta_kms_impl_device_get_path (impl_device),
meta_kms_impl_device_get_driver_name (impl_device));
return NULL;
}
meta_topic (META_DEBUG_KMS, "Found render node '%s' from '%s'",
render_node_path, path);
return meta_device_pool_open (device_pool, render_node_path,
META_DEVICE_FILE_FLAG_NONE,
error);
}
static gboolean
@ -49,21 +89,39 @@ meta_kms_impl_device_dummy_initable_init (GInitable *initable,
GCancellable *cancellable,
GError **error)
{
MetaKmsImplDevice *impl_device = META_KMS_IMPL_DEVICE (initable);
if (!initable_parent_iface->init (initable, cancellable, error))
return FALSE;
g_message ("Added device '%s' (%s) using no mode setting.",
meta_kms_impl_device_get_path (impl_device),
meta_kms_impl_device_get_driver_name (impl_device));
return TRUE;
}
static void
initable_iface_init (GInitableIface *iface)
{
initable_parent_iface = g_type_interface_peek_parent (iface);
iface->init = meta_kms_impl_device_dummy_initable_init;
}
static void
meta_kms_impl_device_dummy_init (MetaKmsImplDeviceDummy *impl_device_dummy)
{
}
static void
meta_kms_impl_device_dummy_class_init (MetaKmsImplDeviceDummyClass *klass)
{
MetaKmsImplDeviceClass *impl_device_class =
META_KMS_IMPL_DEVICE_CLASS (klass);
impl_device_class->open_device_file =
meta_kms_impl_device_dummy_open_device_file;
impl_device_class->discard_pending_page_flips =
meta_kms_impl_device_dummy_discard_pending_page_flips;
}

View File

@ -21,6 +21,7 @@
#include "backends/native/meta-kms-impl-device-simple.h"
#include "backends/native/meta-backend-native-private.h"
#include "backends/native/meta-drm-buffer-gbm.h"
#include "backends/native/meta-kms-connector-private.h"
#include "backends/native/meta-kms-crtc-private.h"
@ -60,6 +61,8 @@ struct _MetaKmsImplDeviceSimple
GHashTable *cached_mode_sets;
};
static GInitableIface *initable_parent_iface;
static void
initable_iface_init (GInitableIface *iface);
@ -1534,6 +1537,22 @@ meta_kms_impl_device_simple_finalize (GObject *object)
G_OBJECT_CLASS (meta_kms_impl_device_simple_parent_class)->finalize (object);
}
static MetaDeviceFile *
meta_kms_impl_device_simple_open_device_file (MetaKmsImplDevice *impl_device,
const char *path,
GError **error)
{
MetaKmsDevice *device = meta_kms_impl_device_get_device (impl_device);
MetaKms *kms = meta_kms_device_get_kms (device);
MetaBackend *backend = meta_kms_get_backend (kms);
MetaDevicePool *device_pool =
meta_backend_native_get_device_pool (META_BACKEND_NATIVE (backend));
return meta_device_pool_open (device_pool, path,
META_DEVICE_FILE_FLAG_TAKE_CONTROL,
error);
}
static gboolean
meta_kms_impl_device_simple_initable_init (GInitable *initable,
GCancellable *cancellable,
@ -1545,6 +1564,9 @@ meta_kms_impl_device_simple_initable_init (GInitable *initable,
MetaKmsDevice *device = meta_kms_impl_device_get_device (impl_device);
GList *l;
if (!initable_parent_iface->init (initable, cancellable, error))
return FALSE;
if (!meta_kms_impl_device_init_mode_setting (impl_device, error))
return FALSE;
@ -1573,6 +1595,10 @@ meta_kms_impl_device_simple_initable_init (GInitable *initable,
crtc);
}
g_message ("Added device '%s' (%s) using non-atomic mode setting.",
meta_kms_impl_device_get_path (impl_device),
meta_kms_impl_device_get_driver_name (impl_device));
return TRUE;
}
@ -1584,6 +1610,8 @@ meta_kms_impl_device_simple_init (MetaKmsImplDeviceSimple *impl_device_simple)
static void
initable_iface_init (GInitableIface *iface)
{
initable_parent_iface = g_type_interface_peek_parent (iface);
iface->init = meta_kms_impl_device_simple_initable_init;
}
@ -1596,6 +1624,8 @@ meta_kms_impl_device_simple_class_init (MetaKmsImplDeviceSimpleClass *klass)
object_class->finalize = meta_kms_impl_device_simple_finalize;
impl_device_class->open_device_file =
meta_kms_impl_device_simple_open_device_file;
impl_device_class->setup_drm_event_context =
meta_kms_impl_device_simple_setup_drm_event_context;
impl_device_class->process_update =

View File

@ -47,10 +47,8 @@ enum
PROP_DEVICE,
PROP_IMPL,
PROP_DEVICE_FILE,
PROP_PATH,
PROP_FLAGS,
PROP_DRIVER_NAME,
PROP_DRIVER_DESCRIPTION,
N_PROPS
};
@ -79,9 +77,16 @@ typedef struct _MetaKmsImplDevicePrivate
GList *fallback_modes;
} MetaKmsImplDevicePrivate;
static void
initable_iface_init (GInitableIface *iface);
G_DEFINE_TYPE_WITH_CODE (MetaKmsImplDevice, meta_kms_impl_device,
G_TYPE_OBJECT,
G_ADD_PRIVATE (MetaKmsImplDevice))
G_ADD_PRIVATE (MetaKmsImplDevice)
G_IMPLEMENT_INTERFACE (G_TYPE_INITABLE,
initable_iface_init))
G_DEFINE_QUARK (-meta-kms-error-quark, meta_kms_error)
MetaKmsDevice *
meta_kms_impl_device_get_device (MetaKmsImplDevice *impl_device)
@ -711,18 +716,9 @@ meta_kms_impl_device_get_property (GObject *object,
case PROP_IMPL:
g_value_set_object (value, priv->impl);
break;
case PROP_DEVICE_FILE:
g_value_set_pointer (value, priv->device_file);
break;
case PROP_FLAGS:
g_value_set_flags (value, priv->flags);
break;
case PROP_DRIVER_NAME:
g_value_set_string (value, priv->driver_name);
break;
case PROP_DRIVER_DESCRIPTION:
g_value_set_string (value, priv->driver_name);
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@ -747,19 +743,12 @@ meta_kms_impl_device_set_property (GObject *object,
case PROP_IMPL:
priv->impl = g_value_get_object (value);
break;
case PROP_DEVICE_FILE:
priv->device_file =
meta_device_file_acquire (g_value_get_pointer (value));
case PROP_PATH:
priv->path = g_value_dup_string (value);
break;
case PROP_FLAGS:
priv->flags = g_value_get_flags (value);
break;
case PROP_DRIVER_NAME:
priv->driver_name = g_value_dup_string (value);
break;
case PROP_DRIVER_DESCRIPTION:
priv->driver_description = g_value_dup_string (value);
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@ -849,16 +838,52 @@ meta_kms_impl_device_prepare_shutdown (MetaKmsImplDevice *impl_device)
klass->prepare_shutdown (impl_device);
}
static void
meta_kms_impl_device_constructed (GObject *object)
static gboolean
get_driver_info (int fd,
char **name,
char **description)
{
MetaKmsImplDevice *impl_device = META_KMS_IMPL_DEVICE (object);
drmVersion *drm_version;
drm_version = drmGetVersion (fd);
if (!drm_version)
return FALSE;
*name = g_strndup (drm_version->name,
drm_version->name_len);
*description = g_strndup (drm_version->desc,
drm_version->desc_len);
drmFreeVersion (drm_version);
return TRUE;
}
static gboolean
meta_kms_impl_device_initable_init (GInitable *initable,
GCancellable *cancellable,
GError **error)
{
MetaKmsImplDevice *impl_device = META_KMS_IMPL_DEVICE (initable);
MetaKmsImplDevicePrivate *priv =
meta_kms_impl_device_get_instance_private (impl_device);
MetaKmsImplDeviceClass *klass = META_KMS_IMPL_DEVICE_GET_CLASS (impl_device);
int fd;
priv->device_file = klass->open_device_file (impl_device, priv->path, error);
if (!priv->device_file)
return FALSE;
g_clear_pointer (&priv->path, g_free);
priv->path = g_strdup (meta_device_file_get_path (priv->device_file));
G_OBJECT_CLASS (meta_kms_impl_device_parent_class)->constructed (object);
fd = meta_device_file_get_fd (priv->device_file);
if (!get_driver_info (fd, &priv->driver_name, &priv->driver_description))
{
priv->driver_name = g_strdup ("unknown");
priv->driver_description = g_strdup ("Unknown");
}
return TRUE;
}
static void
@ -866,6 +891,12 @@ meta_kms_impl_device_init (MetaKmsImplDevice *impl_device)
{
}
static void
initable_iface_init (GInitableIface *iface)
{
iface->init = meta_kms_impl_device_initable_init;
}
static void
meta_kms_impl_device_class_init (MetaKmsImplDeviceClass *klass)
{
@ -873,7 +904,6 @@ meta_kms_impl_device_class_init (MetaKmsImplDeviceClass *klass)
object_class->get_property = meta_kms_impl_device_get_property;
object_class->set_property = meta_kms_impl_device_set_property;
object_class->constructed = meta_kms_impl_device_constructed;
object_class->finalize = meta_kms_impl_device_finalize;
obj_props[PROP_DEVICE] =
@ -892,13 +922,14 @@ meta_kms_impl_device_class_init (MetaKmsImplDeviceClass *klass)
G_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
obj_props[PROP_DEVICE_FILE] =
g_param_spec_pointer ("device-file",
"device-file",
"Device file",
G_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
obj_props[PROP_PATH] =
g_param_spec_string ("path",
"path",
"Device path",
NULL,
G_PARAM_WRITABLE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
obj_props[PROP_FLAGS] =
g_param_spec_flags ("flags",
"flags",
@ -908,21 +939,5 @@ meta_kms_impl_device_class_init (MetaKmsImplDeviceClass *klass)
G_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
obj_props[PROP_DRIVER_NAME] =
g_param_spec_string ("driver-name",
"driver-name",
"DRM device driver name",
NULL,
G_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
obj_props[PROP_DRIVER_DESCRIPTION] =
g_param_spec_string ("driver-description",
"driver-description",
"DRM device driver description",
NULL,
G_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY |
G_PARAM_STATIC_STRINGS);
g_object_class_install_properties (object_class, N_PROPS, obj_props);
}

View File

@ -25,6 +25,7 @@
#include <xf86drm.h>
#include <xf86drmMode.h>
#include "backends/native/meta-device-pool.h"
#include "backends/native/meta-kms-device.h"
#include "backends/native/meta-kms-page-flip-private.h"
#include "backends/native/meta-kms-types.h"
@ -62,6 +63,9 @@ struct _MetaKmsImplDeviceClass
{
GObjectClass parent_class;
MetaDeviceFile * (* open_device_file) (MetaKmsImplDevice *impl_device,
const char *path,
GError **error);
void (* setup_drm_event_context) (MetaKmsImplDevice *impl_device,
drmEventContext *drm_event_context);
MetaKmsFeedback * (* process_update) (MetaKmsImplDevice *impl_device,
@ -73,6 +77,16 @@ struct _MetaKmsImplDeviceClass
void (* prepare_shutdown) (MetaKmsImplDevice *impl_device);
};
enum
{
META_KMS_ERROR_USER_INHIBITED,
META_KMS_ERROR_DENY_LISTED,
META_KMS_ERROR_NOT_SUPPORTED,
};
#define META_KMS_ERROR meta_kms_error_quark ()
GQuark meta_kms_error_quark (void);
MetaKmsDevice * meta_kms_impl_device_get_device (MetaKmsImplDevice *impl_device);
GList * meta_kms_impl_device_copy_connectors (MetaKmsImplDevice *impl_device);