summaryrefslogtreecommitdiff
path: root/drivers/gpu/drm/i915/i915_gem.c
diff options
context:
space:
mode:
authorJohn Harrison <John.C.Harrison@Intel.com>2014-04-10 10:50:59 +0100
committerJohn Harrison <John.C.Harrison@Intel.com>2016-06-28 17:17:10 +0100
commitc5823a5f2d974eb849957ef7903ef8276fbf4167 (patch)
tree5749da170c3ba19b36d98d27e171649420dc74d5 /drivers/gpu/drm/i915/i915_gem.c
parentb9de2d722fcba76596650152475822edb0b8bf04 (diff)
drm/i915: Added scheduler flush calls to ring throttle and idle functions
When requesting that all GPU work is completed, it is now necessary to get the scheduler involved in order to flush out work that queued and not yet submitted. v2: Updated to add support for flushing the scheduler queue by time stamp rather than just doing a blanket flush. v3: Moved submit_max_priority() to this patch from an earlier patch is it is no longer required in the other. v4: Corrected the format of a comment to keep the style checker happy. Downgraded a BUG_ON to a WARN_ON as the latter is preferred. v5: Shuffled functions around to remove forward prototypes, removed similarly offensive white space and added documentation. Re-worked the mutex locking around the submit function. [Joonas Lahtinen] Used lighter weight spinlocks. For: VIZ-1587 Signed-off-by: John Harrison <John.C.Harrison@Intel.com> Cc: Joonas Lahtinen <joonas.lahtinen@linux.intel.com>
Diffstat (limited to 'drivers/gpu/drm/i915/i915_gem.c')
-rw-r--r--drivers/gpu/drm/i915/i915_gem.c24
1 files changed, 23 insertions, 1 deletions
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c
index 33c4e40f6844..682ca62f147d 100644
--- a/drivers/gpu/drm/i915/i915_gem.c
+++ b/drivers/gpu/drm/i915/i915_gem.c
@@ -3812,6 +3812,10 @@ int i915_gpu_idle(struct drm_device *dev)
/* Flush everything onto the inactive list. */
for_each_engine(engine, dev_priv, i) {
+ ret = i915_scheduler_flush(engine, true);
+ if (ret < 0)
+ return ret;
+
if (!i915.enable_execlists) {
struct drm_i915_gem_request *req;
@@ -4545,7 +4549,8 @@ i915_gem_ring_throttle(struct drm_device *dev, struct drm_file *file)
unsigned long recent_enough = jiffies - DRM_I915_THROTTLE_JIFFIES;
struct drm_i915_gem_request *request, *target = NULL;
unsigned reset_counter;
- int ret;
+ int i, ret;
+ struct intel_engine_cs *engine;
ret = i915_gem_wait_for_error(&dev_priv->gpu_error);
if (ret)
@@ -4555,6 +4560,23 @@ i915_gem_ring_throttle(struct drm_device *dev, struct drm_file *file)
if (ret)
return ret;
+ for_each_engine(engine, dev_priv, i) {
+ /*
+ * Flush out scheduler entries that are getting 'stale'. Note
+ * that the following recent_enough test will only check
+ * against the time at which the request was submitted to the
+ * hardware (i.e. when it left the scheduler) not the time it
+ * was submitted to the driver.
+ *
+ * Also, there is not much point worring about busy return
+ * codes from the scheduler flush call. Even if more work
+ * cannot be submitted right now for whatever reason, we
+ * still want to throttle against stale work that has already
+ * been submitted.
+ */
+ i915_scheduler_flush_stamp(engine, recent_enough, false);
+ }
+
spin_lock(&file_priv->mm.lock);
list_for_each_entry(request, &file_priv->mm.request_list, client_list) {
if (time_after_eq(request->emitted_jiffies, recent_enough))