Commit 3e7d4a0c authored by Ben Skeggs's avatar Ben Skeggs

drm/nouveau/fifo: index backend engctx by engine id

Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
Reviewed-by: default avatarLyude Paul <lyude@redhat.com>
parent 2546db0e
...@@ -114,7 +114,7 @@ g84_fifo_chan_engine_init(struct nvkm_fifo_chan *base, ...@@ -114,7 +114,7 @@ g84_fifo_chan_engine_init(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct nv50_fifo_chan *chan = nv50_fifo_chan(base); struct nv50_fifo_chan *chan = nv50_fifo_chan(base);
struct nvkm_gpuobj *engn = chan->engn[engine->subdev.index]; struct nvkm_gpuobj *engn = *nv50_fifo_chan_engine(chan, engine);
u64 limit, start; u64 limit, start;
int offset; int offset;
...@@ -142,12 +142,11 @@ g84_fifo_chan_engine_ctor(struct nvkm_fifo_chan *base, ...@@ -142,12 +142,11 @@ g84_fifo_chan_engine_ctor(struct nvkm_fifo_chan *base,
struct nvkm_object *object) struct nvkm_object *object)
{ {
struct nv50_fifo_chan *chan = nv50_fifo_chan(base); struct nv50_fifo_chan *chan = nv50_fifo_chan(base);
int engn = engine->subdev.index;
if (g84_fifo_chan_engine_addr(engine) < 0) if (g84_fifo_chan_engine_addr(engine) < 0)
return 0; return 0;
return nvkm_object_bind(object, NULL, 0, &chan->engn[engn]); return nvkm_object_bind(object, NULL, 0, nv50_fifo_chan_engine(chan, engine));
} }
static int static int
......
...@@ -22,7 +22,7 @@ struct gf100_fifo_chan { ...@@ -22,7 +22,7 @@ struct gf100_fifo_chan {
struct gf100_fifo_engn { struct gf100_fifo_engn {
struct nvkm_gpuobj *inst; struct nvkm_gpuobj *inst;
struct nvkm_vma *vma; struct nvkm_vma *vma;
} engn[NVKM_SUBDEV_NR]; } engn[NVKM_FIFO_ENGN_NR];
}; };
extern const struct nvkm_fifo_chan_oclass gf100_fifo_gpfifo_oclass; extern const struct nvkm_fifo_chan_oclass gf100_fifo_gpfifo_oclass;
......
...@@ -20,7 +20,7 @@ struct gk104_fifo_chan { ...@@ -20,7 +20,7 @@ struct gk104_fifo_chan {
struct gk104_fifo_engn { struct gk104_fifo_engn {
struct nvkm_gpuobj *inst; struct nvkm_gpuobj *inst;
struct nvkm_vma *vma; struct nvkm_vma *vma;
} engn[NVKM_SUBDEV_NR]; } engn[NVKM_FIFO_ENGN_NR];
}; };
extern const struct nvkm_fifo_chan_func gk104_fifo_gpfifo_func; extern const struct nvkm_fifo_chan_func gk104_fifo_gpfifo_func;
...@@ -30,6 +30,7 @@ int gk104_fifo_gpfifo_new(struct gk104_fifo *, const struct nvkm_oclass *, ...@@ -30,6 +30,7 @@ int gk104_fifo_gpfifo_new(struct gk104_fifo *, const struct nvkm_oclass *,
void *gk104_fifo_gpfifo_dtor(struct nvkm_fifo_chan *); void *gk104_fifo_gpfifo_dtor(struct nvkm_fifo_chan *);
void gk104_fifo_gpfifo_init(struct nvkm_fifo_chan *); void gk104_fifo_gpfifo_init(struct nvkm_fifo_chan *);
void gk104_fifo_gpfifo_fini(struct nvkm_fifo_chan *); void gk104_fifo_gpfifo_fini(struct nvkm_fifo_chan *);
struct gk104_fifo_engn *gk104_fifo_gpfifo_engine(struct gk104_fifo_chan *, struct nvkm_engine *);
int gk104_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *, struct nvkm_engine *, int gk104_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *, struct nvkm_engine *,
struct nvkm_object *); struct nvkm_object *);
void gk104_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *, void gk104_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *,
......
...@@ -13,7 +13,7 @@ struct nv04_fifo_chan { ...@@ -13,7 +13,7 @@ struct nv04_fifo_chan {
#define NV04_FIFO_ENGN_GR 1 #define NV04_FIFO_ENGN_GR 1
#define NV04_FIFO_ENGN_MPEG 2 #define NV04_FIFO_ENGN_MPEG 2
#define NV04_FIFO_ENGN_DMA 3 #define NV04_FIFO_ENGN_DMA 3
struct nvkm_gpuobj *engn[NVKM_SUBDEV_NR]; struct nvkm_gpuobj *engn[NVKM_FIFO_ENGN_NR];
}; };
extern const struct nvkm_fifo_chan_func nv04_fifo_dma_func; extern const struct nvkm_fifo_chan_func nv04_fifo_dma_func;
......
...@@ -42,6 +42,15 @@ nv50_fifo_chan_engine_addr(struct nvkm_engine *engine) ...@@ -42,6 +42,15 @@ nv50_fifo_chan_engine_addr(struct nvkm_engine *engine)
} }
} }
struct nvkm_gpuobj **
nv50_fifo_chan_engine(struct nv50_fifo_chan *chan, struct nvkm_engine *engine)
{
int engi = chan->base.fifo->func->engine_id(chan->base.fifo, engine);
if (engi >= 0)
return &chan->engn[engi];
return NULL;
}
static int static int
nv50_fifo_chan_engine_fini(struct nvkm_fifo_chan *base, nv50_fifo_chan_engine_fini(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine, bool suspend) struct nvkm_engine *engine, bool suspend)
...@@ -103,7 +112,7 @@ nv50_fifo_chan_engine_init(struct nvkm_fifo_chan *base, ...@@ -103,7 +112,7 @@ nv50_fifo_chan_engine_init(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct nv50_fifo_chan *chan = nv50_fifo_chan(base); struct nv50_fifo_chan *chan = nv50_fifo_chan(base);
struct nvkm_gpuobj *engn = chan->engn[engine->subdev.index]; struct nvkm_gpuobj *engn = *nv50_fifo_chan_engine(chan, engine);
u64 limit, start; u64 limit, start;
int offset; int offset;
...@@ -130,7 +139,7 @@ nv50_fifo_chan_engine_dtor(struct nvkm_fifo_chan *base, ...@@ -130,7 +139,7 @@ nv50_fifo_chan_engine_dtor(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct nv50_fifo_chan *chan = nv50_fifo_chan(base); struct nv50_fifo_chan *chan = nv50_fifo_chan(base);
nvkm_gpuobj_del(&chan->engn[engine->subdev.index]); nvkm_gpuobj_del(nv50_fifo_chan_engine(chan, engine));
} }
static int static int
...@@ -139,12 +148,11 @@ nv50_fifo_chan_engine_ctor(struct nvkm_fifo_chan *base, ...@@ -139,12 +148,11 @@ nv50_fifo_chan_engine_ctor(struct nvkm_fifo_chan *base,
struct nvkm_object *object) struct nvkm_object *object)
{ {
struct nv50_fifo_chan *chan = nv50_fifo_chan(base); struct nv50_fifo_chan *chan = nv50_fifo_chan(base);
int engn = engine->subdev.index;
if (nv50_fifo_chan_engine_addr(engine) < 0) if (nv50_fifo_chan_engine_addr(engine) < 0)
return 0; return 0;
return nvkm_object_bind(object, NULL, 0, &chan->engn[engn]); return nvkm_object_bind(object, NULL, 0, nv50_fifo_chan_engine(chan, engine));
} }
void void
......
...@@ -34,13 +34,14 @@ struct nv50_fifo_chan { ...@@ -34,13 +34,14 @@ struct nv50_fifo_chan {
#define G84_FIFO_ENGN_BSP 6 #define G84_FIFO_ENGN_BSP 6
#define G84_FIFO_ENGN_MSVLD 6 #define G84_FIFO_ENGN_MSVLD 6
#define G84_FIFO_ENGN_DMA 7 #define G84_FIFO_ENGN_DMA 7
struct nvkm_gpuobj *engn[NVKM_SUBDEV_NR]; struct nvkm_gpuobj *engn[NVKM_FIFO_ENGN_NR];
}; };
int nv50_fifo_chan_ctor(struct nv50_fifo *, u64 vmm, u64 push, int nv50_fifo_chan_ctor(struct nv50_fifo *, u64 vmm, u64 push,
const struct nvkm_oclass *, struct nv50_fifo_chan *); const struct nvkm_oclass *, struct nv50_fifo_chan *);
void *nv50_fifo_chan_dtor(struct nvkm_fifo_chan *); void *nv50_fifo_chan_dtor(struct nvkm_fifo_chan *);
void nv50_fifo_chan_fini(struct nvkm_fifo_chan *); void nv50_fifo_chan_fini(struct nvkm_fifo_chan *);
struct nvkm_gpuobj **nv50_fifo_chan_engine(struct nv50_fifo_chan *, struct nvkm_engine *);
void nv50_fifo_chan_engine_dtor(struct nvkm_fifo_chan *, struct nvkm_engine *); void nv50_fifo_chan_engine_dtor(struct nvkm_fifo_chan *, struct nvkm_engine *);
void nv50_fifo_chan_object_dtor(struct nvkm_fifo_chan *, int); void nv50_fifo_chan_object_dtor(struct nvkm_fifo_chan *, int);
......
...@@ -55,6 +55,15 @@ nv40_fifo_dma_engine(struct nvkm_engine *engine, u32 *reg, u32 *ctx) ...@@ -55,6 +55,15 @@ nv40_fifo_dma_engine(struct nvkm_engine *engine, u32 *reg, u32 *ctx)
} }
} }
static struct nvkm_gpuobj **
nv40_fifo_dma_engn(struct nv04_fifo_chan *chan, struct nvkm_engine *engine)
{
int engi = chan->base.fifo->func->engine_id(chan->base.fifo, engine);
if (engi >= 0)
return &chan->engn[engi];
return NULL;
}
static int static int
nv40_fifo_dma_engine_fini(struct nvkm_fifo_chan *base, nv40_fifo_dma_engine_fini(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine, bool suspend) struct nvkm_engine *engine, bool suspend)
...@@ -99,7 +108,7 @@ nv40_fifo_dma_engine_init(struct nvkm_fifo_chan *base, ...@@ -99,7 +108,7 @@ nv40_fifo_dma_engine_init(struct nvkm_fifo_chan *base,
if (!nv40_fifo_dma_engine(engine, &reg, &ctx)) if (!nv40_fifo_dma_engine(engine, &reg, &ctx))
return 0; return 0;
inst = chan->engn[engine->subdev.index]->addr >> 4; inst = (*nv40_fifo_dma_engn(chan, engine))->addr >> 4;
spin_lock_irqsave(&fifo->base.lock, flags); spin_lock_irqsave(&fifo->base.lock, flags);
nvkm_mask(device, 0x002500, 0x00000001, 0x00000000); nvkm_mask(device, 0x002500, 0x00000001, 0x00000000);
...@@ -121,7 +130,7 @@ nv40_fifo_dma_engine_dtor(struct nvkm_fifo_chan *base, ...@@ -121,7 +130,7 @@ nv40_fifo_dma_engine_dtor(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct nv04_fifo_chan *chan = nv04_fifo_chan(base); struct nv04_fifo_chan *chan = nv04_fifo_chan(base);
nvkm_gpuobj_del(&chan->engn[engine->subdev.index]); nvkm_gpuobj_del(nv40_fifo_dma_engn(chan, engine));
} }
static int static int
...@@ -130,13 +139,12 @@ nv40_fifo_dma_engine_ctor(struct nvkm_fifo_chan *base, ...@@ -130,13 +139,12 @@ nv40_fifo_dma_engine_ctor(struct nvkm_fifo_chan *base,
struct nvkm_object *object) struct nvkm_object *object)
{ {
struct nv04_fifo_chan *chan = nv04_fifo_chan(base); struct nv04_fifo_chan *chan = nv04_fifo_chan(base);
const int engn = engine->subdev.index;
u32 reg, ctx; u32 reg, ctx;
if (!nv40_fifo_dma_engine(engine, &reg, &ctx)) if (!nv40_fifo_dma_engine(engine, &reg, &ctx))
return 0; return 0;
return nvkm_object_bind(object, NULL, 0, &chan->engn[engn]); return nvkm_object_bind(object, NULL, 0, nv40_fifo_dma_engn(chan, engine));
} }
static int static int
......
...@@ -66,6 +66,15 @@ gf100_fifo_gpfifo_engine_addr(struct nvkm_engine *engine) ...@@ -66,6 +66,15 @@ gf100_fifo_gpfifo_engine_addr(struct nvkm_engine *engine)
} }
} }
static struct gf100_fifo_engn *
gf100_fifo_gpfifo_engine(struct gf100_fifo_chan *chan, struct nvkm_engine *engine)
{
int engi = chan->base.fifo->func->engine_id(chan->base.fifo, engine);
if (engi >= 0)
return &chan->engn[engi];
return NULL;
}
static int static int
gf100_fifo_gpfifo_engine_fini(struct nvkm_fifo_chan *base, gf100_fifo_gpfifo_engine_fini(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine, bool suspend) struct nvkm_engine *engine, bool suspend)
...@@ -108,13 +117,13 @@ gf100_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base, ...@@ -108,13 +117,13 @@ gf100_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base,
{ {
const u32 offset = gf100_fifo_gpfifo_engine_addr(engine); const u32 offset = gf100_fifo_gpfifo_engine_addr(engine);
struct gf100_fifo_chan *chan = gf100_fifo_chan(base); struct gf100_fifo_chan *chan = gf100_fifo_chan(base);
struct gf100_fifo_engn *engn = gf100_fifo_gpfifo_engine(chan, engine);
struct nvkm_gpuobj *inst = chan->base.inst; struct nvkm_gpuobj *inst = chan->base.inst;
if (offset) { if (offset) {
u64 addr = chan->engn[engine->subdev.index].vma->addr;
nvkm_kmap(inst); nvkm_kmap(inst);
nvkm_wo32(inst, offset + 0x00, lower_32_bits(addr) | 4); nvkm_wo32(inst, offset + 0x00, lower_32_bits(engn->vma->addr) | 4);
nvkm_wo32(inst, offset + 0x04, upper_32_bits(addr)); nvkm_wo32(inst, offset + 0x04, upper_32_bits(engn->vma->addr));
nvkm_done(inst); nvkm_done(inst);
} }
...@@ -126,8 +135,9 @@ gf100_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *base, ...@@ -126,8 +135,9 @@ gf100_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct gf100_fifo_chan *chan = gf100_fifo_chan(base); struct gf100_fifo_chan *chan = gf100_fifo_chan(base);
nvkm_vmm_put(chan->base.vmm, &chan->engn[engine->subdev.index].vma); struct gf100_fifo_engn *engn = gf100_fifo_gpfifo_engine(chan, engine);
nvkm_gpuobj_del(&chan->engn[engine->subdev.index].inst); nvkm_vmm_put(chan->base.vmm, &engn->vma);
nvkm_gpuobj_del(&engn->inst);
} }
static int static int
...@@ -136,23 +146,21 @@ gf100_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *base, ...@@ -136,23 +146,21 @@ gf100_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *base,
struct nvkm_object *object) struct nvkm_object *object)
{ {
struct gf100_fifo_chan *chan = gf100_fifo_chan(base); struct gf100_fifo_chan *chan = gf100_fifo_chan(base);
int engn = engine->subdev.index; struct gf100_fifo_engn *engn = gf100_fifo_gpfifo_engine(chan, engine);
int ret; int ret;
if (!gf100_fifo_gpfifo_engine_addr(engine)) if (!gf100_fifo_gpfifo_engine_addr(engine))
return 0; return 0;
ret = nvkm_object_bind(object, NULL, 0, &chan->engn[engn].inst); ret = nvkm_object_bind(object, NULL, 0, &engn->inst);
if (ret) if (ret)
return ret; return ret;
ret = nvkm_vmm_get(chan->base.vmm, 12, chan->engn[engn].inst->size, ret = nvkm_vmm_get(chan->base.vmm, 12, engn->inst->size, &engn->vma);
&chan->engn[engn].vma);
if (ret) if (ret)
return ret; return ret;
return nvkm_memory_map(chan->engn[engn].inst, 0, chan->base.vmm, return nvkm_memory_map(engn->inst, 0, chan->base.vmm, engn->vma, NULL, 0);
chan->engn[engn].vma, NULL, 0);
} }
static void static void
......
...@@ -94,6 +94,15 @@ gk104_fifo_gpfifo_engine_addr(struct nvkm_engine *engine) ...@@ -94,6 +94,15 @@ gk104_fifo_gpfifo_engine_addr(struct nvkm_engine *engine)
} }
} }
struct gk104_fifo_engn *
gk104_fifo_gpfifo_engine(struct gk104_fifo_chan *chan, struct nvkm_engine *engine)
{
int engi = chan->base.fifo->func->engine_id(chan->base.fifo, engine);
if (engi >= 0)
return &chan->engn[engi];
return NULL;
}
static int static int
gk104_fifo_gpfifo_engine_fini(struct nvkm_fifo_chan *base, gk104_fifo_gpfifo_engine_fini(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine, bool suspend) struct nvkm_engine *engine, bool suspend)
...@@ -126,13 +135,13 @@ gk104_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base, ...@@ -126,13 +135,13 @@ gk104_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct gk104_fifo_chan *chan = gk104_fifo_chan(base); struct gk104_fifo_chan *chan = gk104_fifo_chan(base);
struct gk104_fifo_engn *engn = gk104_fifo_gpfifo_engine(chan, engine);
struct nvkm_gpuobj *inst = chan->base.inst; struct nvkm_gpuobj *inst = chan->base.inst;
u32 offset = gk104_fifo_gpfifo_engine_addr(engine); u32 offset = gk104_fifo_gpfifo_engine_addr(engine);
if (offset) { if (offset) {
u64 addr = chan->engn[engine->subdev.index].vma->addr; u32 datalo = lower_32_bits(engn->vma->addr) | 0x00000004;
u32 datalo = lower_32_bits(addr) | 0x00000004; u32 datahi = upper_32_bits(engn->vma->addr);
u32 datahi = upper_32_bits(addr);
nvkm_kmap(inst); nvkm_kmap(inst);
nvkm_wo32(inst, (offset & 0xffff) + 0x00, datalo); nvkm_wo32(inst, (offset & 0xffff) + 0x00, datalo);
nvkm_wo32(inst, (offset & 0xffff) + 0x04, datahi); nvkm_wo32(inst, (offset & 0xffff) + 0x04, datahi);
...@@ -151,8 +160,9 @@ gk104_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *base, ...@@ -151,8 +160,9 @@ gk104_fifo_gpfifo_engine_dtor(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct gk104_fifo_chan *chan = gk104_fifo_chan(base); struct gk104_fifo_chan *chan = gk104_fifo_chan(base);
nvkm_vmm_put(chan->base.vmm, &chan->engn[engine->subdev.index].vma); struct gk104_fifo_engn *engn = gk104_fifo_gpfifo_engine(chan, engine);
nvkm_gpuobj_del(&chan->engn[engine->subdev.index].inst); nvkm_vmm_put(chan->base.vmm, &engn->vma);
nvkm_gpuobj_del(&engn->inst);
} }
int int
...@@ -161,23 +171,21 @@ gk104_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *base, ...@@ -161,23 +171,21 @@ gk104_fifo_gpfifo_engine_ctor(struct nvkm_fifo_chan *base,
struct nvkm_object *object) struct nvkm_object *object)
{ {
struct gk104_fifo_chan *chan = gk104_fifo_chan(base); struct gk104_fifo_chan *chan = gk104_fifo_chan(base);
int engn = engine->subdev.index; struct gk104_fifo_engn *engn = gk104_fifo_gpfifo_engine(chan, engine);
int ret; int ret;
if (!gk104_fifo_gpfifo_engine_addr(engine)) if (!gk104_fifo_gpfifo_engine_addr(engine))
return 0; return 0;
ret = nvkm_object_bind(object, NULL, 0, &chan->engn[engn].inst); ret = nvkm_object_bind(object, NULL, 0, &engn->inst);
if (ret) if (ret)
return ret; return ret;
ret = nvkm_vmm_get(chan->base.vmm, 12, chan->engn[engn].inst->size, ret = nvkm_vmm_get(chan->base.vmm, 12, engn->inst->size, &engn->vma);
&chan->engn[engn].vma);
if (ret) if (ret)
return ret; return ret;
return nvkm_memory_map(chan->engn[engn].inst, 0, chan->base.vmm, return nvkm_memory_map(engn->inst, 0, chan->base.vmm, engn->vma, NULL, 0);
chan->engn[engn].vma, NULL, 0);
} }
void void
......
...@@ -90,17 +90,16 @@ gv100_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base, ...@@ -90,17 +90,16 @@ gv100_fifo_gpfifo_engine_init(struct nvkm_fifo_chan *base,
struct nvkm_engine *engine) struct nvkm_engine *engine)
{ {
struct gk104_fifo_chan *chan = gk104_fifo_chan(base); struct gk104_fifo_chan *chan = gk104_fifo_chan(base);
struct gk104_fifo_engn *engn = gk104_fifo_gpfifo_engine(chan, engine);
struct nvkm_gpuobj *inst = chan->base.inst; struct nvkm_gpuobj *inst = chan->base.inst;
u64 addr;
if (engine->subdev.index >= NVKM_ENGINE_CE0 && if (engine->subdev.index >= NVKM_ENGINE_CE0 &&
engine->subdev.index <= NVKM_ENGINE_CE_LAST) engine->subdev.index <= NVKM_ENGINE_CE_LAST)
return 0; return 0;
addr = chan->engn[engine->subdev.index].vma->addr;
nvkm_kmap(inst); nvkm_kmap(inst);
nvkm_wo32(inst, 0x210, lower_32_bits(addr) | 0x00000004); nvkm_wo32(inst, 0x210, lower_32_bits(engn->vma->addr) | 0x00000004);
nvkm_wo32(inst, 0x214, upper_32_bits(addr)); nvkm_wo32(inst, 0x214, upper_32_bits(engn->vma->addr));
nvkm_done(inst); nvkm_done(inst);
return gv100_fifo_gpfifo_engine_valid(chan, false, true); return gv100_fifo_gpfifo_engine_valid(chan, false, true);
......
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