diff options
Diffstat (limited to 'drivers/gpu')
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_drv.h | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_fence.c | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_object.c | 97 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nv10_graph.c | 1 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nv20_graph.c | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nv40_graph.c | 1 |
6 files changed, 53 insertions, 52 deletions
diff --git a/drivers/gpu/drm/nouveau/nouveau_drv.h b/drivers/gpu/drm/nouveau/nouveau_drv.h index 2fdc26655ca..2099f04c0b0 100644 --- a/drivers/gpu/drm/nouveau/nouveau_drv.h +++ b/drivers/gpu/drm/nouveau/nouveau_drv.h @@ -842,8 +842,6 @@ extern int nouveau_gpuobj_gart_dma_new(struct nouveau_channel *, uint32_t *o_ret); extern int nouveau_gpuobj_gr_new(struct nouveau_channel *, int class, struct nouveau_gpuobj **); -extern int nouveau_gpuobj_sw_new(struct nouveau_channel *, int class, - struct nouveau_gpuobj **); extern int nouveau_ioctl_grobj_alloc(struct drm_device *, void *data, struct drm_file *); extern int nouveau_ioctl_gpuobj_free(struct drm_device *, void *data, diff --git a/drivers/gpu/drm/nouveau/nouveau_fence.c b/drivers/gpu/drm/nouveau/nouveau_fence.c index f70bec835f5..75ce1b45d8a 100644 --- a/drivers/gpu/drm/nouveau/nouveau_fence.c +++ b/drivers/gpu/drm/nouveau/nouveau_fence.c @@ -437,7 +437,7 @@ nouveau_fence_channel_init(struct nouveau_channel *chan) int ret; /* Create an NV_SW object for various sync purposes */ - ret = nouveau_gpuobj_sw_new(chan, NV_SW, &obj); + ret = nouveau_gpuobj_gr_new(chan, NV_SW, &obj); if (ret) return ret; diff --git a/drivers/gpu/drm/nouveau/nouveau_object.c b/drivers/gpu/drm/nouveau/nouveau_object.c index 70ffd753050..9c26da4cdc0 100644 --- a/drivers/gpu/drm/nouveau/nouveau_object.c +++ b/drivers/gpu/drm/nouveau/nouveau_object.c @@ -495,23 +495,67 @@ nouveau_gpuobj_gart_dma_new(struct nouveau_channel *chan, entry[5]: set to 0? */ +static int +nouveau_gpuobj_sw_new(struct nouveau_channel *chan, int class, + struct nouveau_gpuobj **gpuobj_ret) +{ + struct drm_nouveau_private *dev_priv; + struct nouveau_gpuobj *gpuobj; + + if (!chan || !gpuobj_ret || *gpuobj_ret != NULL) + return -EINVAL; + dev_priv = chan->dev->dev_private; + + gpuobj = kzalloc(sizeof(*gpuobj), GFP_KERNEL); + if (!gpuobj) + return -ENOMEM; + gpuobj->dev = chan->dev; + gpuobj->engine = NVOBJ_ENGINE_SW; + gpuobj->class = class; + kref_init(&gpuobj->refcount); + gpuobj->cinst = 0x40; + + spin_lock(&dev_priv->ramin_lock); + list_add_tail(&gpuobj->list, &dev_priv->gpuobj_list); + spin_unlock(&dev_priv->ramin_lock); + *gpuobj_ret = gpuobj; + return 0; +} + int nouveau_gpuobj_gr_new(struct nouveau_channel *chan, int class, struct nouveau_gpuobj **gpuobj) { + struct drm_nouveau_private *dev_priv = chan->dev->dev_private; + struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph; + struct nouveau_pgraph_object_class *grc; struct drm_device *dev = chan->dev; - struct drm_nouveau_private *dev_priv = dev->dev_private; int ret; NV_DEBUG(dev, "ch%d class=0x%04x\n", chan->id, class); + grc = pgraph->grclass; + while (grc->id) { + if (grc->id == class) + break; + grc++; + } + + if (!grc->id) { + NV_ERROR(dev, "illegal object class: 0x%x\n", class); + return -EINVAL; + } + + if (grc->engine == NVOBJ_ENGINE_SW) + return nouveau_gpuobj_sw_new(chan, class, gpuobj); + ret = nouveau_gpuobj_new(dev, chan, nouveau_gpuobj_class_instmem_size(dev, class), 16, NVOBJ_FLAG_ZERO_ALLOC | NVOBJ_FLAG_ZERO_FREE, gpuobj); if (ret) { - NV_ERROR(dev, "Error creating gpuobj: %d\n", ret); + NV_ERROR(dev, "error creating gpuobj: %d\n", ret); return ret; } @@ -541,38 +585,11 @@ nouveau_gpuobj_gr_new(struct nouveau_channel *chan, int class, } dev_priv->engine.instmem.flush(dev); - (*gpuobj)->engine = NVOBJ_ENGINE_GR; + (*gpuobj)->engine = grc->engine; (*gpuobj)->class = class; return 0; } -int -nouveau_gpuobj_sw_new(struct nouveau_channel *chan, int class, - struct nouveau_gpuobj **gpuobj_ret) -{ - struct drm_nouveau_private *dev_priv; - struct nouveau_gpuobj *gpuobj; - - if (!chan || !gpuobj_ret || *gpuobj_ret != NULL) - return -EINVAL; - dev_priv = chan->dev->dev_private; - - gpuobj = kzalloc(sizeof(*gpuobj), GFP_KERNEL); - if (!gpuobj) - return -ENOMEM; - gpuobj->dev = chan->dev; - gpuobj->engine = NVOBJ_ENGINE_SW; - gpuobj->class = class; - kref_init(&gpuobj->refcount); - gpuobj->cinst = 0x40; - - spin_lock(&dev_priv->ramin_lock); - list_add_tail(&gpuobj->list, &dev_priv->gpuobj_list); - spin_unlock(&dev_priv->ramin_lock); - *gpuobj_ret = gpuobj; - return 0; -} - static int nouveau_gpuobj_channel_init_pramin(struct nouveau_channel *chan) { @@ -868,10 +885,7 @@ nouveau_gpuobj_resume(struct drm_device *dev) int nouveau_ioctl_grobj_alloc(struct drm_device *dev, void *data, struct drm_file *file_priv) { - struct drm_nouveau_private *dev_priv = dev->dev_private; struct drm_nouveau_grobj_alloc *init = data; - struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph; - struct nouveau_pgraph_object_class *grc; struct nouveau_gpuobj *gr = NULL; struct nouveau_channel *chan; int ret; @@ -879,18 +893,6 @@ int nouveau_ioctl_grobj_alloc(struct drm_device *dev, void *data, if (init->handle == ~0) return -EINVAL; - grc = pgraph->grclass; - while (grc->id) { - if (grc->id == init->class) - break; - grc++; - } - - if (!grc->id) { - NV_ERROR(dev, "Illegal object class: 0x%x\n", init->class); - return -EPERM; - } - chan = nouveau_channel_get(dev, file_priv, init->channel); if (IS_ERR(chan)) return PTR_ERR(chan); @@ -900,10 +902,7 @@ int nouveau_ioctl_grobj_alloc(struct drm_device *dev, void *data, goto out; } - if (grc->engine != NVOBJ_ENGINE_SW) - ret = nouveau_gpuobj_gr_new(chan, grc->id, &gr); - else - ret = nouveau_gpuobj_sw_new(chan, grc->id, &gr); + ret = nouveau_gpuobj_gr_new(chan, init->class, &gr); if (ret) { NV_ERROR(dev, "Error creating object: %d (%d/0x%08x)\n", ret, init->channel, init->handle); diff --git a/drivers/gpu/drm/nouveau/nv10_graph.c b/drivers/gpu/drm/nouveau/nv10_graph.c index 375d63161d1..ed31a622889 100644 --- a/drivers/gpu/drm/nouveau/nv10_graph.c +++ b/drivers/gpu/drm/nouveau/nv10_graph.c @@ -1075,6 +1075,7 @@ static struct nouveau_pgraph_object_method nv17_graph_celsius_mthds[] = { }; struct nouveau_pgraph_object_class nv10_graph_grclass[] = { + { 0x506e, NVOBJ_ENGINE_SW, NULL }, /* nvsw */ { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */ { 0x0039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */ { 0x004a, NVOBJ_ENGINE_GR, NULL }, /* gdirect */ diff --git a/drivers/gpu/drm/nouveau/nv20_graph.c b/drivers/gpu/drm/nouveau/nv20_graph.c index 109418d72f9..872f8d05969 100644 --- a/drivers/gpu/drm/nouveau/nv20_graph.c +++ b/drivers/gpu/drm/nouveau/nv20_graph.c @@ -757,6 +757,7 @@ nv30_graph_init(struct drm_device *dev) } struct nouveau_pgraph_object_class nv20_graph_grclass[] = { + { 0x506e, NVOBJ_ENGINE_SW, NULL }, /* nvsw */ { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */ { 0x0039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */ { 0x004a, NVOBJ_ENGINE_GR, NULL }, /* gdirect */ @@ -777,6 +778,7 @@ struct nouveau_pgraph_object_class nv20_graph_grclass[] = { }; struct nouveau_pgraph_object_class nv30_graph_grclass[] = { + { 0x506e, NVOBJ_ENGINE_SW, NULL }, /* nvsw */ { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */ { 0x0039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */ { 0x004a, NVOBJ_ENGINE_GR, NULL }, /* gdirect */ diff --git a/drivers/gpu/drm/nouveau/nv40_graph.c b/drivers/gpu/drm/nouveau/nv40_graph.c index cd47760b2d0..70d957895ce 100644 --- a/drivers/gpu/drm/nouveau/nv40_graph.c +++ b/drivers/gpu/drm/nouveau/nv40_graph.c @@ -409,6 +409,7 @@ void nv40_graph_takedown(struct drm_device *dev) } struct nouveau_pgraph_object_class nv40_graph_grclass[] = { + { 0x506e, NVOBJ_ENGINE_SW, NULL }, /* nvsw */ { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */ { 0x0039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */ { 0x004a, NVOBJ_ENGINE_GR, NULL }, /* gdirect */ |