drm/nvc0: explicitly map PDISP semaphore buffer into each channel's vm
authorBen Skeggs <bskeggs@redhat.com>
Tue, 7 Jun 2011 05:43:31 +0000 (15:43 +1000)
committerBen Skeggs <bskeggs@redhat.com>
Thu, 23 Jun 2011 06:00:27 +0000 (16:00 +1000)
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
drivers/gpu/drm/nouveau/nouveau_drv.h
drivers/gpu/drm/nouveau/nouveau_object.c
drivers/gpu/drm/nouveau/nv50_display.c

index 7e12d4d..4a48d6c 100644 (file)
@@ -293,6 +293,7 @@ struct nouveau_channel {
 
        uint32_t sw_subchannel[8];
 
+       struct nouveau_vma dispc_vma[2];
        struct {
                struct nouveau_gpuobj *vblsem;
                uint32_t vblsem_head;
index 37e6ca8..1158271 100644 (file)
@@ -717,6 +717,17 @@ nouveau_gpuobj_channel_init(struct nouveau_channel *chan,
                nv_wo32(chan->ramin, 0x0204, upper_32_bits(vpgd->obj->vinst));
                nv_wo32(chan->ramin, 0x0208, 0xffffffff);
                nv_wo32(chan->ramin, 0x020c, 0x000000ff);
+
+               for (i = 0; i < 2; i++) {
+                       struct nv50_display_crtc *dispc =
+                               &nv50_display(dev)->crtc[i];
+
+                       ret = nouveau_bo_vma_add(dispc->sem.bo, chan->vm,
+                                                &chan->dispc_vma[i]);
+                       if (ret)
+                               return ret;
+               }
+
                return 0;
        }
 
@@ -841,9 +852,14 @@ void
 nouveau_gpuobj_channel_takedown(struct nouveau_channel *chan)
 {
        struct drm_device *dev = chan->dev;
+       int i;
 
        NV_DEBUG(dev, "ch%d\n", chan->id);
 
+       for (i = 0; i < 2; i++) {
+               struct nv50_display_crtc *dispc = &nv50_display(dev)->crtc[i];
+               nouveau_bo_vma_del(dispc->sem.bo, &chan->dispc_vma[i]);
+       }
        nouveau_vm_ref(NULL, &chan->vm, chan->vm_pd);
        nouveau_gpuobj_ref(NULL, &chan->vm_pd);
 
index 93857e6..db1a5f4 100644 (file)
@@ -415,8 +415,6 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb,
 
        /* synchronise with the rendering channel, if necessary */
        if (likely(chan)) {
-               u64 offset = dispc->sem.bo->vma.offset + dispc->sem.offset;
-
                ret = RING_SPACE(chan, 10);
                if (ret) {
                        WIND_RING(evo);
@@ -438,6 +436,8 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb,
                        else
                                OUT_RING  (chan, chan->vram_handle);
                } else {
+                       u64 offset = chan->dispc_vma[nv_crtc->index].offset;
+                       offset += dispc->sem.offset;
                        BEGIN_NVC0(chan, 2, NvSubM2MF, 0x0010, 4);
                        OUT_RING  (chan, upper_32_bits(offset));
                        OUT_RING  (chan, lower_32_bits(offset));