diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/gpu/drm/nouveau/include/nvif/class.h | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/include/nvif/clc36f.h | 19 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_chan.c | 16 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_chan.h | 1 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_dma.c | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nvkm/engine/fifo/chan.h | 1 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nvkm/engine/fifo/changk104.h | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nvkm/engine/fifo/gpfifogv100.c | 31 |
8 files changed, 63 insertions, 13 deletions
diff --git a/drivers/gpu/drm/nouveau/include/nvif/class.h b/drivers/gpu/drm/nouveau/include/nvif/class.h index 6db56bd7d67e..d60c0f023dbf 100644 --- a/drivers/gpu/drm/nouveau/include/nvif/class.h +++ b/drivers/gpu/drm/nouveau/include/nvif/class.h @@ -68,7 +68,7 @@ #define KEPLER_CHANNEL_GPFIFO_B /* cla06f.h */ 0x0000a16f #define MAXWELL_CHANNEL_GPFIFO_A /* cla06f.h */ 0x0000b06f #define PASCAL_CHANNEL_GPFIFO_A /* cla06f.h */ 0x0000c06f -#define VOLTA_CHANNEL_GPFIFO_A /* cla06f.h */ 0x0000c36f +#define VOLTA_CHANNEL_GPFIFO_A /* clc36f.h */ 0x0000c36f #define NV50_DISP /* cl5070.h */ 0x00005070 #define G82_DISP /* cl5070.h */ 0x00008270 diff --git a/drivers/gpu/drm/nouveau/include/nvif/clc36f.h b/drivers/gpu/drm/nouveau/include/nvif/clc36f.h new file mode 100644 index 000000000000..6b14d7e3f6bb --- /dev/null +++ b/drivers/gpu/drm/nouveau/include/nvif/clc36f.h @@ -0,0 +1,19 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +#ifndef __NVIF_CLC36F_H__ +#define __NVIF_CLC36F_H__ + +struct volta_channel_gpfifo_a_v0 { + __u8 version; + __u8 priv; + __u16 chid; + __u32 ilength; + __u64 ioffset; + __u64 runlist; + __u64 vmm; + __u64 inst; + __u32 token; +}; + +#define NVC36F_V0_NTFY_NON_STALL_INTERRUPT 0x00 +#define NVC36F_V0_NTFY_KILLED 0x01 +#endif diff --git a/drivers/gpu/drm/nouveau/nouveau_chan.c b/drivers/gpu/drm/nouveau/nouveau_chan.c index 5daf9248ae63..ae10df756b2c 100644 --- a/drivers/gpu/drm/nouveau/nouveau_chan.c +++ b/drivers/gpu/drm/nouveau/nouveau_chan.c @@ -29,6 +29,7 @@ #include <nvif/cl506f.h> #include <nvif/cl906f.h> #include <nvif/cla06f.h> +#include <nvif/clc36f.h> #include <nvif/ioctl.h> /*XXX*/ @@ -234,6 +235,7 @@ nouveau_channel_ind(struct nouveau_drm *drm, struct nvif_device *device, struct nv50_channel_gpfifo_v0 nv50; struct fermi_channel_gpfifo_v0 fermi; struct kepler_channel_gpfifo_a_v0 kepler; + struct volta_channel_gpfifo_a_v0 volta; } args; struct nouveau_channel *chan; u32 size; @@ -247,6 +249,15 @@ nouveau_channel_ind(struct nouveau_drm *drm, struct nvif_device *device, /* create channel object */ do { + if (oclass[0] >= VOLTA_CHANNEL_GPFIFO_A) { + args.volta.version = 0; + args.volta.ilength = 0x02000; + args.volta.ioffset = 0x10000 + chan->push.addr; + args.volta.runlist = runlist; + args.volta.vmm = nvif_handle(&cli->vmm.vmm.object); + args.volta.priv = priv; + size = sizeof(args.volta); + } else if (oclass[0] >= KEPLER_CHANNEL_GPFIFO_A) { args.kepler.version = 0; args.kepler.ilength = 0x02000; @@ -274,6 +285,11 @@ nouveau_channel_ind(struct nouveau_drm *drm, struct nvif_device *device, ret = nvif_object_init(&device->object, 0, *oclass++, &args, size, &chan->user); if (ret == 0) { + if (chan->user.oclass >= VOLTA_CHANNEL_GPFIFO_A) { + chan->chid = args.volta.chid; + chan->inst = args.volta.inst; + chan->token = args.volta.token; + } else if (chan->user.oclass >= KEPLER_CHANNEL_GPFIFO_A) { chan->chid = args.kepler.chid; chan->inst = args.kepler.inst; diff --git a/drivers/gpu/drm/nouveau/nouveau_chan.h b/drivers/gpu/drm/nouveau/nouveau_chan.h index a62d233b2a97..28418f4e5748 100644 --- a/drivers/gpu/drm/nouveau/nouveau_chan.h +++ b/drivers/gpu/drm/nouveau/nouveau_chan.h @@ -11,6 +11,7 @@ struct nouveau_channel { int chid; u64 inst; + u32 token; struct nvif_object vram; struct nvif_object gart; diff --git a/drivers/gpu/drm/nouveau/nouveau_dma.c b/drivers/gpu/drm/nouveau/nouveau_dma.c index 945afd34138e..078f65d849ce 100644 --- a/drivers/gpu/drm/nouveau/nouveau_dma.c +++ b/drivers/gpu/drm/nouveau/nouveau_dma.c @@ -101,7 +101,7 @@ nv50_dma_push(struct nouveau_channel *chan, u64 offset, int length) nvif_wr32(&chan->user, 0x8c, chan->dma.ib_put); if (user->func && user->func->doorbell) - user->func->doorbell(user, chan->chid); + user->func->doorbell(user, chan->token); chan->dma.ib_free--; } diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/chan.h b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/chan.h index 3ffef236189e..2c7c5afc1ea5 100644 --- a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/chan.h +++ b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/chan.h @@ -17,6 +17,7 @@ struct nvkm_fifo_chan_func { bool suspend); int (*object_ctor)(struct nvkm_fifo_chan *, struct nvkm_object *); void (*object_dtor)(struct nvkm_fifo_chan *, int); + u32 (*submit_token)(struct nvkm_fifo_chan *); }; int nvkm_fifo_chan_ctor(const struct nvkm_fifo_chan_func *, struct nvkm_fifo *, diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/changk104.h b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/changk104.h index 68df966205d0..f041aa281d9d 100644 --- a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/changk104.h +++ b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/changk104.h @@ -38,4 +38,8 @@ int gk104_fifo_gpfifo_kick_locked(struct gk104_fifo_chan *); int gv100_fifo_gpfifo_new(struct gk104_fifo *, const struct nvkm_oclass *, void *data, u32 size, struct nvkm_object **); +int gv100_fifo_gpfifo_new_(const struct nvkm_fifo_chan_func *, + struct gk104_fifo *, u64 *, u16 *, u64, u64, u64, + u64 *, bool, u32 *, const struct nvkm_oclass *, + struct nvkm_object **); #endif diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gpfifogv100.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gpfifogv100.c index ad5d119f6a36..386dcf7420ad 100644 --- a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gpfifogv100.c +++ b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gpfifogv100.c @@ -25,9 +25,15 @@ #include <core/client.h> #include <core/gpuobj.h> -#include <nvif/cla06f.h> +#include <nvif/clc36f.h> #include <nvif/unpack.h> +static u32 +gv100_fifo_gpfifo_submit_token(struct nvkm_fifo_chan *chan) +{ + return chan->chid; +} + static int gv100_fifo_gpfifo_engine_valid(struct gk104_fifo_chan *chan, bool ce, bool valid) { @@ -100,8 +106,8 @@ gv100_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base, return gv100_fifo_gpfifo_engine_valid(chan, false, true); } -const struct nvkm_fifo_chan_func -gv100_fifo_gpfifo_func = { +static const struct nvkm_fifo_chan_func +gv100_fifo_gpfifo = { .dtor = gk104_fifo_gpfifo_dtor, .init = gk104_fifo_gpfifo_init, .fini = gk104_fifo_gpfifo_fini, @@ -110,12 +116,14 @@ gv100_fifo_gpfifo_func = { .engine_dtor = gk104_fifo_gpfifo_engine_dtor, .engine_init = gv100_fifo_gpfifo_engine_init, .engine_fini = gv100_fifo_gpfifo_engine_fini, + .submit_token = gv100_fifo_gpfifo_submit_token, }; -static int -gv100_fifo_gpfifo_new_(struct gk104_fifo *fifo, u64 *runlists, u16 *chid, +int +gv100_fifo_gpfifo_new_(const struct nvkm_fifo_chan_func *func, + struct gk104_fifo *fifo, u64 *runlists, u16 *chid, u64 vmm, u64 ioffset, u64 ilength, u64 *inst, bool priv, - const struct nvkm_oclass *oclass, + u32 *token, const struct nvkm_oclass *oclass, struct nvkm_object **pobject) { struct nvkm_device *device = fifo->base.engine.subdev.device; @@ -144,15 +152,15 @@ gv100_fifo_gpfifo_new_(struct gk104_fifo *fifo, u64 *runlists, u16 *chid, chan->runl = runlist; INIT_LIST_HEAD(&chan->head); - ret = nvkm_fifo_chan_ctor(&gv100_fifo_gpfifo_func, &fifo->base, - 0x1000, 0x1000, true, vmm, 0, subdevs, - 1, fifo->user.bar->addr, 0x200, + ret = nvkm_fifo_chan_ctor(func, &fifo->base, 0x1000, 0x1000, true, vmm, + 0, subdevs, 1, fifo->user.bar->addr, 0x200, oclass, &chan->base); if (ret) return ret; *chid = chan->base.chid; *inst = chan->base.inst->addr; + *token = chan->base.func->submit_token(&chan->base); /* Hack to support GPUs where even individual channels should be * part of a channel group. @@ -218,7 +226,7 @@ gv100_fifo_gpfifo_new(struct gk104_fifo *fifo, const struct nvkm_oclass *oclass, { struct nvkm_object *parent = oclass->parent; union { - struct kepler_channel_gpfifo_a_v0 v0; + struct volta_channel_gpfifo_a_v0 v0; } *args = data; int ret = -ENOSYS; @@ -231,7 +239,7 @@ gv100_fifo_gpfifo_new(struct gk104_fifo *fifo, const struct nvkm_oclass *oclass, args->v0.ilength, args->v0.runlist, args->v0.priv); if (args->v0.priv && !oclass->client->super) return -EINVAL; - return gv100_fifo_gpfifo_new_(fifo, + return gv100_fifo_gpfifo_new_(&gv100_fifo_gpfifo, fifo, &args->v0.runlist, &args->v0.chid, args->v0.vmm, @@ -239,6 +247,7 @@ gv100_fifo_gpfifo_new(struct gk104_fifo *fifo, const struct nvkm_oclass *oclass, args->v0.ilength, &args->v0.inst, args->v0.priv, + &args->v0.token, oclass, pobject); } |