aboutsummaryrefslogtreecommitdiff
path: root/libdrm/nouveau
diff options
context:
space:
mode:
authorBen Skeggs <skeggsb@gmail.com>2009-02-05 23:03:29 +1000
committerBen Skeggs <skeggsb@gmail.com>2009-02-05 23:17:05 +1000
commit97fdadee6a79f9406a55c235ee46104814321152 (patch)
tree74b1cc1f0346b17a3c945eeb49bc31edd2c75ce2 /libdrm/nouveau
parent8b8803695b24d4cb4d041437a4709be06e59471b (diff)
nouveau: fix some issues where buffer objects never get freed
Diffstat (limited to 'libdrm/nouveau')
-rw-r--r--libdrm/nouveau/nouveau_bo.c15
-rw-r--r--libdrm/nouveau/nouveau_channel.c11
2 files changed, 22 insertions, 4 deletions
diff --git a/libdrm/nouveau/nouveau_bo.c b/libdrm/nouveau/nouveau_bo.c
index 0ab426dc..6b9877fc 100644
--- a/libdrm/nouveau/nouveau_bo.c
+++ b/libdrm/nouveau/nouveau_bo.c
@@ -435,10 +435,18 @@ nouveau_bo_del(struct nouveau_bo **bo)
}
nouveau_bo_ufree(nvbo);
- if (!nouveau_device(nvbo->base.device)->mm_enabled && nvbo->fence)
- nouveau_fence_signal_cb(nvbo->fence, nouveau_bo_del_cb, nvbo);
- else
+
+ if (!nouveau_device(nvbo->base.device)->mm_enabled && nvbo->fence) {
+ nouveau_fence_flush(nvbo->fence->channel);
+ if (nouveau_fence(nvbo->fence)->signalled) {
+ nouveau_bo_del_cb(nvbo);
+ } else {
+ nouveau_fence_signal_cb(nvbo->fence,
+ nouveau_bo_del_cb, nvbo);
+ }
+ } else {
nouveau_bo_del_cb(nvbo);
+ }
}
int
@@ -786,7 +794,6 @@ nouveau_bo_busy(struct nouveau_bo *bo, uint32_t access)
return 1;
}
-#include <stdio.h>
struct drm_nouveau_gem_pushbuf_bo *
nouveau_bo_emit_buffer(struct nouveau_channel *chan, struct nouveau_bo *bo)
{
diff --git a/libdrm/nouveau/nouveau_channel.c b/libdrm/nouveau/nouveau_channel.c
index e0fb4157..5de27dc8 100644
--- a/libdrm/nouveau/nouveau_channel.c
+++ b/libdrm/nouveau/nouveau_channel.c
@@ -150,6 +150,17 @@ nouveau_channel_free(struct nouveau_channel **chan)
FIRE_RING(&nvchan->base);
+ if (!nvdev->mm_enabled) {
+ struct nouveau_fence *fence = NULL;
+
+ /* Make sure all buffer objects on delayed delete queue
+ * actually get freed.
+ */
+ nouveau_fence_new(&nvchan->base, &fence);
+ nouveau_fence_emit(fence);
+ nouveau_fence_wait(&fence);
+ }
+
if (nvchan->notifier_block)
drmUnmap(nvchan->notifier_block, nvchan->drm.notifier_size);