aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2016-09-09 09:11:50 -0400
committerChris Wilson <chris@chris-wilson.co.uk>2016-09-09 09:23:03 -0400
commit22dd3bb9190566c7c3b80edb7dea67d1e21d0f91 (patch)
tree01898a53077a19a7c4608716a7c638924bc0992b /drivers/gpu/drm
parentea746f3659232b3104d9534d5a7ebd9934ae1dd6 (diff)
drm/i915: Mark up all locked waiters
In the next patch we want to handle reset directly by a locked waiter in order to avoid issues with returning before the reset is handled. To handle the reset, we must first know whether we hold the struct_mutex. If we do not hold the struct_mtuex we can not perform the reset, but we do not block the reset worker either (and so we can just continue to wait for request completion) - otherwise we must relinquish the mutex. Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> Reviewed-by: Mika Kuoppala <mika.kuoppala@intel.com> Link: http://patchwork.freedesktop.org/patch/msgid/20160909131201.16673-10-chris@chris-wilson.co.uk
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r--drivers/gpu/drm/i915/i915_debugfs.c4
-rw-r--r--drivers/gpu/drm/i915/i915_gem.c7
-rw-r--r--drivers/gpu/drm/i915/i915_gem_evict.c8
-rw-r--r--drivers/gpu/drm/i915/i915_gem_gtt.c2
-rw-r--r--drivers/gpu/drm/i915/i915_gem_request.c15
-rw-r--r--drivers/gpu/drm/i915/i915_gem_request.h11
-rw-r--r--drivers/gpu/drm/i915/i915_gem_shrinker.c2
-rw-r--r--drivers/gpu/drm/i915/intel_ringbuffer.c3
8 files changed, 38 insertions, 14 deletions
diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c
index 0e4cbad7a883..6a270bc0fdb3 100644
--- a/drivers/gpu/drm/i915/i915_debugfs.c
+++ b/drivers/gpu/drm/i915/i915_debugfs.c
@@ -4794,7 +4794,9 @@ i915_drop_caches_set(void *data, u64 val)
4794 return ret; 4794 return ret;
4795 4795
4796 if (val & DROP_ACTIVE) { 4796 if (val & DROP_ACTIVE) {
4797 ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); 4797 ret = i915_gem_wait_for_idle(dev_priv,
4798 I915_WAIT_INTERRUPTIBLE |
4799 I915_WAIT_LOCKED);
4798 if (ret) 4800 if (ret)
4799 goto unlock; 4801 goto unlock;
4800 } 4802 }
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c
index 4617250c3000..23069a2d2850 100644
--- a/drivers/gpu/drm/i915/i915_gem.c
+++ b/drivers/gpu/drm/i915/i915_gem.c
@@ -2802,7 +2802,8 @@ __i915_gem_object_sync(struct drm_i915_gem_request *to,
2802 2802
2803 if (!i915.semaphores) { 2803 if (!i915.semaphores) {
2804 ret = i915_wait_request(from, 2804 ret = i915_wait_request(from,
2805 from->i915->mm.interruptible, 2805 from->i915->mm.interruptible |
2806 I915_WAIT_LOCKED,
2806 NULL, 2807 NULL,
2807 NO_WAITBOOST); 2808 NO_WAITBOOST);
2808 if (ret) 2809 if (ret)
@@ -4304,7 +4305,9 @@ int i915_gem_suspend(struct drm_device *dev)
4304 if (ret) 4305 if (ret)
4305 goto err; 4306 goto err;
4306 4307
4307 ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); 4308 ret = i915_gem_wait_for_idle(dev_priv,
4309 I915_WAIT_INTERRUPTIBLE |
4310 I915_WAIT_LOCKED);
4308 if (ret) 4311 if (ret)
4309 goto err; 4312 goto err;
4310 4313
diff --git a/drivers/gpu/drm/i915/i915_gem_evict.c b/drivers/gpu/drm/i915/i915_gem_evict.c
index 103085246975..5b6f81c1dbca 100644
--- a/drivers/gpu/drm/i915/i915_gem_evict.c
+++ b/drivers/gpu/drm/i915/i915_gem_evict.c
@@ -170,7 +170,9 @@ search_again:
170 if (ret) 170 if (ret)
171 return ret; 171 return ret;
172 172
173 ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); 173 ret = i915_gem_wait_for_idle(dev_priv,
174 I915_WAIT_INTERRUPTIBLE |
175 I915_WAIT_LOCKED);
174 if (ret) 176 if (ret)
175 return ret; 177 return ret;
176 178
@@ -275,7 +277,9 @@ int i915_gem_evict_vm(struct i915_address_space *vm, bool do_idle)
275 return ret; 277 return ret;
276 } 278 }
277 279
278 ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_INTERRUPTIBLE); 280 ret = i915_gem_wait_for_idle(dev_priv,
281 I915_WAIT_INTERRUPTIBLE |
282 I915_WAIT_LOCKED);
279 if (ret) 283 if (ret)
280 return ret; 284 return ret;
281 285
diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c
index 9bcac52b8268..f3c6876da521 100644
--- a/drivers/gpu/drm/i915/i915_gem_gtt.c
+++ b/drivers/gpu/drm/i915/i915_gem_gtt.c
@@ -2683,7 +2683,7 @@ void i915_gem_gtt_finish_object(struct drm_i915_gem_object *obj)
2683 struct i915_ggtt *ggtt = &dev_priv->ggtt; 2683 struct i915_ggtt *ggtt = &dev_priv->ggtt;
2684 2684
2685 if (unlikely(ggtt->do_idle_maps)) { 2685 if (unlikely(ggtt->do_idle_maps)) {
2686 if (i915_gem_wait_for_idle(dev_priv, 0)) { 2686 if (i915_gem_wait_for_idle(dev_priv, I915_WAIT_LOCKED)) {
2687 DRM_ERROR("Failed to wait for idle; VT'd may hang.\n"); 2687 DRM_ERROR("Failed to wait for idle; VT'd may hang.\n");
2688 /* Wait a bit, in hopes it avoids the hang */ 2688 /* Wait a bit, in hopes it avoids the hang */
2689 udelay(10); 2689 udelay(10);
diff --git a/drivers/gpu/drm/i915/i915_gem_request.c b/drivers/gpu/drm/i915/i915_gem_request.c
index f4c15f319d08..5f89801e6a16 100644
--- a/drivers/gpu/drm/i915/i915_gem_request.c
+++ b/drivers/gpu/drm/i915/i915_gem_request.c
@@ -260,7 +260,9 @@ static int i915_gem_init_seqno(struct drm_i915_private *dev_priv, u32 seqno)
260 260
261 /* Carefully retire all requests without writing to the rings */ 261 /* Carefully retire all requests without writing to the rings */
262 for_each_engine(engine, dev_priv) { 262 for_each_engine(engine, dev_priv) {
263 ret = intel_engine_idle(engine, I915_WAIT_INTERRUPTIBLE); 263 ret = intel_engine_idle(engine,
264 I915_WAIT_INTERRUPTIBLE |
265 I915_WAIT_LOCKED);
264 if (ret) 266 if (ret)
265 return ret; 267 return ret;
266 } 268 }
@@ -625,6 +627,10 @@ int i915_wait_request(struct drm_i915_gem_request *req,
625 int ret = 0; 627 int ret = 0;
626 628
627 might_sleep(); 629 might_sleep();
630#if IS_ENABLED(CONFIG_LOCKDEP)
631 GEM_BUG_ON(!!lockdep_is_held(&req->i915->drm.struct_mutex) !=
632 !!(flags & I915_WAIT_LOCKED));
633#endif
628 634
629 if (i915_gem_request_completed(req)) 635 if (i915_gem_request_completed(req))
630 return 0; 636 return 0;
@@ -667,7 +673,8 @@ int i915_wait_request(struct drm_i915_gem_request *req,
667 goto complete; 673 goto complete;
668 674
669 set_current_state(state); 675 set_current_state(state);
670 add_wait_queue(&req->i915->gpu_error.wait_queue, &reset); 676 if (flags & I915_WAIT_LOCKED)
677 add_wait_queue(&req->i915->gpu_error.wait_queue, &reset);
671 678
672 intel_wait_init(&wait, req->fence.seqno); 679 intel_wait_init(&wait, req->fence.seqno);
673 if (intel_engine_add_wait(req->engine, &wait)) 680 if (intel_engine_add_wait(req->engine, &wait))
@@ -707,10 +714,12 @@ wakeup:
707 if (i915_spin_request(req, state, 2)) 714 if (i915_spin_request(req, state, 2))
708 break; 715 break;
709 } 716 }
710 remove_wait_queue(&req->i915->gpu_error.wait_queue, &reset);
711 717
712 intel_engine_remove_wait(req->engine, &wait); 718 intel_engine_remove_wait(req->engine, &wait);
719 if (flags & I915_WAIT_LOCKED)
720 remove_wait_queue(&req->i915->gpu_error.wait_queue, &reset);
713 __set_current_state(TASK_RUNNING); 721 __set_current_state(TASK_RUNNING);
722
714complete: 723complete:
715 trace_i915_gem_request_wait_end(req); 724 trace_i915_gem_request_wait_end(req);
716 725
diff --git a/drivers/gpu/drm/i915/i915_gem_request.h b/drivers/gpu/drm/i915/i915_gem_request.h
index 479896ef791e..def35721e9ed 100644
--- a/drivers/gpu/drm/i915/i915_gem_request.h
+++ b/drivers/gpu/drm/i915/i915_gem_request.h
@@ -222,7 +222,8 @@ int i915_wait_request(struct drm_i915_gem_request *req,
222 s64 *timeout, 222 s64 *timeout,
223 struct intel_rps_client *rps) 223 struct intel_rps_client *rps)
224 __attribute__((nonnull(1))); 224 __attribute__((nonnull(1)));
225#define I915_WAIT_INTERRUPTIBLE BIT(0) 225#define I915_WAIT_INTERRUPTIBLE BIT(0)
226#define I915_WAIT_LOCKED BIT(1) /* struct_mutex held, handle GPU reset */
226 227
227static inline u32 intel_engine_get_seqno(struct intel_engine_cs *engine); 228static inline u32 intel_engine_get_seqno(struct intel_engine_cs *engine);
228 229
@@ -576,7 +577,9 @@ i915_gem_active_wait(const struct i915_gem_active *active, struct mutex *mutex)
576 if (!request) 577 if (!request)
577 return 0; 578 return 0;
578 579
579 return i915_wait_request(request, I915_WAIT_INTERRUPTIBLE, NULL, NULL); 580 return i915_wait_request(request,
581 I915_WAIT_INTERRUPTIBLE | I915_WAIT_LOCKED,
582 NULL, NULL);
580} 583}
581 584
582/** 585/**
@@ -639,7 +642,9 @@ i915_gem_active_retire(struct i915_gem_active *active,
639 if (!request) 642 if (!request)
640 return 0; 643 return 0;
641 644
642 ret = i915_wait_request(request, I915_WAIT_INTERRUPTIBLE, NULL, NULL); 645 ret = i915_wait_request(request,
646 I915_WAIT_INTERRUPTIBLE | I915_WAIT_LOCKED,
647 NULL, NULL);
643 if (ret) 648 if (ret)
644 return ret; 649 return ret;
645 650
diff --git a/drivers/gpu/drm/i915/i915_gem_shrinker.c b/drivers/gpu/drm/i915/i915_gem_shrinker.c
index 35a05f4c51c1..1c237d02f30b 100644
--- a/drivers/gpu/drm/i915/i915_gem_shrinker.c
+++ b/drivers/gpu/drm/i915/i915_gem_shrinker.c
@@ -414,7 +414,7 @@ i915_gem_shrinker_vmap(struct notifier_block *nb, unsigned long event, void *ptr
414 return NOTIFY_DONE; 414 return NOTIFY_DONE;
415 415
416 /* Force everything onto the inactive lists */ 416 /* Force everything onto the inactive lists */
417 ret = i915_gem_wait_for_idle(dev_priv, 0); 417 ret = i915_gem_wait_for_idle(dev_priv, I915_WAIT_LOCKED);
418 if (ret) 418 if (ret)
419 goto out; 419 goto out;
420 420
diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c
index a5bf18877068..8687a84a7ff3 100644
--- a/drivers/gpu/drm/i915/intel_ringbuffer.c
+++ b/drivers/gpu/drm/i915/intel_ringbuffer.c
@@ -2223,7 +2223,8 @@ static int wait_for_space(struct drm_i915_gem_request *req, int bytes)
2223 if (WARN_ON(&target->ring_link == &ring->request_list)) 2223 if (WARN_ON(&target->ring_link == &ring->request_list))
2224 return -ENOSPC; 2224 return -ENOSPC;
2225 2225
2226 ret = i915_wait_request(target, I915_WAIT_INTERRUPTIBLE, 2226 ret = i915_wait_request(target,
2227 I915_WAIT_INTERRUPTIBLE | I915_WAIT_LOCKED,
2227 NULL, NO_WAITBOOST); 2228 NULL, NO_WAITBOOST);
2228 if (ret) 2229 if (ret)
2229 return ret; 2230 return ret;