- transition from "ioctl" interface Signed-off-by: Ben Skeggs <bskeggs@xxxxxxxxxx> --- drivers/gpu/drm/nouveau/include/nvif/device.h | 4 ++ .../gpu/drm/nouveau/include/nvif/driverif.h | 6 +++ drivers/gpu/drm/nouveau/nouveau_chan.c | 11 +++-- drivers/gpu/drm/nouveau/nouveau_chan.h | 3 +- drivers/gpu/drm/nouveau/nvif/device.c | 17 ++++++++ drivers/gpu/drm/nouveau/nvkm/device/user.c | 41 ++++++++++++++++++- 6 files changed, 73 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/drm/nouveau/include/nvif/device.h b/drivers/gpu/drm/nouveau/include/nvif/device.h index fa8402e575da..5fb71e6da7cd 100644 --- a/drivers/gpu/drm/nouveau/include/nvif/device.h +++ b/drivers/gpu/drm/nouveau/include/nvif/device.h @@ -5,6 +5,7 @@ #include <nvif/cl0080.h> #include <nvif/driverif.h> #include <nvif/user.h> +struct nvif_ctxdma; struct nvif_device { const struct nvif_device_impl *impl; @@ -22,6 +23,9 @@ void nvif_device_dtor(struct nvif_device *); int nvif_device_map(struct nvif_device *); u64 nvif_device_time(struct nvif_device *); +int nvif_device_ctxdma_ctor(struct nvif_device *, const char *name, s32 oclass, + void *argv, u32 argc, struct nvif_ctxdma *); + /*XXX*/ #include <subdev/bios.h> #include <subdev/fb.h> diff --git a/drivers/gpu/drm/nouveau/include/nvif/driverif.h b/drivers/gpu/drm/nouveau/include/nvif/driverif.h index 75168621427a..c1971b85d927 100644 --- a/drivers/gpu/drm/nouveau/include/nvif/driverif.h +++ b/drivers/gpu/drm/nouveau/include/nvif/driverif.h @@ -507,6 +507,12 @@ struct nvif_device_impl { const struct nvif_disp_impl **, struct nvif_disp_priv **); } disp; + struct { + int (*new)(struct nvif_device_priv *, s32 oclass, void *argv, u32 argc, + const struct nvif_ctxdma_impl **, struct nvif_ctxdma_priv **, + u64 handle); + } ctxdma; + struct nvif_device_impl_fifo { u8 engine_nr; u8 runl_nr; diff --git a/drivers/gpu/drm/nouveau/nouveau_chan.c b/drivers/gpu/drm/nouveau/nouveau_chan.c index 771a4b4b3f1d..7c57bc48a8af 100644 --- a/drivers/gpu/drm/nouveau/nouveau_chan.c +++ b/drivers/gpu/drm/nouveau/nouveau_chan.c @@ -106,7 +106,7 @@ nouveau_channel_del(struct nouveau_channel **pchan) nvif_object_unmap_cpu(&chan->userd.map); nvif_object_dtor(&chan->user); nvif_mem_dtor(&chan->userd.mem); - nvif_object_dtor(&chan->push.ctxdma); + nvif_ctxdma_dtor(&chan->push.ctxdma); nouveau_vma_del(&chan->push.vma); nouveau_bo_unmap(chan->push.buffer); if (chan->push.buffer && chan->push.buffer->bo.pin_count) @@ -242,9 +242,8 @@ nouveau_channel_prep(struct nouveau_cli *cli, } } - ret = nvif_object_ctor(&device->object, "abi16PushCtxDma", 0, - NV_DMA_FROM_MEMORY, &args, sizeof(args), - &chan->push.ctxdma); + ret = nvif_device_ctxdma_ctor(device, "abi16PushCtxDma", NV_DMA_FROM_MEMORY, + &args, sizeof(args), &chan->push.ctxdma); if (ret) { nouveau_channel_del(pchan); return ret; @@ -315,13 +314,13 @@ nouveau_channel_ctor(struct nouveau_cli *cli, bool priv, u64 runm, args.chan.devm = BIT(0); if (oclass < NV50_CHANNEL_GPFIFO) { args.chan.vmm = 0; - args.chan.ctxdma = nvif_handle(&chan->push.ctxdma); + args.chan.ctxdma = nvif_handle(&chan->push.ctxdma.object); args.chan.offset = chan->push.addr; args.chan.length = 0; } else { args.chan.vmm = nvif_handle(&chan->vmm->vmm.object); if (oclass < FERMI_CHANNEL_GPFIFO) - args.chan.ctxdma = nvif_handle(&chan->push.ctxdma); + args.chan.ctxdma = nvif_handle(&chan->push.ctxdma.object); else args.chan.ctxdma = 0; args.chan.offset = ioffset + chan->push.addr; diff --git a/drivers/gpu/drm/nouveau/nouveau_chan.h b/drivers/gpu/drm/nouveau/nouveau_chan.h index 811271ae6fe1..786c929843d1 100644 --- a/drivers/gpu/drm/nouveau/nouveau_chan.h +++ b/drivers/gpu/drm/nouveau/nouveau_chan.h @@ -2,6 +2,7 @@ #ifndef __NOUVEAU_CHAN_H__ #define __NOUVEAU_CHAN_H__ #include <nvif/object.h> +#include <nvif/ctxdma.h> #include <nvif/event.h> #include <nvif/push.h> struct nvif_device; @@ -31,7 +32,7 @@ struct nouveau_channel { struct { struct nouveau_bo *buffer; struct nouveau_vma *vma; - struct nvif_object ctxdma; + struct nvif_ctxdma ctxdma; u64 addr; } push; diff --git a/drivers/gpu/drm/nouveau/nvif/device.c b/drivers/gpu/drm/nouveau/nvif/device.c index 7d057691600f..555c63e96660 100644 --- a/drivers/gpu/drm/nouveau/nvif/device.c +++ b/drivers/gpu/drm/nouveau/nvif/device.c @@ -23,8 +23,25 @@ */ #include <nvif/device.h> #include <nvif/client.h> +#include <nvif/ctxdma.h> #include <nvif/printf.h> +int +nvif_device_ctxdma_ctor(struct nvif_device *device, const char *name, s32 oclass, + void *argv, u32 argc, struct nvif_ctxdma *ctxdma) +{ + int ret; + + ret = device->impl->ctxdma.new(device->priv, oclass, argv, argc, + &ctxdma->impl, &ctxdma->priv, nvif_handle(&ctxdma->object)); + NVIF_ERRON(ret, &device->object, "[NEW ctxdma%04x]", oclass); + if (ret) + return ret; + + nvif_ctxdma_ctor(&device->object, name ?: "nvifDeviceCtxDma", 0, oclass, ctxdma); + return 0; +} + u64 nvif_device_time(struct nvif_device *device) { diff --git a/drivers/gpu/drm/nouveau/nvkm/device/user.c b/drivers/gpu/drm/nouveau/nvkm/device/user.c index f76861945cd0..fc81d595bdb7 100644 --- a/drivers/gpu/drm/nouveau/nvkm/device/user.c +++ b/drivers/gpu/drm/nouveau/nvkm/device/user.c @@ -111,6 +111,42 @@ nvkm_udevice_cgrp_new(struct nvif_device_priv *udev, u8 runl, struct nvif_vmm_pr return 0; } +#include <engine/dma/priv.h> + +static void +nvkm_udevice_ctxdma_del(struct nvif_ctxdma_priv *priv) +{ + struct nvkm_dmaobj *dmaobj = (void *)priv; + struct nvkm_object *object = &dmaobj->object; + + nvkm_object_del(&object); +} + +static const struct nvif_ctxdma_impl +nvkm_udevice_ctxdma_impl = { + .del = nvkm_udevice_ctxdma_del +}; + +static int +nvkm_udevice_ctxdma_new(struct nvif_device_priv *udev, s32 oclass, void *argv, u32 argc, + const struct nvif_ctxdma_impl **pimpl, struct nvif_ctxdma_priv **ppriv, + u64 handle) +{ + struct nvkm_dma *dma = udev->device->dma; + struct nvkm_dmaobj *dmaobj; + int ret; + + ret = dma->func->class_new(dma, &(struct nvkm_oclass) { .base.oclass = oclass }, + argv, argc, &dmaobj); + if (ret) + return ret; + + *pimpl = &nvkm_udevice_ctxdma_impl; + *ppriv = (void *)dmaobj; + + return nvkm_object_link_rb(udev->object.client, &udev->object, handle, &dmaobj->object); +} + static int nvkm_udevice_disp_new(struct nvif_device_priv *udev, const struct nvif_disp_impl **pimpl, struct nvif_disp_priv **ppriv) @@ -217,8 +253,7 @@ nvkm_udevice_child_get(struct nvkm_object *object, int index, struct nvif_device_priv *udev = container_of(object, typeof(*udev), object); struct nvkm_device *device = udev->device; struct nvkm_engine *engine; - u64 mask = (1ULL << NVKM_ENGINE_DMAOBJ) | - (1ULL << NVKM_ENGINE_FIFO); + u64 mask = (1ULL << NVKM_ENGINE_FIFO); const struct nvkm_device_oclass *sclass = NULL; int i; @@ -353,6 +388,8 @@ nvkm_udevice_new(struct nvkm_device *device, } if (device->fifo) { + udev->impl.ctxdma.new = nvkm_udevice_ctxdma_new; + if (!WARN_ON(nvkm_subdev_oneinit(&device->fifo->engine.subdev))) { nvkm_ufifo_ctor(device->fifo, &udev->impl.fifo); -- 2.41.0