diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2019-12-23 02:35:58 +0300 |
---|---|---|
committer | Chris Wilson <chris@chris-wilson.co.uk> | 2019-12-23 16:08:47 +0300 |
commit | 6a8679c048eb104dbcc6aa43a0baa7450de46503 (patch) | |
tree | 5a8d237b517620b18fa9d8518d3a2272d1008366 /drivers/gpu/drm/i915/i915_gpu_error.c | |
parent | 76f9764cc3d538435262dea885bf69fac2415402 (diff) | |
download | linux-6a8679c048eb104dbcc6aa43a0baa7450de46503.tar.xz |
drm/i915: Mark the GEM context link as RCU protected
The only protection for intel_context.gem_cotext is granted by RCU, so
annotate it as a rcu protected pointer and carefully dereference it in
the few occasions we need to use it.
Fixes: 9f3ccd40acf4 ("drm/i915: Drop GEM context as a direct link from i915_request")
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Cc: Andi Shyti <andi.shyti@intel.com>
Acked-by: Andi Shyti <andi.shyti@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20191222233558.2201901-1-chris@chris-wilson.co.uk
Diffstat (limited to 'drivers/gpu/drm/i915/i915_gpu_error.c')
-rw-r--r-- | drivers/gpu/drm/i915/i915_gpu_error.c | 40 |
1 files changed, 26 insertions, 14 deletions
diff --git a/drivers/gpu/drm/i915/i915_gpu_error.c b/drivers/gpu/drm/i915/i915_gpu_error.c index 7e2cb063110c..fda0977d2059 100644 --- a/drivers/gpu/drm/i915/i915_gpu_error.c +++ b/drivers/gpu/drm/i915/i915_gpu_error.c @@ -1221,7 +1221,7 @@ static void error_record_engine_registers(struct i915_gpu_state *error, static void record_request(const struct i915_request *request, struct drm_i915_error_request *erq) { - const struct i915_gem_context *ctx = request->context->gem_context; + const struct i915_gem_context *ctx; erq->flags = request->fence.flags; erq->context = request->fence.context; @@ -1231,7 +1231,13 @@ static void record_request(const struct i915_request *request, erq->start = i915_ggtt_offset(request->ring->vma); erq->head = request->head; erq->tail = request->tail; - erq->pid = ctx && ctx->pid ? pid_nr(ctx->pid) : 0; + + erq->pid = 0; + rcu_read_lock(); + ctx = rcu_dereference(request->context->gem_context); + if (ctx) + erq->pid = pid_nr(ctx->pid); + rcu_read_unlock(); } static void engine_record_requests(struct intel_engine_cs *engine, @@ -1298,28 +1304,34 @@ static void error_record_engine_execlists(const struct intel_engine_cs *engine, static bool record_context(struct drm_i915_error_context *e, const struct i915_request *rq) { - const struct i915_gem_context *ctx = rq->context->gem_context; + struct i915_gem_context *ctx; + struct task_struct *task; + bool capture; + rcu_read_lock(); + ctx = rcu_dereference(rq->context->gem_context); + if (ctx && !kref_get_unless_zero(&ctx->ref)) + ctx = NULL; + rcu_read_unlock(); if (!ctx) return false; - if (ctx->pid) { - struct task_struct *task; - - rcu_read_lock(); - task = pid_task(ctx->pid, PIDTYPE_PID); - if (task) { - strcpy(e->comm, task->comm); - e->pid = task->pid; - } - rcu_read_unlock(); + rcu_read_lock(); + task = pid_task(ctx->pid, PIDTYPE_PID); + if (task) { + strcpy(e->comm, task->comm); + e->pid = task->pid; } + rcu_read_unlock(); e->sched_attr = ctx->sched; e->guilty = atomic_read(&ctx->guilty_count); e->active = atomic_read(&ctx->active_count); - return i915_gem_context_no_error_capture(ctx); + capture = i915_gem_context_no_error_capture(ctx); + + i915_gem_context_put(ctx); + return capture; } struct capture_vma { |