drm/nv50/dmaobj: extend class to allow gpu-specific attributes to be defined
authorBen Skeggs <bskeggs@redhat.com>
Mon, 8 Oct 2012 04:29:16 +0000 (14:29 +1000)
committerBen Skeggs <bskeggs@redhat.com>
Wed, 28 Nov 2012 23:56:39 +0000 (09:56 +1000)
disp is going to need to be able to create more specific dma objects
than was previously possible.

Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
drivers/gpu/drm/nouveau/core/engine/dmaobj/base.c
drivers/gpu/drm/nouveau/core/engine/dmaobj/nv50.c
drivers/gpu/drm/nouveau/core/include/core/class.h
drivers/gpu/drm/nouveau/core/include/engine/dmaobj.h
drivers/gpu/drm/nouveau/nouveau_abi16.c
drivers/gpu/drm/nouveau/nouveau_chan.c

index 325b79dd619acafaf3517a116b769e0e0701e264..5103e88d18779f12dbd4edbfacab491e1568abb2 100644 (file)
@@ -85,6 +85,7 @@ nouveau_dmaobj_ctor(struct nouveau_object *parent,
 
        dmaobj->start = args->start;
        dmaobj->limit = args->limit;
+       dmaobj->conf0 = args->conf0;
 
        switch (nv_mclass(parent)) {
        case NV_DEVICE_CLASS:
index 3dab016b6fe4181ac14d8721a99f3e2d820824e6..bda7afcf8d3c2be0577f75c36ab3b796618e8a33 100644 (file)
@@ -38,7 +38,8 @@ nv50_dmaobj_bind(struct nouveau_dmaeng *dmaeng,
                 struct nouveau_dmaobj *dmaobj,
                 struct nouveau_gpuobj **pgpuobj)
 {
-       u32 flags = nv_mclass(dmaobj);
+       u32 flags0 = nv_mclass(dmaobj);
+       u32 flags5 = 0x00000000;
        int ret;
 
        if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
@@ -53,23 +54,37 @@ nv50_dmaobj_bind(struct nouveau_dmaeng *dmaeng,
                }
        }
 
+       if (!(dmaobj->conf0 & NV50_DMA_CONF0_ENABLE)) {
+               if (dmaobj->target == NV_MEM_TARGET_VM) {
+                       dmaobj->conf0  = NV50_DMA_CONF0_PRIV_VM;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_PART_VM;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_COMP_VM;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_TYPE_VM;
+               } else {
+                       dmaobj->conf0  = NV50_DMA_CONF0_PRIV_US;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_PART_256;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_COMP_NONE;
+                       dmaobj->conf0 |= NV50_DMA_CONF0_TYPE_LINEAR;
+               }
+       }
+
+       flags0 |= (dmaobj->conf0 & NV50_DMA_CONF0_COMP) << 22;
+       flags0 |= (dmaobj->conf0 & NV50_DMA_CONF0_TYPE) << 22;
+       flags0 |= (dmaobj->conf0 & NV50_DMA_CONF0_PRIV);
+       flags5 |= (dmaobj->conf0 & NV50_DMA_CONF0_PART);
+
        switch (dmaobj->target) {
        case NV_MEM_TARGET_VM:
-               flags |= 0x00000000;
-               flags |= 0x60000000; /* COMPRESSION_USEVM */
-               flags |= 0x1fc00000; /* STORAGE_TYPE_USEVM */
+               flags0 |= 0x00000000;
                break;
        case NV_MEM_TARGET_VRAM:
-               flags |= 0x00010000;
-               flags |= 0x00100000; /* ACCESSUS_USER_SYSTEM */
+               flags0 |= 0x00010000;
                break;
        case NV_MEM_TARGET_PCI:
-               flags |= 0x00020000;
-               flags |= 0x00100000; /* ACCESSUS_USER_SYSTEM */
+               flags0 |= 0x00020000;
                break;
        case NV_MEM_TARGET_PCI_NOSNOOP:
-               flags |= 0x00030000;
-               flags |= 0x00100000; /* ACCESSUS_USER_SYSTEM */
+               flags0 |= 0x00030000;
                break;
        default:
                return -EINVAL;
@@ -79,23 +94,23 @@ nv50_dmaobj_bind(struct nouveau_dmaeng *dmaeng,
        case NV_MEM_ACCESS_VM:
                break;
        case NV_MEM_ACCESS_RO:
-               flags |= 0x00040000;
+               flags0 |= 0x00040000;
                break;
        case NV_MEM_ACCESS_WO:
        case NV_MEM_ACCESS_RW:
-               flags |= 0x00080000;
+               flags0 |= 0x00080000;
                break;
        }
 
        ret = nouveau_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
        if (ret == 0) {
-               nv_wo32(*pgpuobj, 0x00, flags);
+               nv_wo32(*pgpuobj, 0x00, flags0);
                nv_wo32(*pgpuobj, 0x04, lower_32_bits(dmaobj->limit));
                nv_wo32(*pgpuobj, 0x08, lower_32_bits(dmaobj->start));
                nv_wo32(*pgpuobj, 0x0c, upper_32_bits(dmaobj->limit) << 24 |
                                        upper_32_bits(dmaobj->start));
                nv_wo32(*pgpuobj, 0x10, 0x00000000);
-               nv_wo32(*pgpuobj, 0x14, 0x00000000);
+               nv_wo32(*pgpuobj, 0x14, flags5);
        }
 
        return ret;
index 6180ae9800fc0dc5bd3c214bc8346e6deb481240..445a4bad2936e56c6b5d4a04fcf8104018d8f531 100644 (file)
@@ -52,11 +52,29 @@ struct nv_device_class {
 #define NV_DMA_ACCESS_WR                                             0x00000200
 #define NV_DMA_ACCESS_RDWR                                           0x00000300
 
+/* NV50:NVC0 */
+#define NV50_DMA_CONF0_ENABLE                                        0x80000000
+#define NV50_DMA_CONF0_PRIV                                          0x00300000
+#define NV50_DMA_CONF0_PRIV_VM                                       0x00000000
+#define NV50_DMA_CONF0_PRIV_US                                       0x00100000
+#define NV50_DMA_CONF0_PRIV__S                                       0x00200000
+#define NV50_DMA_CONF0_PART                                          0x00030000
+#define NV50_DMA_CONF0_PART_VM                                       0x00000000
+#define NV50_DMA_CONF0_PART_256                                      0x00010000
+#define NV50_DMA_CONF0_PART_1KB                                      0x00020000
+#define NV50_DMA_CONF0_COMP                                          0x00000180
+#define NV50_DMA_CONF0_COMP_NONE                                     0x00000000
+#define NV50_DMA_CONF0_COMP_VM                                       0x00000180
+#define NV50_DMA_CONF0_TYPE                                          0x0000007f
+#define NV50_DMA_CONF0_TYPE_LINEAR                                   0x00000000
+#define NV50_DMA_CONF0_TYPE_VM                                       0x0000007f
+
 struct nv_dma_class {
        u32 flags;
        u32 pad0;
        u64 start;
        u64 limit;
+       u32 conf0;
 };
 
 /* DMA FIFO channel classes
index 21f9edcdd6c93be48a95ace8f35cafb91bcf3638..b28914ed175297eb963374f42fc284b7583629c6 100644 (file)
@@ -12,6 +12,7 @@ struct nouveau_dmaobj {
        u32 access;
        u64 start;
        u64 limit;
+       u32 conf0;
 };
 
 struct nouveau_dmaeng {
index cc79c796afee316cd810125b93dd86fbef940d5e..2720ce009664eeae41d1ec7817357e24532dc9ba 100644 (file)
@@ -378,7 +378,7 @@ nouveau_abi16_ioctl_notifierobj_alloc(ABI16_IOCTL_ARGS)
        struct nouveau_abi16_chan *chan, *temp;
        struct nouveau_abi16_ntfy *ntfy;
        struct nouveau_object *object;
-       struct nv_dma_class args;
+       struct nv_dma_class args = {};
        int ret;
 
        if (unlikely(!abi16))
index c1d7301c0e9c0b48c96b72613e4536c1ada9b1e8..049c6b23e1d7c7d569c77299ace00f1f9b26b590 100644 (file)
@@ -267,7 +267,7 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
        struct nouveau_fb *pfb = nouveau_fb(device);
        struct nouveau_software_chan *swch;
        struct nouveau_object *object;
-       struct nv_dma_class args;
+       struct nv_dma_class args = {};
        int ret, i;
 
        /* allocate dma objects to cover all allowed vram, and gart */