Ben Skeggs 35a02f9
From ef0744eff71f519db7641313d1588289f5cb49d2 Mon Sep 17 00:00:00 2001
Ben Skeggs 35a02f9
From: Ben Skeggs <bskeggs@redhat.com>
Ben Skeggs 35a02f9
Date: Wed, 8 Sep 2010 15:40:30 +1000
Ben Skeggs 35a02f9
Subject: [PATCH] drm/nouveau: handle fifo pusher errors better
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
The most important part of this change is that we now instruct PFIFO to
Ben Skeggs 35a02f9
drop all pending fetches, rather than attempting to skip a single dword
Ben Skeggs 35a02f9
and hope that things would magically sort themselves out - they usually
Ben Skeggs 35a02f9
don't, and we end up with PFIFO being completely hung.
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
This commit also adds somewhat more useful logging when these exceptions
Ben Skeggs 35a02f9
occur.
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Ben Skeggs 35a02f9
---
Ben Skeggs 35a02f9
 drivers/gpu/drm/nouveau/nouveau_irq.c |   45 +++++++++++++++++++++++++++------
Ben Skeggs 35a02f9
 1 files changed, 37 insertions(+), 8 deletions(-)
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
diff --git a/drivers/gpu/drm/nouveau/nouveau_irq.c b/drivers/gpu/drm/nouveau/nouveau_irq.c
Ben Skeggs 35a02f9
index 53360f1..a0f31e4 100644
Ben Skeggs 35a02f9
--- a/drivers/gpu/drm/nouveau/nouveau_irq.c
Ben Skeggs 35a02f9
+++ b/drivers/gpu/drm/nouveau/nouveau_irq.c
Ben Skeggs 35a02f9
@@ -200,16 +200,45 @@ nouveau_fifo_irq_handler(struct drm_device *dev)
Ben Skeggs 35a02f9
		}
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
		if (status & NV_PFIFO_INTR_DMA_PUSHER) {
Ben Skeggs 35a02f9
-			NV_INFO(dev, "PFIFO_DMA_PUSHER - Ch %d\n", chid);
Ben Skeggs 35a02f9
+			u32 get = nv_rd32(dev, 0x003244);
Ben Skeggs 35a02f9
+			u32 put = nv_rd32(dev, 0x003240);
Ben Skeggs 35a02f9
+			u32 push = nv_rd32(dev, 0x003220);
Ben Skeggs 35a02f9
+			u32 state = nv_rd32(dev, 0x003228);
Ben Skeggs 35a02f9
+
Ben Skeggs 35a02f9
+			if (dev_priv->card_type == NV_50) {
Ben Skeggs 35a02f9
+				u32 ho_get = nv_rd32(dev, 0x003328);
Ben Skeggs 35a02f9
+				u32 ho_put = nv_rd32(dev, 0x003320);
Ben Skeggs 35a02f9
+				u32 ib_get = nv_rd32(dev, 0x003334);
Ben Skeggs 35a02f9
+				u32 ib_put = nv_rd32(dev, 0x003330);
Ben Skeggs 35a02f9
+
Ben Skeggs 35a02f9
+				NV_INFO(dev, "PFIFO_DMA_PUSHER - Ch %d Get 0x%02x%08x "
Ben Skeggs 35a02f9
+					     "Put 0x%02x%08x IbGet 0x%08x IbPut 0x%08x "
Ben Skeggs 35a02f9
+					     "State 0x%08x Push 0x%08x\n",
Ben Skeggs 35a02f9
+					chid, ho_get, get, ho_put, put, ib_get, ib_put,
Ben Skeggs 35a02f9
+					state, push);
Ben Skeggs 35a02f9
+
Ben Skeggs 35a02f9
+				/* METHOD_COUNT, in DMA_STATE on earlier chipsets */
Ben Skeggs 35a02f9
+				nv_wr32(dev, 0x003364, 0x00000000);
Ben Skeggs 35a02f9
+				if (get != put || ho_get != ho_put) {
Ben Skeggs 35a02f9
+					nv_wr32(dev, 0x003244, put);
Ben Skeggs 35a02f9
+					nv_wr32(dev, 0x003328, ho_put);
Ben Skeggs 35a02f9
+				} else
Ben Skeggs 35a02f9
+				if (ib_get != ib_put) {
Ben Skeggs 35a02f9
+					nv_wr32(dev, 0x003334, ib_put);
Ben Skeggs 35a02f9
+				}
Ben Skeggs 35a02f9
+			} else {
Ben Skeggs 35a02f9
+				NV_INFO(dev, "PFIFO_DMA_PUSHER - Ch %d Get 0x%08x "
Ben Skeggs 35a02f9
+					     "Put 0x%08x State 0x%08x Push 0x%08x\n",
Ben Skeggs 35a02f9
+					chid, get, put, state, push);
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
-			status &= ~NV_PFIFO_INTR_DMA_PUSHER;
Ben Skeggs 35a02f9
-			nv_wr32(dev, NV03_PFIFO_INTR_0,
Ben Skeggs 35a02f9
-						NV_PFIFO_INTR_DMA_PUSHER);
Ben Skeggs 35a02f9
+				if (get != put)
Ben Skeggs 35a02f9
+					nv_wr32(dev, 0x003244, put);
Ben Skeggs 35a02f9
+			}
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
-			nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_STATE, 0x00000000);
Ben Skeggs 35a02f9
-			if (nv_rd32(dev, NV04_PFIFO_CACHE1_DMA_PUT) != get)
Ben Skeggs 35a02f9
-				nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_GET,
Ben Skeggs 35a02f9
-								get + 4);
Ben Skeggs 35a02f9
+			nv_wr32(dev, 0x003228, 0x00000000);
Ben Skeggs 35a02f9
+			nv_wr32(dev, 0x003220, 0x00000001);
Ben Skeggs 35a02f9
+			nv_wr32(dev, 0x002100, NV_PFIFO_INTR_DMA_PUSHER);
Ben Skeggs 35a02f9
+			status &= ~NV_PFIFO_INTR_DMA_PUSHER;
Ben Skeggs 35a02f9
		}
Ben Skeggs 35a02f9
Ben Skeggs 35a02f9
		if (status & NV_PFIFO_INTR_SEMAPHORE) {
Ben Skeggs 35a02f9
--
Ben Skeggs 35a02f9
1.7.2.2