|
@@ -28,37 +28,39 @@
|
|
|
#include <subdev/fb.h>
|
|
|
#include <engine/dmaobj.h>
|
|
|
|
|
|
-int
|
|
|
-nouveau_dmaobj_create_(struct nouveau_object *parent,
|
|
|
- struct nouveau_object *engine,
|
|
|
- struct nouveau_oclass *oclass,
|
|
|
- void *data, u32 size, int len, void **pobject)
|
|
|
+static int
|
|
|
+nouveau_dmaobj_ctor(struct nouveau_object *parent,
|
|
|
+ struct nouveau_object *engine,
|
|
|
+ struct nouveau_oclass *oclass, void *data, u32 size,
|
|
|
+ struct nouveau_object **pobject)
|
|
|
{
|
|
|
+ struct nouveau_dmaeng *dmaeng = (void *)engine;
|
|
|
+ struct nouveau_dmaobj *dmaobj;
|
|
|
+ struct nouveau_gpuobj *gpuobj;
|
|
|
struct nv_dma_class *args = data;
|
|
|
- struct nouveau_dmaobj *object;
|
|
|
int ret;
|
|
|
|
|
|
if (size < sizeof(*args))
|
|
|
return -EINVAL;
|
|
|
|
|
|
- ret = nouveau_object_create_(parent, engine, oclass, 0, len, pobject);
|
|
|
- object = *pobject;
|
|
|
+ ret = nouveau_object_create(parent, engine, oclass, 0, &dmaobj);
|
|
|
+ *pobject = nv_object(dmaobj);
|
|
|
if (ret)
|
|
|
return ret;
|
|
|
|
|
|
switch (args->flags & NV_DMA_TARGET_MASK) {
|
|
|
case NV_DMA_TARGET_VM:
|
|
|
- object->target = NV_MEM_TARGET_VM;
|
|
|
+ dmaobj->target = NV_MEM_TARGET_VM;
|
|
|
break;
|
|
|
case NV_DMA_TARGET_VRAM:
|
|
|
- object->target = NV_MEM_TARGET_VRAM;
|
|
|
+ dmaobj->target = NV_MEM_TARGET_VRAM;
|
|
|
break;
|
|
|
case NV_DMA_TARGET_PCI:
|
|
|
- object->target = NV_MEM_TARGET_PCI;
|
|
|
+ dmaobj->target = NV_MEM_TARGET_PCI;
|
|
|
break;
|
|
|
case NV_DMA_TARGET_PCI_US:
|
|
|
case NV_DMA_TARGET_AGP:
|
|
|
- object->target = NV_MEM_TARGET_PCI_NOSNOOP;
|
|
|
+ dmaobj->target = NV_MEM_TARGET_PCI_NOSNOOP;
|
|
|
break;
|
|
|
default:
|
|
|
return -EINVAL;
|
|
@@ -66,22 +68,58 @@ nouveau_dmaobj_create_(struct nouveau_object *parent,
|
|
|
|
|
|
switch (args->flags & NV_DMA_ACCESS_MASK) {
|
|
|
case NV_DMA_ACCESS_VM:
|
|
|
- object->access = NV_MEM_ACCESS_VM;
|
|
|
+ dmaobj->access = NV_MEM_ACCESS_VM;
|
|
|
break;
|
|
|
case NV_DMA_ACCESS_RD:
|
|
|
- object->access = NV_MEM_ACCESS_RO;
|
|
|
+ dmaobj->access = NV_MEM_ACCESS_RO;
|
|
|
break;
|
|
|
case NV_DMA_ACCESS_WR:
|
|
|
- object->access = NV_MEM_ACCESS_WO;
|
|
|
+ dmaobj->access = NV_MEM_ACCESS_WO;
|
|
|
break;
|
|
|
case NV_DMA_ACCESS_RDWR:
|
|
|
- object->access = NV_MEM_ACCESS_RW;
|
|
|
+ dmaobj->access = NV_MEM_ACCESS_RW;
|
|
|
break;
|
|
|
default:
|
|
|
return -EINVAL;
|
|
|
}
|
|
|
|
|
|
- object->start = args->start;
|
|
|
- object->limit = args->limit;
|
|
|
- return 0;
|
|
|
+ dmaobj->start = args->start;
|
|
|
+ dmaobj->limit = args->limit;
|
|
|
+
|
|
|
+ switch (nv_mclass(parent)) {
|
|
|
+ case NV_DEVICE_CLASS:
|
|
|
+ break;
|
|
|
+ case NV03_CHANNEL_DMA_CLASS:
|
|
|
+ case NV10_CHANNEL_DMA_CLASS:
|
|
|
+ case NV17_CHANNEL_DMA_CLASS:
|
|
|
+ case NV40_CHANNEL_DMA_CLASS:
|
|
|
+ case NV50_CHANNEL_DMA_CLASS:
|
|
|
+ case NV84_CHANNEL_DMA_CLASS:
|
|
|
+ case NV50_CHANNEL_IND_CLASS:
|
|
|
+ case NV84_CHANNEL_IND_CLASS:
|
|
|
+ ret = dmaeng->bind(dmaeng, *pobject, dmaobj, &gpuobj);
|
|
|
+ nouveau_object_ref(NULL, pobject);
|
|
|
+ *pobject = nv_object(gpuobj);
|
|
|
+ break;
|
|
|
+ default:
|
|
|
+ return -EINVAL;
|
|
|
+ }
|
|
|
+
|
|
|
+ return ret;
|
|
|
}
|
|
|
+
|
|
|
+static struct nouveau_ofuncs
|
|
|
+nouveau_dmaobj_ofuncs = {
|
|
|
+ .ctor = nouveau_dmaobj_ctor,
|
|
|
+ .dtor = nouveau_object_destroy,
|
|
|
+ .init = nouveau_object_init,
|
|
|
+ .fini = nouveau_object_fini,
|
|
|
+};
|
|
|
+
|
|
|
+struct nouveau_oclass
|
|
|
+nouveau_dmaobj_sclass[] = {
|
|
|
+ { NV_DMA_FROM_MEMORY_CLASS, &nouveau_dmaobj_ofuncs },
|
|
|
+ { NV_DMA_TO_MEMORY_CLASS, &nouveau_dmaobj_ofuncs },
|
|
|
+ { NV_DMA_IN_MEMORY_CLASS, &nouveau_dmaobj_ofuncs },
|
|
|
+ {}
|
|
|
+};
|