diff options
author | Ben Skeggs <bskeggs@redhat.com> | 2010-10-19 20:39:35 -0400 |
---|---|---|
committer | Ben Skeggs <bskeggs@redhat.com> | 2010-12-03 00:06:56 -0500 |
commit | b8c157d3a9a13871742c8a8d3d4598c3791ed5f5 (patch) | |
tree | 3ee372c2e8aa1100148f3d6e8232befdb386399a /drivers/gpu/drm/nouveau/nv50_graph.c | |
parent | a6a1a38075661bec189f2bad7912f8861e6ce357 (diff) |
drm/nouveau: only expose the object classes that are supported by the chipset
We previously added all the available classes for the entire generation,
even though the objects wouldn't work on the hardware.
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/nouveau/nv50_graph.c')
-rw-r--r-- | drivers/gpu/drm/nouveau/nv50_graph.c | 91 |
1 files changed, 61 insertions, 30 deletions
diff --git a/drivers/gpu/drm/nouveau/nv50_graph.c b/drivers/gpu/drm/nouveau/nv50_graph.c index 01a598917e3c..84ca90e91811 100644 --- a/drivers/gpu/drm/nouveau/nv50_graph.c +++ b/drivers/gpu/drm/nouveau/nv50_graph.c | |||
@@ -30,6 +30,8 @@ | |||
30 | #include "nouveau_ramht.h" | 30 | #include "nouveau_ramht.h" |
31 | #include "nouveau_grctx.h" | 31 | #include "nouveau_grctx.h" |
32 | 32 | ||
33 | static int nv50_graph_register(struct drm_device *); | ||
34 | |||
33 | static void | 35 | static void |
34 | nv50_graph_init_reset(struct drm_device *dev) | 36 | nv50_graph_init_reset(struct drm_device *dev) |
35 | { | 37 | { |
@@ -145,12 +147,15 @@ nv50_graph_init(struct drm_device *dev) | |||
145 | nv50_graph_init_reset(dev); | 147 | nv50_graph_init_reset(dev); |
146 | nv50_graph_init_regs__nv(dev); | 148 | nv50_graph_init_regs__nv(dev); |
147 | nv50_graph_init_regs(dev); | 149 | nv50_graph_init_regs(dev); |
148 | nv50_graph_init_intr(dev); | ||
149 | 150 | ||
150 | ret = nv50_graph_init_ctxctl(dev); | 151 | ret = nv50_graph_init_ctxctl(dev); |
151 | if (ret) | 152 | if (ret) |
152 | return ret; | 153 | return ret; |
153 | 154 | ||
155 | ret = nv50_graph_register(dev); | ||
156 | if (ret) | ||
157 | return ret; | ||
158 | nv50_graph_init_intr(dev); | ||
154 | return 0; | 159 | return 0; |
155 | } | 160 | } |
156 | 161 | ||
@@ -333,8 +338,8 @@ nv50_graph_context_switch(struct drm_device *dev) | |||
333 | } | 338 | } |
334 | 339 | ||
335 | static int | 340 | static int |
336 | nv50_graph_nvsw_dma_vblsem(struct nouveau_channel *chan, int grclass, | 341 | nv50_graph_nvsw_dma_vblsem(struct nouveau_channel *chan, |
337 | int mthd, uint32_t data) | 342 | u32 class, u32 mthd, u32 data) |
338 | { | 343 | { |
339 | struct nouveau_gpuobj *gpuobj; | 344 | struct nouveau_gpuobj *gpuobj; |
340 | 345 | ||
@@ -351,8 +356,8 @@ nv50_graph_nvsw_dma_vblsem(struct nouveau_channel *chan, int grclass, | |||
351 | } | 356 | } |
352 | 357 | ||
353 | static int | 358 | static int |
354 | nv50_graph_nvsw_vblsem_offset(struct nouveau_channel *chan, int grclass, | 359 | nv50_graph_nvsw_vblsem_offset(struct nouveau_channel *chan, |
355 | int mthd, uint32_t data) | 360 | u32 class, u32 mthd, u32 data) |
356 | { | 361 | { |
357 | if (nouveau_notifier_offset(chan->nvsw.vblsem, &data)) | 362 | if (nouveau_notifier_offset(chan->nvsw.vblsem, &data)) |
358 | return -ERANGE; | 363 | return -ERANGE; |
@@ -362,16 +367,16 @@ nv50_graph_nvsw_vblsem_offset(struct nouveau_channel *chan, int grclass, | |||
362 | } | 367 | } |
363 | 368 | ||
364 | static int | 369 | static int |
365 | nv50_graph_nvsw_vblsem_release_val(struct nouveau_channel *chan, int grclass, | 370 | nv50_graph_nvsw_vblsem_release_val(struct nouveau_channel *chan, |
366 | int mthd, uint32_t data) | 371 | u32 class, u32 mthd, u32 data) |
367 | { | 372 | { |
368 | chan->nvsw.vblsem_rval = data; | 373 | chan->nvsw.vblsem_rval = data; |
369 | return 0; | 374 | return 0; |
370 | } | 375 | } |
371 | 376 | ||
372 | static int | 377 | static int |
373 | nv50_graph_nvsw_vblsem_release(struct nouveau_channel *chan, int grclass, | 378 | nv50_graph_nvsw_vblsem_release(struct nouveau_channel *chan, |
374 | int mthd, uint32_t data) | 379 | u32 class, u32 mthd, u32 data) |
375 | { | 380 | { |
376 | struct drm_device *dev = chan->dev; | 381 | struct drm_device *dev = chan->dev; |
377 | struct drm_nouveau_private *dev_priv = dev->dev_private; | 382 | struct drm_nouveau_private *dev_priv = dev->dev_private; |
@@ -392,27 +397,53 @@ nv50_graph_nvsw_vblsem_release(struct nouveau_channel *chan, int grclass, | |||
392 | return 0; | 397 | return 0; |
393 | } | 398 | } |
394 | 399 | ||
395 | static struct nouveau_pgraph_object_method nv50_graph_nvsw_methods[] = { | 400 | static int |
396 | { 0x018c, nv50_graph_nvsw_dma_vblsem }, | 401 | nv50_graph_register(struct drm_device *dev) |
397 | { 0x0400, nv50_graph_nvsw_vblsem_offset }, | 402 | { |
398 | { 0x0404, nv50_graph_nvsw_vblsem_release_val }, | 403 | struct drm_nouveau_private *dev_priv = dev->dev_private; |
399 | { 0x0408, nv50_graph_nvsw_vblsem_release }, | 404 | |
400 | {} | 405 | if (dev_priv->engine.graph.registered) |
401 | }; | 406 | return 0; |
402 | 407 | ||
403 | struct nouveau_pgraph_object_class nv50_graph_grclass[] = { | 408 | NVOBJ_CLASS(dev, 0x506e, SW); /* nvsw */ |
404 | { 0x506e, NVOBJ_ENGINE_SW, nv50_graph_nvsw_methods }, /* nvsw */ | 409 | NVOBJ_MTHD (dev, 0x506e, 0x018c, nv50_graph_nvsw_dma_vblsem); |
405 | { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */ | 410 | NVOBJ_MTHD (dev, 0x506e, 0x0400, nv50_graph_nvsw_vblsem_offset); |
406 | { 0x5039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */ | 411 | NVOBJ_MTHD (dev, 0x506e, 0x0404, nv50_graph_nvsw_vblsem_release_val); |
407 | { 0x502d, NVOBJ_ENGINE_GR, NULL }, /* 2d */ | 412 | NVOBJ_MTHD (dev, 0x506e, 0x0408, nv50_graph_nvsw_vblsem_release); |
408 | { 0x50c0, NVOBJ_ENGINE_GR, NULL }, /* compute */ | 413 | |
409 | { 0x85c0, NVOBJ_ENGINE_GR, NULL }, /* compute (nva3, nva5, nva8) */ | 414 | NVOBJ_CLASS(dev, 0x0030, GR); /* null */ |
410 | { 0x5097, NVOBJ_ENGINE_GR, NULL }, /* tesla (nv50) */ | 415 | NVOBJ_CLASS(dev, 0x5039, GR); /* m2mf */ |
411 | { 0x8297, NVOBJ_ENGINE_GR, NULL }, /* tesla (nv8x/nv9x) */ | 416 | NVOBJ_CLASS(dev, 0x502d, GR); /* 2d */ |
412 | { 0x8397, NVOBJ_ENGINE_GR, NULL }, /* tesla (nva0, nvaa, nvac) */ | 417 | NVOBJ_CLASS(dev, 0x50c0, GR); /* compute */ |
413 | { 0x8597, NVOBJ_ENGINE_GR, NULL }, /* tesla (nva3, nva5, nva8) */ | 418 | NVOBJ_CLASS(dev, 0x85c0, GR); /* compute (nva3, nva5, nva8) */ |
414 | {} | 419 | |
415 | }; | 420 | /* tesla */ |
421 | if (dev_priv->chipset == 0x50) | ||
422 | NVOBJ_CLASS(dev, 0x5097, GR); /* tesla (nv50) */ | ||
423 | else | ||
424 | if (dev_priv->chipset < 0xa0) | ||
425 | NVOBJ_CLASS(dev, 0x8297, GR); /* tesla (nv8x/nv9x) */ | ||
426 | else { | ||
427 | switch (dev_priv->chipset) { | ||
428 | case 0xa0: | ||
429 | case 0xaa: | ||
430 | case 0xac: | ||
431 | NVOBJ_CLASS(dev, 0x8397, GR); | ||
432 | break; | ||
433 | case 0xa3: | ||
434 | case 0xa5: | ||
435 | case 0xa8: | ||
436 | NVOBJ_CLASS(dev, 0x8597, GR); | ||
437 | break; | ||
438 | case 0xaf: | ||
439 | NVOBJ_CLASS(dev, 0x8697, GR); | ||
440 | break; | ||
441 | } | ||
442 | } | ||
443 | |||
444 | dev_priv->engine.graph.registered = true; | ||
445 | return 0; | ||
446 | } | ||
416 | 447 | ||
417 | void | 448 | void |
418 | nv50_graph_tlb_flush(struct drm_device *dev) | 449 | nv50_graph_tlb_flush(struct drm_device *dev) |