summaryrefslogtreecommitdiff
path: root/drivers/char/drm/drm_drv.c
diff options
context:
space:
mode:
authorDave Airlie <airlied@redhat.com>2008-04-21 16:47:32 +1000
committerDave Airlie <airlied@linux.ie>2008-04-26 17:55:07 +1000
commit2c14f28be2a3f2a2e9861b156d64fbe2bc7000c3 (patch)
treedbf55c07d1b245a45330e0d879833df29954fe12 /drivers/char/drm/drm_drv.c
parent7b832b56bd971348329c3f4c753ca0abfdf3a3d1 (diff)
drm: reorganise minor number handling using backported modesetting code.
rips out the head crap and replaces it with an idr and drm_minor structure Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers/char/drm/drm_drv.c')
-rw-r--r--drivers/char/drm/drm_drv.c60
1 files changed, 28 insertions, 32 deletions
diff --git a/drivers/char/drm/drm_drv.c b/drivers/char/drm/drm_drv.c
index 0e7af53c87de..fc54140551a7 100644
--- a/drivers/char/drm/drm_drv.c
+++ b/drivers/char/drm/drm_drv.c
@@ -313,35 +313,36 @@ static void drm_cleanup(struct drm_device * dev)
drm_ht_remove(&dev->map_hash);
drm_ctxbitmap_cleanup(dev);
- drm_put_head(&dev->primary);
+ drm_put_minor(&dev->primary);
if (drm_put_dev(dev))
DRM_ERROR("Cannot unload module\n");
}
-void drm_exit(struct drm_driver *driver)
+int drm_minors_cleanup(int id, void *ptr, void *data)
{
- int i;
- struct drm_device *dev = NULL;
- struct drm_head *head;
+ struct drm_minor *minor = ptr;
+ struct drm_device *dev;
+ struct drm_driver *driver = data;
+
+ dev = minor->dev;
+ if (minor->dev->driver != driver)
+ return 0;
+
+ if (minor->type != DRM_MINOR_LEGACY)
+ return 0;
+ if (dev)
+ pci_dev_put(dev->pdev);
+ drm_cleanup(dev);
+ return 1;
+}
+
+void drm_exit(struct drm_driver *driver)
+{
DRM_DEBUG("\n");
- for (i = 0; i < drm_cards_limit; i++) {
- head = drm_heads[i];
- if (!head)
- continue;
- if (!head->dev)
- continue;
- if (head->dev->driver != driver)
- continue;
- dev = head->dev;
- if (dev) {
- /* release the pci driver */
- if (dev->pdev)
- pci_dev_put(dev->pdev);
- drm_cleanup(dev);
- }
- }
+ idr_for_each(&drm_minors_idr, &drm_minors_cleanup, driver);
+
DRM_INFO("Module unloaded\n");
}
@@ -357,13 +358,7 @@ static int __init drm_core_init(void)
{
int ret = -ENOMEM;
- drm_cards_limit =
- (drm_cards_limit <
- DRM_MAX_MINOR + 1 ? drm_cards_limit : DRM_MAX_MINOR + 1);
- drm_heads =
- drm_calloc(drm_cards_limit, sizeof(*drm_heads), DRM_MEM_STUB);
- if (!drm_heads)
- goto err_p1;
+ idr_init(&drm_minors_idr);
if (register_chrdev(DRM_MAJOR, "drm", &drm_stub_fops))
goto err_p1;
@@ -391,7 +386,8 @@ err_p3:
drm_sysfs_destroy();
err_p2:
unregister_chrdev(DRM_MAJOR, "drm");
- drm_free(drm_heads, sizeof(*drm_heads) * drm_cards_limit, DRM_MEM_STUB);
+
+ idr_destroy(&drm_minors_idr);
err_p1:
return ret;
}
@@ -403,7 +399,7 @@ static void __exit drm_core_exit(void)
unregister_chrdev(DRM_MAJOR, "drm");
- drm_free(drm_heads, sizeof(*drm_heads) * drm_cards_limit, DRM_MEM_STUB);
+ idr_destroy(&drm_minors_idr);
}
module_init(drm_core_init);
@@ -452,7 +448,7 @@ int drm_ioctl(struct inode *inode, struct file *filp,
unsigned int cmd, unsigned long arg)
{
struct drm_file *file_priv = filp->private_data;
- struct drm_device *dev = file_priv->head->dev;
+ struct drm_device *dev = file_priv->minor->dev;
struct drm_ioctl_desc *ioctl;
drm_ioctl_t *func;
unsigned int nr = DRM_IOCTL_NR(cmd);
@@ -465,7 +461,7 @@ int drm_ioctl(struct inode *inode, struct file *filp,
DRM_DEBUG("pid=%d, cmd=0x%02x, nr=0x%02x, dev 0x%lx, auth=%d\n",
task_pid_nr(current), cmd, nr,
- (long)old_encode_dev(file_priv->head->device),
+ (long)old_encode_dev(file_priv->minor->device),
file_priv->authenticated);
if ((nr >= DRM_CORE_IOCTL_COUNT) &&