drm/i915: fix another use-after-free in i915_gem_evict_everything
authorMichel Thierry <michel.thierry@intel.com>
Tue, 9 Sep 2014 12:04:43 +0000 (13:04 +0100)
committerDaniel Vetter <daniel.vetter@ffwll.ch>
Fri, 19 Sep 2014 12:41:16 +0000 (14:41 +0200)
Also here, i915_gem_evict_vm causes an unbind, which can end up dropping
the last ref to the ppgtt.

Triggered by igt gem_evict_everything test.

Testcase: igt/gem_evict_everything
Signed-off-by: Michel Thierry <michel.thierry@intel.com>
Reviewed-by: Chris Wilson <chris@cris-wilsonc.co.uk>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
drivers/gpu/drm/i915/i915_gem_evict.c

index bbf4b12d842effa7972e7dcaaa23e1de08434b59..886ff2ee7a282e0762855e244e40cd8a7493b1fe 100644 (file)
@@ -243,7 +243,7 @@ int
 i915_gem_evict_everything(struct drm_device *dev)
 {
        struct drm_i915_private *dev_priv = dev->dev_private;
-       struct i915_address_space *vm;
+       struct i915_address_space *vm, *v;
        bool lists_empty = true;
        int ret;
 
@@ -270,7 +270,7 @@ i915_gem_evict_everything(struct drm_device *dev)
        i915_gem_retire_requests(dev);
 
        /* Having flushed everything, unbind() should never raise an error */
-       list_for_each_entry(vm, &dev_priv->vm_list, global_link)
+       list_for_each_entry_safe(vm, v, &dev_priv->vm_list, global_link)
                WARN_ON(i915_gem_evict_vm(vm, false));
 
        return 0;