No subject


Sat Jul 24 14:26:24 PDT 2010


/* A typical clean-up sequence for objects stored in an idr tree, will
 * use idr_for_each() to free all objects, if necessary, then
 * idr_remove_all() to remove all ids, and idr_destroy() to free
 * up the cached idr_layers.
 */

We were missing the vital idr_rmove_all() step and so were leaking
the used layers for every dri client:

unreferenced object 0xf32133c0 (size 148):
  comm "plymouthd", pid 131, jiffies 4294678490 (age 2308.030s)
  hex dump (first 32 bytes):
    04 00 00 00 00 00 00 00 00 00 00 00 00 40 19 f3  ............. at ..
    00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00  ................
  backtrace:
    [<c04e5657>] create_object+0x124/0x1f1
    [<c07cf100>] kmemleak_alloc+0x4c/0x90
    [<c04db6a9>] kmem_cache_alloc+0xee/0x13c
    [<c05c3d25>] idr_pre_get+0x24/0x61
    [<f8315c9c>] drm_gem_handle_create+0x27/0x7f [drm]
    [<f89925b2>] i915_gem_create_ioctl+0x4f/0x71 [i915]
    [<f83148ac>] drm_ioctl+0x272/0x356 [drm]
    [<c04f27c4>] vfs_ioctl+0x33/0x91
    [<c04f31cf>] do_vfs_ioctl+0x46b/0x496
    [<c04f3240>] sys_ioctl+0x46/0x66
    [<c040325f>] sysenter_do_call+0x12/0x38
    [<ffffffff>] 0xffffffff

Fixes https://bugzilla.kernel.org/show_bug.cgi?id=15803

Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>
---
 drivers/gpu/drm/drm_drv.c |    1 +
 drivers/gpu/drm/drm_gem.c |    1 +
 2 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/drivers/gpu/drm/drm_drv.c b/drivers/gpu/drm/drm_drv.c
index 4a66201..79b73cb 100644
--- a/drivers/gpu/drm/drm_drv.c
+++ b/drivers/gpu/drm/drm_drv.c
@@ -362,6 +362,7 @@ static void __exit drm_core_exit(void)
 
 	unregister_chrdev(DRM_MAJOR, "drm");
 
+	idr_remove_all(&drm_minors_idr);
 	idr_destroy(&drm_minors_idr);
 }
 
diff --git a/drivers/gpu/drm/drm_gem.c b/drivers/gpu/drm/drm_gem.c
index 830cb97..58bd0f7 100644
--- a/drivers/gpu/drm/drm_gem.c
+++ b/drivers/gpu/drm/drm_gem.c
@@ -419,6 +419,7 @@ drm_gem_release(struct drm_device *dev, struct drm_file *file_private)
 	idr_for_each(&file_private->object_idr,
 		     &drm_gem_object_release_handle, NULL);
 
+	idr_remove_all(&file_private->object_idr);
 	idr_destroy(&file_private->object_idr);
 }
 
-- 
1.7.1



More information about the dri-devel mailing list