aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBen Skeggs <bskeggs@redhat.com>2012-11-26 20:05:36 -0500
committerBen Skeggs <bskeggs@redhat.com>2012-11-28 18:58:12 -0500
commitedc260d06181cbf38d5cd326e6cf824d8e2e0eaf (patch)
tree2d840c53ad09f1bdc02a29948bdd0d1f0349d329
parentc9aa763fe9690a334d0636f88e6eb85340f36f89 (diff)
drm/nouveau/fifo: trigger engine context unload before zeroing context pointer
Fixes a PCE0 page fault noticed on NVD9 during module unload. Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
-rw-r--r--drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c20
-rw-r--r--drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c16
-rw-r--r--drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c7
-rw-r--r--drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c7
4 files changed, 25 insertions, 25 deletions
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c
index 3d3ed547ed4c..bd096364f680 100644
--- a/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c
+++ b/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c
@@ -112,14 +112,6 @@ nv50_fifo_context_detach(struct nouveau_object *parent, bool suspend,
112 return -EINVAL; 112 return -EINVAL;
113 } 113 }
114 114
115 nv_wo32(base->eng, addr + 0x00, 0x00000000);
116 nv_wo32(base->eng, addr + 0x04, 0x00000000);
117 nv_wo32(base->eng, addr + 0x08, 0x00000000);
118 nv_wo32(base->eng, addr + 0x0c, 0x00000000);
119 nv_wo32(base->eng, addr + 0x10, 0x00000000);
120 nv_wo32(base->eng, addr + 0x14, 0x00000000);
121 bar->flush(bar);
122
123 /* HW bug workaround: 115 /* HW bug workaround:
124 * 116 *
125 * PFIFO will hang forever if the connected engines don't report 117 * PFIFO will hang forever if the connected engines don't report
@@ -141,8 +133,18 @@ nv50_fifo_context_detach(struct nouveau_object *parent, bool suspend,
141 if (suspend) 133 if (suspend)
142 ret = -EBUSY; 134 ret = -EBUSY;
143 } 135 }
144
145 nv_wr32(priv, 0x00b860, me); 136 nv_wr32(priv, 0x00b860, me);
137
138 if (ret == 0) {
139 nv_wo32(base->eng, addr + 0x00, 0x00000000);
140 nv_wo32(base->eng, addr + 0x04, 0x00000000);
141 nv_wo32(base->eng, addr + 0x08, 0x00000000);
142 nv_wo32(base->eng, addr + 0x0c, 0x00000000);
143 nv_wo32(base->eng, addr + 0x10, 0x00000000);
144 nv_wo32(base->eng, addr + 0x14, 0x00000000);
145 bar->flush(bar);
146 }
147
146 return ret; 148 return ret;
147} 149}
148 150
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c
index 7969df948cfa..1eb1c512f503 100644
--- a/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c
+++ b/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c
@@ -95,14 +95,6 @@ nv84_fifo_context_detach(struct nouveau_object *parent, bool suspend,
95 return -EINVAL; 95 return -EINVAL;
96 } 96 }
97 97
98 nv_wo32(base->eng, addr + 0x00, 0x00000000);
99 nv_wo32(base->eng, addr + 0x04, 0x00000000);
100 nv_wo32(base->eng, addr + 0x08, 0x00000000);
101 nv_wo32(base->eng, addr + 0x0c, 0x00000000);
102 nv_wo32(base->eng, addr + 0x10, 0x00000000);
103 nv_wo32(base->eng, addr + 0x14, 0x00000000);
104 bar->flush(bar);
105
106 save = nv_mask(priv, 0x002520, 0x0000003f, 1 << engn); 98 save = nv_mask(priv, 0x002520, 0x0000003f, 1 << engn);
107 nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12); 99 nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12);
108 done = nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff); 100 done = nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff);
@@ -112,6 +104,14 @@ nv84_fifo_context_detach(struct nouveau_object *parent, bool suspend,
112 if (suspend) 104 if (suspend)
113 return -EBUSY; 105 return -EBUSY;
114 } 106 }
107
108 nv_wo32(base->eng, addr + 0x00, 0x00000000);
109 nv_wo32(base->eng, addr + 0x04, 0x00000000);
110 nv_wo32(base->eng, addr + 0x08, 0x00000000);
111 nv_wo32(base->eng, addr + 0x0c, 0x00000000);
112 nv_wo32(base->eng, addr + 0x10, 0x00000000);
113 nv_wo32(base->eng, addr + 0x14, 0x00000000);
114 bar->flush(bar);
115 return 0; 115 return 0;
116} 116}
117 117
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c
index 8f25255247e5..b4365dde1859 100644
--- a/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c
+++ b/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c
@@ -147,10 +147,6 @@ nvc0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
147 return -EINVAL; 147 return -EINVAL;
148 } 148 }
149 149
150 nv_wo32(base, addr + 0x00, 0x00000000);
151 nv_wo32(base, addr + 0x04, 0x00000000);
152 bar->flush(bar);
153
154 nv_wr32(priv, 0x002634, chan->base.chid); 150 nv_wr32(priv, 0x002634, chan->base.chid);
155 if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) { 151 if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
156 nv_error(priv, "channel %d kick timeout\n", chan->base.chid); 152 nv_error(priv, "channel %d kick timeout\n", chan->base.chid);
@@ -158,6 +154,9 @@ nvc0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
158 return -EBUSY; 154 return -EBUSY;
159 } 155 }
160 156
157 nv_wo32(base, addr + 0x00, 0x00000000);
158 nv_wo32(base, addr + 0x04, 0x00000000);
159 bar->flush(bar);
161 return 0; 160 return 0;
162} 161}
163 162
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c
index 9df59c028e45..c930da99c2c1 100644
--- a/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c
+++ b/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c
@@ -182,10 +182,6 @@ nve0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
182 return -EINVAL; 182 return -EINVAL;
183 } 183 }
184 184
185 nv_wo32(base, addr + 0x00, 0x00000000);
186 nv_wo32(base, addr + 0x04, 0x00000000);
187 bar->flush(bar);
188
189 nv_wr32(priv, 0x002634, chan->base.chid); 185 nv_wr32(priv, 0x002634, chan->base.chid);
190 if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) { 186 if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
191 nv_error(priv, "channel %d kick timeout\n", chan->base.chid); 187 nv_error(priv, "channel %d kick timeout\n", chan->base.chid);
@@ -193,6 +189,9 @@ nve0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
193 return -EBUSY; 189 return -EBUSY;
194 } 190 }
195 191
192 nv_wo32(base, addr + 0x00, 0x00000000);
193 nv_wo32(base, addr + 0x04, 0x00000000);
194 bar->flush(bar);
196 return 0; 195 return 0;
197} 196}
198 197