summaryrefslogtreecommitdiff
path: root/sys/dev/pci/drm
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@cvs.openbsd.org>2016-04-06 14:39:20 +0000
committerMark Kettenis <kettenis@cvs.openbsd.org>2016-04-06 14:39:20 +0000
commitb2bf01fceec9880dbd34e96f7af56a0344712684 (patch)
tree8f5e889025bc2eb06e6856a5c67baf57b2618dfd /sys/dev/pci/drm
parentca58bbb32586ae033dfdea3b3fcb3f4357167d5d (diff)
Another "idr" conversion.
Diffstat (limited to 'sys/dev/pci/drm')
-rw-r--r--sys/dev/pci/drm/drm_crtc.c111
-rw-r--r--sys/dev/pci/drm/drm_crtc.h7
2 files changed, 37 insertions, 81 deletions
diff --git a/sys/dev/pci/drm/drm_crtc.c b/sys/dev/pci/drm/drm_crtc.c
index fcfa8d638ab..98ab127db10 100644
--- a/sys/dev/pci/drm/drm_crtc.c
+++ b/sys/dev/pci/drm/drm_crtc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: drm_crtc.c,v 1.19 2015/09/27 11:09:26 jsg Exp $ */
+/* $OpenBSD: drm_crtc.c,v 1.20 2016/04/06 14:39:19 kettenis Exp $ */
/*
* Copyright (c) 2006-2008 Intel Corporation
* Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
@@ -99,10 +99,6 @@ EXPORT_SYMBOL(drm_warn_on_modeset_not_all_locked);
return "(unknown)"; \
}
-int drm_mode_handle_cmp(struct drm_mode_handle *, struct drm_mode_handle *);
-
-SPLAY_PROTOTYPE(drm_mode_tree, drm_mode_handle, entry, drm_mode_handle_cmp);
-
/*
* Global properties
*/
@@ -313,27 +309,21 @@ EXPORT_SYMBOL(drm_get_format_name);
static int drm_mode_object_get(struct drm_device *dev,
struct drm_mode_object *obj, uint32_t obj_type)
{
- struct drm_mode_handle *han;
- int new_id = 0;
+ int ret;
- if ((han = drm_calloc(1, sizeof(*han))) == NULL)
- return -ENOMEM;
- han->obj = obj;
- rw_enter_write(&dev->mode_config.idr_rwl);
-
-again:
- new_id = han->handle = ++dev->mode_config.mode_obj_id;
- /*
- * Make sure we have no duplicates. this'll hurt once we wrap, 0 is
- * reserved.
- */
- obj->id = new_id;
- obj->type = obj_type;
- if (han->handle == 0 || SPLAY_INSERT(drm_mode_tree,
- &dev->mode_config.mode_tree, han))
- goto again;
- rw_exit_write(&dev->mode_config.idr_rwl);
- return 0;
+ mutex_lock(&dev->mode_config.idr_mutex);
+ ret = idr_alloc(&dev->mode_config.crtc_idr, obj, 1, 0, GFP_KERNEL);
+ if (ret >= 0) {
+ /*
+ * Set up the object linking under the protection of the idr
+ * lock so that other users can't see inconsistent state.
+ */
+ obj->id = ret;
+ obj->type = obj_type;
+ }
+ mutex_unlock(&dev->mode_config.idr_mutex);
+
+ return ret < 0 ? ret : 0;
}
/**
@@ -346,13 +336,9 @@ again:
static void drm_mode_object_put(struct drm_device *dev,
struct drm_mode_object *object)
{
- struct drm_mode_handle han;
- han.obj = object;
- han.handle = object->id;
-
- rw_enter_write(&dev->mode_config.idr_rwl);
- SPLAY_REMOVE(drm_mode_tree, &dev->mode_config.mode_tree, &han);
- rw_exit_write(&dev->mode_config.idr_rwl);
+ mutex_lock(&dev->mode_config.idr_mutex);
+ idr_remove(&dev->mode_config.crtc_idr, object->id);
+ mutex_unlock(&dev->mode_config.idr_mutex);
}
/**
@@ -368,21 +354,16 @@ struct drm_mode_object *drm_mode_object_find(struct drm_device *dev,
uint32_t id, uint32_t type)
{
struct drm_mode_object *obj = NULL;
- struct drm_mode_handle *han, search;
- rw_enter_write(&dev->mode_config.idr_rwl);
- search.handle = id;
- han = SPLAY_FIND(drm_mode_tree, &dev->mode_config.mode_tree, &search);
- if (han == NULL) {
- rw_exit_write(&dev->mode_config.idr_rwl);
- return NULL;
- }
-
- obj = han->obj;
- if (obj->type != type) {
+ /* Framebuffers are reference counted and need their own lookup
+ * function.*/
+ WARN_ON(type == DRM_MODE_OBJECT_FB);
+
+ mutex_lock(&dev->mode_config.idr_mutex);
+ obj = idr_find(&dev->mode_config.crtc_idr, id);
+ if (!obj || (obj->type != type) || (obj->id != id))
obj = NULL;
- }
- rw_exit_write(&dev->mode_config.idr_rwl);
+ mutex_unlock(&dev->mode_config.idr_mutex);
return obj;
}
@@ -444,23 +425,15 @@ static struct drm_framebuffer *__drm_framebuffer_lookup(struct drm_device *dev,
uint32_t id)
{
struct drm_mode_object *obj = NULL;
- struct drm_mode_handle *han, search;
struct drm_framebuffer *fb;
- rw_enter_write(&dev->mode_config.idr_rwl);
- search.handle = id;
- han = SPLAY_FIND(drm_mode_tree, &dev->mode_config.mode_tree, &search);
- if (han == NULL) {
- rw_exit_write(&dev->mode_config.idr_rwl);
- return NULL;
- }
-
- obj = han->obj;
+ mutex_lock(&dev->mode_config.idr_mutex);
+ obj = idr_find(&dev->mode_config.crtc_idr, id);
if (!obj || (obj->type != DRM_MODE_OBJECT_FB) || (obj->id != id))
fb = NULL;
else
fb = obj_to_fb(obj);
- rw_exit_write(&dev->mode_config.idr_rwl);
+ mutex_unlock(&dev->mode_config.idr_mutex);
return fb;
}
@@ -528,13 +501,9 @@ static void __drm_framebuffer_unreference(struct drm_framebuffer *fb)
static void __drm_framebuffer_unregister(struct drm_device *dev,
struct drm_framebuffer *fb)
{
- struct drm_mode_handle han;
- han.obj = &fb->base;
- han.handle = fb->base.id;
-
- rw_enter_write(&dev->mode_config.idr_rwl);
- SPLAY_REMOVE(drm_mode_tree, &dev->mode_config.mode_tree, &han);
- rw_exit_write(&dev->mode_config.idr_rwl);
+ mutex_lock(&dev->mode_config.idr_mutex);
+ idr_remove(&dev->mode_config.crtc_idr, fb->base.id);
+ mutex_unlock(&dev->mode_config.idr_mutex);
fb->base.id = 0;
@@ -4089,7 +4058,7 @@ EXPORT_SYMBOL(drm_format_vert_chroma_subsampling);
void drm_mode_config_init(struct drm_device *dev)
{
rw_init(&dev->mode_config.mutex, "mcrwl");
- rw_init(&dev->mode_config.idr_rwl, "idrwl");
+ rw_init(&dev->mode_config.idr_mutex, "idrwl");
rw_init(&dev->mode_config.fb_lock, "fblk");
INIT_LIST_HEAD(&dev->mode_config.fb_list);
INIT_LIST_HEAD(&dev->mode_config.crtc_list);
@@ -4099,7 +4068,7 @@ void drm_mode_config_init(struct drm_device *dev)
INIT_LIST_HEAD(&dev->mode_config.property_list);
INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
INIT_LIST_HEAD(&dev->mode_config.plane_list);
- SPLAY_INIT(&dev->mode_config.mode_tree);
+ idr_init(&dev->mode_config.crtc_idr);
drm_modeset_lock_all(dev);
drm_mode_create_standard_connector_properties(dev);
@@ -4184,18 +4153,6 @@ void drm_mode_config_cleanup(struct drm_device *dev)
crtc->funcs->destroy(crtc);
}
-#ifdef __linux__
idr_destroy(&dev->mode_config.crtc_idr);
-#else
- /* XXX destroy idr/SPLAY tree */
-#endif
}
EXPORT_SYMBOL(drm_mode_config_cleanup);
-
-int
-drm_mode_handle_cmp(struct drm_mode_handle *a, struct drm_mode_handle *b)
-{
- return a->handle < b->handle ? -1 : a->handle > b->handle;
-}
-
-SPLAY_GENERATE(drm_mode_tree, drm_mode_handle, entry, drm_mode_handle_cmp);
diff --git a/sys/dev/pci/drm/drm_crtc.h b/sys/dev/pci/drm/drm_crtc.h
index 8b69ab36325..8a6880eb25a 100644
--- a/sys/dev/pci/drm/drm_crtc.h
+++ b/sys/dev/pci/drm/drm_crtc.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: drm_crtc.h,v 1.6 2015/09/27 11:09:26 jsg Exp $ */
+/* $OpenBSD: drm_crtc.h,v 1.7 2016/04/06 14:39:19 kettenis Exp $ */
/*
* Copyright © 2006 Keith Packard
* Copyright © 2007-2008 Dave Airlie
@@ -837,9 +837,8 @@ struct drm_mode_group {
*/
struct drm_mode_config {
struct rwlock mutex; /* protects configuration (mode lists etc.) */
- struct rwlock idr_rwl; /* for IDR management */
- SPLAY_HEAD(drm_mode_tree, drm_mode_handle) mode_tree; /* use this idr for all IDs, fb, crtc, connector, modes - just makes life easier */
- uint32_t mode_obj_id;
+ struct rwlock idr_mutex; /* for IDR management */
+ struct idr crtc_idr; /* use this idr for all IDs, fb, crtc, connector, modes - just makes life easier */
/* this is limited to one for now */