[PATCH 30/39] drm/i915: Acquire the object lock around page directories

Chris Wilson chris at chris-wilson.co.uk
Sun Aug 9 15:16:40 UTC 2020


Now that the page directories are backed by an object, and we wish to
acquire multiple objects together under the same acquire context, teach
i915_vm_map_pt_stash() to use i915_acquire_ctx.

Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>
---
 .../gpu/drm/i915/gem/i915_gem_execbuffer.c    |  2 +-
 drivers/gpu/drm/i915/gt/intel_gtt.c           | 14 +++++++-
 drivers/gpu/drm/i915/gt/intel_gtt.h           |  4 +++
 drivers/gpu/drm/i915/gt/intel_ppgtt.c         | 34 +++++++++++++++++--
 4 files changed, 49 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/gem/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/gem/i915_gem_execbuffer.c
index 0665a38618dd..54e31d359c25 100644
--- a/drivers/gpu/drm/i915/gem/i915_gem_execbuffer.c
+++ b/drivers/gpu/drm/i915/gem/i915_gem_execbuffer.c
@@ -1450,7 +1450,7 @@ static int eb_reserve_vm(struct i915_execbuffer *eb)
 			return eb_vm_work_cancel(work, err);
 
 		/* We also need to prepare mappings to write the PD pages */
-		err = i915_vm_map_pt_stash(work->vm, &work->stash);
+		err = __i915_vm_map_pt_stash_locked(work->vm, &work->stash);
 		if (err)
 			return eb_vm_work_cancel(work, err);
 
diff --git a/drivers/gpu/drm/i915/gt/intel_gtt.c b/drivers/gpu/drm/i915/gt/intel_gtt.c
index 1a7efbad8f74..b0629de490a3 100644
--- a/drivers/gpu/drm/i915/gt/intel_gtt.c
+++ b/drivers/gpu/drm/i915/gt/intel_gtt.c
@@ -19,7 +19,8 @@ struct drm_i915_gem_object *alloc_pt_dma(struct i915_address_space *vm, int sz)
 	return i915_gem_object_create_internal(vm->i915, sz);
 }
 
-int map_pt_dma(struct i915_address_space *vm, struct drm_i915_gem_object *obj)
+int __map_pt_dma_locked(struct i915_address_space *vm,
+			struct drm_i915_gem_object *obj)
 {
 	void *vaddr;
 
@@ -31,6 +32,17 @@ int map_pt_dma(struct i915_address_space *vm, struct drm_i915_gem_object *obj)
 	return 0;
 }
 
+int map_pt_dma(struct i915_address_space *vm, struct drm_i915_gem_object *obj)
+{
+	int err;
+
+	i915_gem_object_lock(obj);
+	err = __map_pt_dma_locked(vm, obj);
+	i915_gem_object_unlock(obj);
+
+	return err;
+}
+
 void __i915_vm_close(struct i915_address_space *vm)
 {
 	struct i915_vma *vma, *vn;
diff --git a/drivers/gpu/drm/i915/gt/intel_gtt.h b/drivers/gpu/drm/i915/gt/intel_gtt.h
index c659dbd6cda2..b4e1519e4028 100644
--- a/drivers/gpu/drm/i915/gt/intel_gtt.h
+++ b/drivers/gpu/drm/i915/gt/intel_gtt.h
@@ -525,6 +525,8 @@ struct i915_page_directory *alloc_pd(struct i915_address_space *vm);
 struct i915_page_directory *__alloc_pd(int npde);
 
 int map_pt_dma(struct i915_address_space *vm, struct drm_i915_gem_object *obj);
+int __map_pt_dma_locked(struct i915_address_space *vm,
+			struct drm_i915_gem_object *obj);
 
 void free_px(struct i915_address_space *vm,
 	     struct i915_page_table *pt, int lvl);
@@ -573,6 +575,8 @@ int i915_vm_alloc_pt_stash(struct i915_address_space *vm,
 			   u64 size);
 int i915_vm_map_pt_stash(struct i915_address_space *vm,
 			 struct i915_vm_pt_stash *stash);
+int __i915_vm_map_pt_stash_locked(struct i915_address_space *vm,
+				  struct i915_vm_pt_stash *stash);
 void i915_vm_free_pt_stash(struct i915_address_space *vm,
 			   struct i915_vm_pt_stash *stash);
 
diff --git a/drivers/gpu/drm/i915/gt/intel_ppgtt.c b/drivers/gpu/drm/i915/gt/intel_ppgtt.c
index 11e7288464c0..ada894885795 100644
--- a/drivers/gpu/drm/i915/gt/intel_ppgtt.c
+++ b/drivers/gpu/drm/i915/gt/intel_ppgtt.c
@@ -5,6 +5,8 @@
 
 #include <linux/slab.h>
 
+#include "mm/i915_acquire_ctx.h"
+
 #include "i915_trace.h"
 #include "intel_gtt.h"
 #include "gen6_ppgtt.h"
@@ -253,15 +255,15 @@ int i915_vm_alloc_pt_stash(struct i915_address_space *vm,
 	return 0;
 }
 
-int i915_vm_map_pt_stash(struct i915_address_space *vm,
-			 struct i915_vm_pt_stash *stash)
+int __i915_vm_map_pt_stash_locked(struct i915_address_space *vm,
+				  struct i915_vm_pt_stash *stash)
 {
 	struct i915_page_table *pt;
 	int n, err;
 
 	for (n = 0; n < ARRAY_SIZE(stash->pt); n++) {
 		for (pt = stash->pt[n]; pt; pt = pt->stash) {
-			err = map_pt_dma(vm, pt->base);
+			err = __map_pt_dma_locked(vm, pt->base);
 			if (err)
 				return err;
 		}
@@ -270,6 +272,32 @@ int i915_vm_map_pt_stash(struct i915_address_space *vm,
 	return 0;
 }
 
+int i915_vm_map_pt_stash(struct i915_address_space *vm,
+			 struct i915_vm_pt_stash *stash)
+{
+	struct i915_acquire_ctx acquire;
+	struct i915_page_table *pt;
+	int n, err;
+
+	/* Acquire all the pages for the page directories simultaneously */
+	i915_acquire_ctx_init(&acquire);
+	for (n = 0; n < ARRAY_SIZE(stash->pt); n++) {
+		for (pt = stash->pt[n]; pt; pt = pt->stash) {
+			err = i915_acquire_ctx_lock(&acquire, pt->base);
+			if (err)
+				goto out;
+		}
+	}
+
+	err = i915_acquire_mm(&acquire);
+	if (err == 0)
+		err = __i915_vm_map_pt_stash_locked(vm, stash);
+
+out:
+	i915_acquire_ctx_fini(&acquire);
+	return err;
+}
+
 void i915_vm_free_pt_stash(struct i915_address_space *vm,
 			   struct i915_vm_pt_stash *stash)
 {
-- 
2.20.1



More information about the Intel-gfx-trybot mailing list