Blob Blame History Raw
From: Ben Skeggs <bskeggs@redhat.com>
Date: Wed, 1 Nov 2017 03:56:19 +1000
Subject: drm/nouveau/imem: separate suspend/resume backup handling into their
 own functions
Git-commit: d52ddc953e7f74a8271c88fc0aa3bd0d436b04f0
Patch-mainline: v4.15-rc1
References: FATE#326289 FATE#326079 FATE#326049 FATE#322398 FATE#326166

Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Acked-by: Petr Tesarik <ptesarik@suse.com>
---
 drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c |   76 ++++++++++++---------
 1 file changed, 46 insertions(+), 30 deletions(-)

--- a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c
@@ -28,6 +28,36 @@
 /******************************************************************************
  * instmem object base implementation
  *****************************************************************************/
+static void
+nvkm_instobj_load(struct nvkm_instobj *iobj)
+{
+	struct nvkm_memory *memory = &iobj->memory;
+	const u64 size = nvkm_memory_size(memory);
+	int i;
+
+	for (i = 0; i < size; i += 4)
+		nvkm_wo32(memory, i, iobj->suspend[i / 4]);
+	vfree(iobj->suspend);
+	iobj->suspend = NULL;
+}
+
+static int
+nvkm_instobj_save(struct nvkm_instobj *iobj)
+{
+	struct nvkm_memory *memory = &iobj->memory;
+	const u64 size = nvkm_memory_size(memory);
+	int i;
+
+	iobj->suspend = vmalloc(size);
+	if (!iobj->suspend)
+		return -ENOMEM;
+
+	for (i = 0; i < size; i += 4)
+		iobj->suspend[i / 4] = nvkm_ro32(memory, i);
+
+	return 0;
+}
+
 void
 nvkm_instobj_dtor(struct nvkm_instmem *imem, struct nvkm_instobj *iobj)
 {
@@ -104,34 +134,18 @@ nvkm_instmem_fini(struct nvkm_subdev *su
 {
 	struct nvkm_instmem *imem = nvkm_instmem(subdev);
 	struct nvkm_instobj *iobj;
-	int i;
-
-	if (imem->func->fini)
-		imem->func->fini(imem);
 
 	if (suspend) {
 		list_for_each_entry(iobj, &imem->list, head) {
-			struct nvkm_memory *memory = &iobj->memory;
-			u64 size = nvkm_memory_size(memory);
-
-			iobj->suspend = vmalloc(size);
-			if (!iobj->suspend)
-				return -ENOMEM;
-
-			for (i = 0; i < size; i += 4)
-				iobj->suspend[i / 4] = nvkm_ro32(memory, i);
+			int ret = nvkm_instobj_save(iobj);
+			if (ret)
+				return ret;
 		}
 	}
 
-	return 0;
-}
+	if (imem->func->fini)
+		imem->func->fini(imem);
 
-static int
-nvkm_instmem_oneinit(struct nvkm_subdev *subdev)
-{
-	struct nvkm_instmem *imem = nvkm_instmem(subdev);
-	if (imem->func->oneinit)
-		return imem->func->oneinit(imem);
 	return 0;
 }
 
@@ -140,22 +154,24 @@ nvkm_instmem_init(struct nvkm_subdev *su
 {
 	struct nvkm_instmem *imem = nvkm_instmem(subdev);
 	struct nvkm_instobj *iobj;
-	int i;
 
 	list_for_each_entry(iobj, &imem->list, head) {
-		if (iobj->suspend) {
-			struct nvkm_memory *memory = &iobj->memory;
-			u64 size = nvkm_memory_size(memory);
-			for (i = 0; i < size; i += 4)
-				nvkm_wo32(memory, i, iobj->suspend[i / 4]);
-			vfree(iobj->suspend);
-			iobj->suspend = NULL;
-		}
+		if (iobj->suspend)
+			nvkm_instobj_load(iobj);
 	}
 
 	return 0;
 }
 
+static int
+nvkm_instmem_oneinit(struct nvkm_subdev *subdev)
+{
+	struct nvkm_instmem *imem = nvkm_instmem(subdev);
+	if (imem->func->oneinit)
+		return imem->func->oneinit(imem);
+	return 0;
+}
+
 static void *
 nvkm_instmem_dtor(struct nvkm_subdev *subdev)
 {