summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBen Skeggs <skeggsb@gmail.com>2007-08-10 13:53:10 +1000
committerBen Skeggs <skeggsb@gmail.com>2007-08-10 13:53:10 +1000
commit39907f613b6c84499c34c9a6ece5f5dde64788c0 (patch)
tree6056d3cc52bf0999746a5d6817e586154fc4b42b
parent7784e8c6e74b93ffb39d82e3385bd3268a55507c (diff)
nouveau: Allow creation of gpuobjs before any other init has taken place.
-rw-r--r--shared-core/nouveau_drv.h2
-rw-r--r--shared-core/nouveau_object.c26
-rw-r--r--shared-core/nouveau_state.c5
3 files changed, 30 insertions, 3 deletions
diff --git a/shared-core/nouveau_drv.h b/shared-core/nouveau_drv.h
index 572df46e..4d5c7f7e 100644
--- a/shared-core/nouveau_drv.h
+++ b/shared-core/nouveau_drv.h
@@ -370,8 +370,10 @@ extern int nouveau_fifo_alloc(struct drm_device *dev,
extern void nouveau_fifo_free(struct nouveau_channel *);
/* nouveau_object.c */
+extern int nouveau_gpuobj_early_init(struct drm_device *);
extern int nouveau_gpuobj_init(struct drm_device *);
extern void nouveau_gpuobj_takedown(struct drm_device *);
+extern void nouveau_gpuobj_late_takedown(struct drm_device *);
extern int nouveau_gpuobj_channel_init(struct nouveau_channel *,
uint32_t vram_h, uint32_t tt_h);
extern void nouveau_gpuobj_channel_takedown(struct nouveau_channel *);
diff --git a/shared-core/nouveau_object.c b/shared-core/nouveau_object.c
index bb096531..d4142e44 100644
--- a/shared-core/nouveau_object.c
+++ b/shared-core/nouveau_object.c
@@ -265,11 +265,25 @@ nouveau_gpuobj_new(struct drm_device *dev, struct nouveau_channel *chan,
}
int
+nouveau_gpuobj_early_init(struct drm_device *dev)
+{
+ struct drm_nouveau_private *dev_priv = dev->dev_private;
+
+ DRM_DEBUG("\n");
+
+ INIT_LIST_HEAD(&dev_priv->gpuobj_list);
+
+ return 0;
+}
+
+int
nouveau_gpuobj_init(struct drm_device *dev)
{
struct drm_nouveau_private *dev_priv = dev->dev_private;
int ret;
+ DRM_DEBUG("\n");
+
if (dev_priv->card_type < NV_50) {
if ((ret = nouveau_gpuobj_new_fake(dev, dev_priv->ramht_offset,
dev_priv->ramht_size,
@@ -286,12 +300,20 @@ void
nouveau_gpuobj_takedown(struct drm_device *dev)
{
struct drm_nouveau_private *dev_priv = dev->dev_private;
- struct nouveau_gpuobj *gpuobj = NULL;
- struct list_head *entry, *tmp;
DRM_DEBUG("\n");
nouveau_gpuobj_del(dev, &dev_priv->ramht);
+}
+
+void
+nouveau_gpuobj_late_takedown(struct drm_device *dev)
+{
+ struct drm_nouveau_private *dev_priv = dev->dev_private;
+ struct nouveau_gpuobj *gpuobj = NULL;
+ struct list_head *entry, *tmp;
+
+ DRM_DEBUG("\n");
list_for_each_safe(entry, tmp, &dev_priv->gpuobj_list) {
gpuobj = list_entry(entry, struct nouveau_gpuobj, list);
diff --git a/shared-core/nouveau_state.c b/shared-core/nouveau_state.c
index e80e77a5..eac38060 100644
--- a/shared-core/nouveau_state.c
+++ b/shared-core/nouveau_state.c
@@ -296,7 +296,8 @@ nouveau_card_init(struct drm_device *dev)
engine = &dev_priv->Engine;
dev_priv->init_state = NOUVEAU_CARD_INIT_FAILED;
- INIT_LIST_HEAD(&dev_priv->gpuobj_list);
+ ret = nouveau_gpuobj_early_init(dev);
+ if (ret) return ret;
/* Initialise instance memory, must happen before mem_init so we
* know exactly how much VRAM we're able to use for "normal"
@@ -375,6 +376,8 @@ static void nouveau_card_takedown(struct drm_device *dev)
drm_irq_uninstall(dev);
+ nouveau_gpuobj_late_takedown(dev);
+
dev_priv->init_state = NOUVEAU_CARD_INIT_DOWN;
}
}