*/
                struct list_head flushing_list;
 
+               /**
+                * List of objects currently pending a GPU write flush.
+                *
+                * All elements on this list will belong to either the
+                * active_list or flushing_list, last_rendering_seqno can
+                * be used to differentiate between the two elements.
+                */
+               struct list_head gpu_write_list;
+
                /**
                 * LRU list of objects which are not in the ringbuffer and
                 * are ready to unbind, but are still in the GTT.
 
        /** This object's place on the active/flushing/inactive lists */
        struct list_head list;
+       /** This object's place on GPU write list */
+       struct list_head gpu_write_list;
 
        /** This object's place on the fenced object LRU */
        struct list_head fence_list;
 
        else
                list_move_tail(&obj_priv->list, &dev_priv->mm.inactive_list);
 
+       BUG_ON(!list_empty(&obj_priv->gpu_write_list));
+
        obj_priv->last_rendering_seqno = 0;
        if (obj_priv->active) {
                obj_priv->active = 0;
                struct drm_i915_gem_object *obj_priv, *next;
 
                list_for_each_entry_safe(obj_priv, next,
-                                        &dev_priv->mm.flushing_list, list) {
+                                        &dev_priv->mm.gpu_write_list,
+                                        gpu_write_list) {
                        struct drm_gem_object *obj = obj_priv->obj;
 
                        if ((obj->write_domain & flush_domains) ==
                                uint32_t old_write_domain = obj->write_domain;
 
                                obj->write_domain = 0;
+                               list_del_init(&obj_priv->gpu_write_list);
                                i915_gem_object_move_to_active(obj, seqno);
 
                                trace_i915_gem_object_change_domain(obj,
 i915_gem_evict_everything(struct drm_device *dev)
 {
        drm_i915_private_t *dev_priv = dev->dev_private;
-       uint32_t seqno;
        int ret;
+       uint32_t seqno;
        bool lists_empty;
 
        spin_lock(&dev_priv->mm.active_list_lock);
        if (ret)
                return ret;
 
+       BUG_ON(!list_empty(&dev_priv->mm.flushing_list));
+
        ret = i915_gem_evict_from_inactive_list(dev);
        if (ret)
                return ret;
        old_write_domain = obj->write_domain;
        i915_gem_flush(dev, 0, obj->write_domain);
        seqno = i915_add_request(dev, NULL, obj->write_domain);
-       obj->write_domain = 0;
+       BUG_ON(obj->write_domain);
        i915_gem_object_move_to_active(obj, seqno);
 
        trace_i915_gem_object_change_domain(obj,
                i915_gem_flush(dev,
                               dev->invalidate_domains,
                               dev->flush_domains);
-               if (dev->flush_domains)
+               if (dev->flush_domains & I915_GEM_GPU_DOMAINS)
                        (void)i915_add_request(dev, file_priv,
                                               dev->flush_domains);
        }
 
        for (i = 0; i < args->buffer_count; i++) {
                struct drm_gem_object *obj = object_list[i];
+               struct drm_i915_gem_object *obj_priv = obj->driver_private;
                uint32_t old_write_domain = obj->write_domain;
 
                obj->write_domain = obj->pending_write_domain;
+               if (obj->write_domain)
+                       list_move_tail(&obj_priv->gpu_write_list,
+                                      &dev_priv->mm.gpu_write_list);
+               else
+                       list_del_init(&obj_priv->gpu_write_list);
+
                trace_i915_gem_object_change_domain(obj,
                                                    obj->read_domains,
                                                    old_write_domain);
        obj_priv->obj = obj;
        obj_priv->fence_reg = I915_FENCE_REG_NONE;
        INIT_LIST_HEAD(&obj_priv->list);
+       INIT_LIST_HEAD(&obj_priv->gpu_write_list);
        INIT_LIST_HEAD(&obj_priv->fence_list);
        obj_priv->madv = I915_MADV_WILLNEED;
 
        spin_lock_init(&dev_priv->mm.active_list_lock);
        INIT_LIST_HEAD(&dev_priv->mm.active_list);
        INIT_LIST_HEAD(&dev_priv->mm.flushing_list);
+       INIT_LIST_HEAD(&dev_priv->mm.gpu_write_list);
        INIT_LIST_HEAD(&dev_priv->mm.inactive_list);
        INIT_LIST_HEAD(&dev_priv->mm.request_list);
        INIT_LIST_HEAD(&dev_priv->mm.fence_list);