dri-devel Archive on lore.kernel.org
 help / color / mirror / Atom feed
From: j.glisse@gmail.com
To: dri-devel@lists.freedesktop.org
Cc: Jerome Glisse <jglisse@redhat.com>
Subject: [PATCH 4/4] drm/radeon: improve sa allocator to agressivly free idle bo
Date: Wed,  2 May 2012 16:20:13 -0400	[thread overview]
Message-ID: <1335990013-5877-5-git-send-email-j.glisse@gmail.com> (raw)
In-Reply-To: <1335990013-5877-1-git-send-email-j.glisse@gmail.com>

From: Jerome Glisse <jglisse@redhat.com>

With fence rework it's now easier to agressivly free idle bo
when there is no hole to satisfy current allocation request.
The hit of some cs ioctl to have to go through the sa bo list
and free them is minimal, it happens once in while and avoid
some fence waiting.

Signed-off-by: Jerome Glisse <jglisse@redhat.com>
---
 drivers/gpu/drm/radeon/radeon.h       |    1 +
 drivers/gpu/drm/radeon/radeon_fence.c |    2 +-
 drivers/gpu/drm/radeon/radeon_sa.c    |   51 +++++++++++++++++++++++++++++---
 3 files changed, 48 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h
index 141aee2..5459722 100644
--- a/drivers/gpu/drm/radeon/radeon.h
+++ b/drivers/gpu/drm/radeon/radeon.h
@@ -314,6 +314,7 @@ int radeon_fence_wait_empty(struct radeon_device *rdev, int ring);
 struct radeon_fence *radeon_fence_ref(struct radeon_fence *fence);
 void radeon_fence_unref(struct radeon_fence **fence);
 unsigned radeon_fence_count_emitted(struct radeon_device *rdev, int ring);
+bool radeon_fence_poll(struct radeon_device *rdev, int ring);
 
 /*
  * Tiling registers
diff --git a/drivers/gpu/drm/radeon/radeon_fence.c b/drivers/gpu/drm/radeon/radeon_fence.c
index 3f34f7b..043f431 100644
--- a/drivers/gpu/drm/radeon/radeon_fence.c
+++ b/drivers/gpu/drm/radeon/radeon_fence.c
@@ -78,7 +78,7 @@ int radeon_fence_emit(struct radeon_device *rdev, struct radeon_fence *fence)
 	return 0;
 }
 
-static bool radeon_fence_poll(struct radeon_device *rdev, int ring)
+bool radeon_fence_poll(struct radeon_device *rdev, int ring)
 {
 	uint64_t seq;
 
diff --git a/drivers/gpu/drm/radeon/radeon_sa.c b/drivers/gpu/drm/radeon/radeon_sa.c
index e758aaa..2cbf5ba 100644
--- a/drivers/gpu/drm/radeon/radeon_sa.c
+++ b/drivers/gpu/drm/radeon/radeon_sa.c
@@ -48,6 +48,10 @@
 #include "drm.h"
 #include "radeon.h"
 
+static bool radeon_sa_manager_try_free(struct radeon_device *rdev,
+				       struct radeon_sa_manager *sa_manager,
+				       struct radeon_sa_bo *oldest);
+
 int radeon_sa_bo_manager_init(struct radeon_device *rdev,
 			      struct radeon_sa_manager *sa_manager,
 			      unsigned size, u32 domain)
@@ -77,7 +81,16 @@ void radeon_sa_bo_manager_fini(struct radeon_device *rdev,
 	struct radeon_sa_bo *sa_bo, *tmp;
 
 	if (!list_empty(&sa_manager->sa_bo)) {
-		dev_err(rdev->dev, "sa_manager is not empty, clearing anyway\n");
+		struct radeon_sa_bo *oldest;
+
+		/* try to free them */
+		oldest =  list_entry(sa_manager->sa_bo.next, struct radeon_sa_bo, list);
+		radeon_sa_manager_try_free(rdev, sa_manager, oldest);
+
+		if (!list_empty(&sa_manager->sa_bo)) {
+			/* something went wrong */
+			dev_err(rdev->dev, "sa_manager is not empty, clearing anyway\n");
+		}
 	}
 	list_for_each_entry_safe(sa_bo, tmp, &sa_manager->sa_bo, list) {
 		list_del_init(&sa_bo->list);
@@ -171,15 +184,43 @@ static void radeon_sa_bo_free_locked(struct radeon_device *rdev, struct radeon_s
 }
 
 static bool radeon_sa_manager_try_free(struct radeon_device *rdev,
+				       struct radeon_sa_manager *sa_manager,
 				       struct radeon_sa_bo *oldest)
 {
-	if (oldest->fence && oldest->fence->emitted) {
-		if (radeon_fence_signaled(oldest->fence)) {
+	struct radeon_sa_bo *tmp, *sa_bo;
+	unsigned ring, free_count = 0;
+
+	if (oldest->fence == NULL || !oldest->fence->emitted) {
+		return false;
+	}
+	ring = oldest->fence->ring;
+	radeon_fence_poll(rdev, ring);
+	if (rdev->fence_drv[ring].last_seq < oldest->fence->seq) {
+		return false;
+	}
+	free_count++;
+	/* go over the remaining of the list and try to free as much
+	 * as possible
+	 */
+	sa_bo = oldest;
+	list_for_each_entry_safe_continue(sa_bo, tmp, &sa_manager->sa_bo, list) {
+		if (sa_bo->fence == NULL || !sa_bo->fence->emitted) {
+			radeon_sa_bo_free_locked(rdev, oldest);
+			return true;
+		}
+		if (ring != sa_bo->fence->ring) {
+			ring = sa_bo->fence->ring;
+			radeon_fence_poll(rdev, ring);
+		}
+		if (rdev->fence_drv[ring].last_seq < sa_bo->fence->seq) {
 			radeon_sa_bo_free_locked(rdev, oldest);
 			return true;
 		}
+		radeon_sa_bo_free_locked(rdev, sa_bo);
+		free_count++;
 	}
-	return false;
+	radeon_sa_bo_free_locked(rdev, oldest);
+	return true;
 }
 
 /*
@@ -260,7 +301,7 @@ retry:
 		}
 	}
 	/* try to be optimist and free the oldest one */
-	if (radeon_sa_manager_try_free(rdev, oldest)) {
+	if (radeon_sa_manager_try_free(rdev, sa_manager, oldest)) {
 		goto retry;
 	}
 
-- 
1.7.7.6

      parent reply	other threads:[~2012-05-02 20:20 UTC|newest]

Thread overview: 17+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-05-02 20:20 [RFC] Convert fence to use 64bits sequence j.glisse
2012-05-02 20:20 ` [PATCH 1/4] drm/radeon: allow to allocate adjacent scratch reg j.glisse
2012-05-02 20:20 ` [PATCH 2/4] drm/radeon: convert fence to uint64_t j.glisse
2012-05-03  7:21   ` Michel Dänzer
2012-05-03 11:39     ` Christian König
2012-05-03 15:56       ` Jerome Glisse
2012-05-03 16:29         ` Alex Deucher
2012-05-03 16:34           ` Jerome Glisse
2012-05-03 16:45             ` Christian König
2012-05-03 20:46             ` Jerome Glisse
2012-05-03 21:04               ` Alex Deucher
2012-05-03 21:06                 ` [PATCH] drm/radeon: clarify and extend wb setup on APUs and NI+ asics alexdeucher
2012-05-04  5:47                   ` Michel Dänzer
2012-05-03 21:36                 ` Re: [PATCH 2/4] drm/radeon: convert fence to uint64_t Jerome Glisse
2012-05-02 20:20 ` [PATCH 3/4] drm/radeon: rework fence handling, drop fence list j.glisse
2012-05-02 20:43   ` Adam Jackson
2012-05-02 20:20 ` j.glisse [this message]

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1335990013-5877-5-git-send-email-j.glisse@gmail.com \
    --to=j.glisse@gmail.com \
    --cc=dri-devel@lists.freedesktop.org \
    --cc=jglisse@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox