Commit 12c9b05d authored by Ben Skeggs's avatar Ben Skeggs Committed by Lyude Paul

drm/nouveau/imem: support allocations not preserved across suspend

Will initially be used to tag some large grctx allocations which don't
need to be saved, to speedup suspend/resume.
Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
Reviewed-by: default avatarLyude Paul <lyude@redhat.com>
Acked-by: default avatarDanilo Krummrich <me@dakr.org>
Signed-off-by: default avatarLyude Paul <lyude@redhat.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20230919220442.202488-3-lyude@redhat.com
parent d79d9102
...@@ -12,6 +12,7 @@ struct nvkm_tags { ...@@ -12,6 +12,7 @@ struct nvkm_tags {
}; };
enum nvkm_memory_target { enum nvkm_memory_target {
NVKM_MEM_TARGET_INST_SR_LOST, /* instance memory - not preserved across suspend */
NVKM_MEM_TARGET_INST, /* instance memory */ NVKM_MEM_TARGET_INST, /* instance memory */
NVKM_MEM_TARGET_VRAM, /* video memory */ NVKM_MEM_TARGET_VRAM, /* video memory */
NVKM_MEM_TARGET_HOST, /* coherent system memory */ NVKM_MEM_TARGET_HOST, /* coherent system memory */
......
...@@ -26,7 +26,7 @@ struct nvkm_instmem { ...@@ -26,7 +26,7 @@ struct nvkm_instmem {
u32 nvkm_instmem_rd32(struct nvkm_instmem *, u32 addr); u32 nvkm_instmem_rd32(struct nvkm_instmem *, u32 addr);
void nvkm_instmem_wr32(struct nvkm_instmem *, u32 addr, u32 data); void nvkm_instmem_wr32(struct nvkm_instmem *, u32 addr, u32 data);
int nvkm_instobj_new(struct nvkm_instmem *, u32 size, u32 align, bool zero, int nvkm_instobj_new(struct nvkm_instmem *, u32 size, u32 align, bool zero, bool preserve,
struct nvkm_memory **); struct nvkm_memory **);
int nvkm_instobj_wrap(struct nvkm_device *, struct nvkm_memory *, struct nvkm_memory **); int nvkm_instobj_wrap(struct nvkm_device *, struct nvkm_memory *, struct nvkm_memory **);
......
...@@ -140,12 +140,23 @@ nvkm_memory_new(struct nvkm_device *device, enum nvkm_memory_target target, ...@@ -140,12 +140,23 @@ nvkm_memory_new(struct nvkm_device *device, enum nvkm_memory_target target,
{ {
struct nvkm_instmem *imem = device->imem; struct nvkm_instmem *imem = device->imem;
struct nvkm_memory *memory; struct nvkm_memory *memory;
bool preserve = true;
int ret; int ret;
if (unlikely(target != NVKM_MEM_TARGET_INST || !imem)) if (unlikely(!imem))
return -ENOSYS; return -ENOSYS;
ret = nvkm_instobj_new(imem, size, align, zero, &memory); switch (target) {
case NVKM_MEM_TARGET_INST_SR_LOST:
preserve = false;
break;
case NVKM_MEM_TARGET_INST:
break;
default:
return -ENOSYS;
}
ret = nvkm_instobj_new(imem, size, align, zero, preserve, &memory);
if (ret) if (ret)
return ret; return ret;
......
...@@ -94,15 +94,21 @@ nvkm_instobj_wrap(struct nvkm_device *device, ...@@ -94,15 +94,21 @@ nvkm_instobj_wrap(struct nvkm_device *device,
struct nvkm_memory *memory, struct nvkm_memory **pmemory) struct nvkm_memory *memory, struct nvkm_memory **pmemory)
{ {
struct nvkm_instmem *imem = device->imem; struct nvkm_instmem *imem = device->imem;
int ret;
if (!imem->func->memory_wrap) if (!imem->func->memory_wrap)
return -ENOSYS; return -ENOSYS;
return imem->func->memory_wrap(imem, memory, pmemory); ret = imem->func->memory_wrap(imem, memory, pmemory);
if (ret)
return ret;
container_of(*pmemory, struct nvkm_instobj, memory)->preserve = true;
return 0;
} }
int int
nvkm_instobj_new(struct nvkm_instmem *imem, u32 size, u32 align, bool zero, nvkm_instobj_new(struct nvkm_instmem *imem, u32 size, u32 align, bool zero, bool preserve,
struct nvkm_memory **pmemory) struct nvkm_memory **pmemory)
{ {
struct nvkm_subdev *subdev = &imem->subdev; struct nvkm_subdev *subdev = &imem->subdev;
...@@ -130,6 +136,7 @@ nvkm_instobj_new(struct nvkm_instmem *imem, u32 size, u32 align, bool zero, ...@@ -130,6 +136,7 @@ nvkm_instobj_new(struct nvkm_instmem *imem, u32 size, u32 align, bool zero,
nvkm_done(memory); nvkm_done(memory);
} }
container_of(memory, struct nvkm_instobj, memory)->preserve = preserve;
done: done:
if (ret) if (ret)
nvkm_memory_unref(&memory); nvkm_memory_unref(&memory);
...@@ -176,9 +183,11 @@ nvkm_instmem_fini(struct nvkm_subdev *subdev, bool suspend) ...@@ -176,9 +183,11 @@ nvkm_instmem_fini(struct nvkm_subdev *subdev, bool suspend)
if (suspend) { if (suspend) {
list_for_each_entry(iobj, &imem->list, head) { list_for_each_entry(iobj, &imem->list, head) {
int ret = nvkm_instobj_save(iobj); if (iobj->preserve) {
if (ret) int ret = nvkm_instobj_save(iobj);
return ret; if (ret)
return ret;
}
} }
nvkm_bar_bar2_fini(subdev->device); nvkm_bar_bar2_fini(subdev->device);
......
...@@ -25,6 +25,7 @@ void nvkm_instmem_boot(struct nvkm_instmem *); ...@@ -25,6 +25,7 @@ void nvkm_instmem_boot(struct nvkm_instmem *);
struct nvkm_instobj { struct nvkm_instobj {
struct nvkm_memory memory; struct nvkm_memory memory;
struct list_head head; struct list_head head;
bool preserve;
u32 *suspend; u32 *suspend;
}; };
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment