#define WATCH_EXEC 0
#define WATCH_LRU 0
#define WATCH_RELOC 0
+#define WATCH_INACTIVE 0
static int
i915_gem_object_set_domain(struct drm_gem_object *obj,
&dev_priv->mm.active_list);
}
+#if WATCH_INACTIVE
+static void
+i915_verify_inactive(struct drm_device *dev, char *file, int line)
+{
+ drm_i915_private_t *dev_priv = dev->dev_private;
+ struct drm_gem_object *obj;
+ struct drm_i915_gem_object *obj_priv;
+
+ list_for_each_entry(obj_priv, &dev_priv->mm.inactive_list, list) {
+ obj = obj_priv->obj;
+ if (obj_priv->pin_count || obj_priv->active || (obj->write_domain & ~I915_GEM_DOMAIN_CPU))
+ DRM_ERROR("inactive %p (p %d a %d w %x) %s:%d\n",
+ obj,
+ obj_priv->pin_count, obj_priv->active, obj->write_domain, file, line);
+ }
+}
+#else
+#define i915_verify_inactive(dev,file,line)
+#endif
+
static void
i915_gem_object_move_to_inactive(struct drm_gem_object *obj)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct drm_i915_gem_object *obj_priv = obj->driver_private;
+ i915_verify_inactive(dev, __FILE__, __LINE__);
if (obj_priv->pin_count != 0)
list_del_init(&obj_priv->list);
else
obj_priv->active = 0;
drm_gem_object_unreference(obj);
}
+ i915_verify_inactive(dev, __FILE__, __LINE__);
}
/**
mutex_lock(&dev->struct_mutex);
+ i915_verify_inactive(dev, __FILE__, __LINE__);
if (dev_priv->mm.suspended) {
DRM_ERROR("Execbuf while VT-switched.\n");
mutex_unlock(&dev->struct_mutex);
batch_obj->pending_read_domains = I915_GEM_DOMAIN_COMMAND;
batch_obj->pending_write_domain = 0;
+ i915_verify_inactive(dev, __FILE__, __LINE__);
+
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;
goto err;
}
+ i915_verify_inactive(dev, __FILE__, __LINE__);
+
/* Flush/invalidate caches and chipset buffer */
flush_domains = i915_gem_dev_set_domain(dev);
+ i915_verify_inactive(dev, __FILE__, __LINE__);
+
#if WATCH_COHERENCY
for (i = 0; i < args->buffer_count; i++) {
i915_gem_object_check_coherency(object_list[i],
*/
flush_domains |= i915_retire_commands(dev);
+ i915_verify_inactive(dev, __FILE__, __LINE__);
+
/*
* Get a seqno representing the execution of the current buffer,
* which we can wait on. We would like to mitigate these interrupts,
i915_dump_lru(dev, __func__);
#endif
+ i915_verify_inactive(dev, __FILE__, __LINE__);
+
/* Copy the new buffer offsets back to the user's exec list. */
ret = copy_to_user((struct drm_i915_relocation_entry __user *)
(uintptr_t) args->buffers_ptr,
struct drm_i915_gem_object *obj_priv = obj->driver_private;
int ret;
+ i915_verify_inactive(dev, __FILE__, __LINE__);
if (obj_priv->gtt_space == NULL) {
ret = i915_gem_object_bind_to_gtt(obj, alignment);
if (ret != 0) {
if (!obj_priv->active && obj->write_domain == 0)
list_del_init(&obj_priv->list);
}
+ i915_verify_inactive(dev, __FILE__, __LINE__);
return 0;
}
drm_i915_private_t *dev_priv = dev->dev_private;
struct drm_i915_gem_object *obj_priv = obj->driver_private;
+ i915_verify_inactive(dev, __FILE__, __LINE__);
obj_priv->pin_count--;
BUG_ON(obj_priv->pin_count < 0);
BUG_ON(obj_priv->gtt_space == NULL);
-
+
/* If the object is no longer pinned, and is
* neither active nor being flushed, then stick it on
* the inactive list
atomic_dec(&dev->pin_count);
atomic_sub(obj->size, &dev->pin_memory);
}
+ i915_verify_inactive(dev, __FILE__, __LINE__);
}
int