aboutsummaryrefslogtreecommitdiffstats
path: root/common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch
diff options
context:
space:
mode:
Diffstat (limited to 'common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch')
-rw-r--r--common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch402
1 files changed, 0 insertions, 402 deletions
diff --git a/common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch b/common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch
deleted file mode 100644
index 0f7202a6..00000000
--- a/common/recipes-kernel/linux/files/0411-drm-amdgpu-move-wait_queue_head-from-adev-to-ring-v2.patch
+++ /dev/null
@@ -1,402 +0,0 @@
-From 7f06c236b964db3d8d086c5a0087b2eb4de3bf7a Mon Sep 17 00:00:00 2001
-From: "monk.liu" <monk.liu@amd.com>
-Date: Thu, 30 Jul 2015 18:28:12 +0800
-Subject: [PATCH 0411/1050] drm/amdgpu: move wait_queue_head from adev to ring
- (v2)
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
-
-thus unnecessary wake up could be avoid between rings
-v2:
-move wait_queue_head to fence_drv from ring
-
-Signed-off-by: monk.liu <monk.liu@amd.com>
-Reviewed-by: Christian König <christian.koenig@amd.com>
----
- drivers/gpu/drm/amd/amdgpu/amdgpu.h | 2 +-
- drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c | 225 ++++++++++--------------------
- drivers/gpu/drm/amd/amdgpu/amdgpu_ring.c | 2 +
- 3 files changed, 77 insertions(+), 152 deletions(-)
-
-diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu.h b/drivers/gpu/drm/amd/amdgpu/amdgpu.h
-index 5f32f85..98b4760 100644
---- a/drivers/gpu/drm/amd/amdgpu/amdgpu.h
-+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu.h
-@@ -391,6 +391,7 @@ struct amdgpu_fence_driver {
- struct amdgpu_irq_src *irq_src;
- unsigned irq_type;
- struct delayed_work lockup_work;
-+ wait_queue_head_t fence_queue;
- };
-
- /* some special values for the owner field */
-@@ -2036,7 +2037,6 @@ struct amdgpu_device {
- struct amdgpu_irq_src hpd_irq;
-
- /* rings */
-- wait_queue_head_t fence_queue;
- unsigned fence_context;
- struct mutex ring_lock;
- unsigned num_rings;
-diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
-index 0f9800b..60e6d66 100644
---- a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
-+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
-@@ -126,7 +126,8 @@ int amdgpu_fence_emit(struct amdgpu_ring *ring, void *owner,
- (*fence)->ring = ring;
- (*fence)->owner = owner;
- fence_init(&(*fence)->base, &amdgpu_fence_ops,
-- &adev->fence_queue.lock, adev->fence_context + ring->idx,
-+ &ring->fence_drv.fence_queue.lock,
-+ adev->fence_context + ring->idx,
- (*fence)->seq);
- amdgpu_ring_emit_fence(ring, ring->fence_drv.gpu_addr,
- (*fence)->seq,
-@@ -164,7 +165,7 @@ static int amdgpu_fence_check_signaled(wait_queue_t *wait, unsigned mode, int fl
- else
- FENCE_TRACE(&fence->base, "was already signaled\n");
-
-- __remove_wait_queue(&adev->fence_queue, &fence->fence_wake);
-+ __remove_wait_queue(&fence->ring->fence_drv.fence_queue, &fence->fence_wake);
- fence_put(&fence->base);
- } else
- FENCE_TRACE(&fence->base, "pending\n");
-@@ -265,8 +266,9 @@ static void amdgpu_fence_check_lockup(struct work_struct *work)
- return;
- }
-
-- if (amdgpu_fence_activity(ring))
-- wake_up_all(&ring->adev->fence_queue);
-+ if (amdgpu_fence_activity(ring)) {
-+ wake_up_all(&ring->fence_drv.fence_queue);
-+ }
- else if (amdgpu_ring_is_lockup(ring)) {
- /* good news we believe it's a lockup */
- dev_warn(ring->adev->dev, "GPU lockup (current fence id "
-@@ -276,7 +278,7 @@ static void amdgpu_fence_check_lockup(struct work_struct *work)
-
- /* remember that we need an reset */
- ring->adev->needs_reset = true;
-- wake_up_all(&ring->adev->fence_queue);
-+ wake_up_all(&ring->fence_drv.fence_queue);
- }
- up_read(&ring->adev->exclusive_lock);
- }
-@@ -364,7 +366,7 @@ void amdgpu_fence_process(struct amdgpu_ring *ring)
- } while (amd_sched_get_handled_seq(ring->scheduler) < latest_seq);
- }
-
-- wake_up_all(&ring->adev->fence_queue);
-+ wake_up_all(&ring->fence_drv.fence_queue);
- }
- exit:
- spin_unlock_irqrestore(&ring->fence_lock, irqflags);
-@@ -427,7 +429,6 @@ static bool amdgpu_fence_enable_signaling(struct fence *f)
- {
- struct amdgpu_fence *fence = to_amdgpu_fence(f);
- struct amdgpu_ring *ring = fence->ring;
-- struct amdgpu_device *adev = ring->adev;
-
- if (atomic64_read(&ring->fence_drv.last_seq) >= fence->seq)
- return false;
-@@ -435,7 +436,7 @@ static bool amdgpu_fence_enable_signaling(struct fence *f)
- fence->fence_wake.flags = 0;
- fence->fence_wake.private = NULL;
- fence->fence_wake.func = amdgpu_fence_check_signaled;
-- __add_wait_queue(&adev->fence_queue, &fence->fence_wake);
-+ __add_wait_queue(&ring->fence_drv.fence_queue, &fence->fence_wake);
- fence_get(f);
- FENCE_TRACE(&fence->base, "armed on ring %i!\n", ring->idx);
- return true;
-@@ -463,152 +464,79 @@ bool amdgpu_fence_signaled(struct amdgpu_fence *fence)
- return false;
- }
-
--/**
-- * amdgpu_fence_any_seq_signaled - check if any sequence number is signaled
-- *
-- * @adev: amdgpu device pointer
-- * @seq: sequence numbers
-- *
-- * Check if the last signaled fence sequnce number is >= the requested
-- * sequence number (all asics).
-- * Returns true if any has signaled (current value is >= requested value)
-- * or false if it has not. Helper function for amdgpu_fence_wait_seq.
-- */
--static bool amdgpu_fence_any_seq_signaled(struct amdgpu_device *adev, u64 *seq)
--{
-- unsigned i;
--
-- for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-- if (!adev->rings[i] || !seq[i])
-- continue;
--
-- if (amdgpu_fence_seq_signaled(adev->rings[i], seq[i]))
-- return true;
-- }
--
-- return false;
--}
--
--/**
-- * amdgpu_fence_wait_seq_timeout - wait for a specific sequence numbers
-- *
-- * @adev: amdgpu device pointer
-- * @target_seq: sequence number(s) we want to wait for
-- * @intr: use interruptable sleep
-- * @timeout: maximum time to wait, or MAX_SCHEDULE_TIMEOUT for infinite wait
-+/*
-+ * amdgpu_ring_wait_seq_timeout - wait for seq of the specific ring to signal
-+ * @ring: ring to wait on for the seq number
-+ * @seq: seq number wait for
-+ * @intr: if interruptible
-+ * @timeout: jiffies before time out
- *
-- * Wait for the requested sequence number(s) to be written by any ring
-- * (all asics). Sequnce number array is indexed by ring id.
-- * @intr selects whether to use interruptable (true) or non-interruptable
-- * (false) sleep when waiting for the sequence number. Helper function
-- * for amdgpu_fence_wait_*().
-- * Returns remaining time if the sequence number has passed, 0 when
-- * the wait timeout, or an error for all other cases.
-- * -EDEADLK is returned when a GPU lockup has been detected.
-+ * return value:
-+ * 0: time out but seq not signaled, and gpu not hang
-+ * X (X > 0): seq signaled and X means how many jiffies remains before time out
-+ * -EDEADL: GPU hang before time out
-+ * -ESYSRESTART: interrupted before seq signaled
-+ * -EINVAL: some paramter is not valid
- */
--static long amdgpu_fence_wait_seq_timeout(struct amdgpu_device *adev,
-- u64 *target_seq, bool intr,
-- long timeout)
-+static long amdgpu_fence_ring_wait_seq_timeout(struct amdgpu_ring *ring, uint64_t seq,
-+ bool intr, long timeout)
- {
-- uint64_t last_seq[AMDGPU_MAX_RINGS];
-- bool signaled;
-- int i;
-- long r;
--
-- if (timeout == 0) {
-- return amdgpu_fence_any_seq_signaled(adev, target_seq);
-- }
--
-- while (!amdgpu_fence_any_seq_signaled(adev, target_seq)) {
--
-- /* Save current sequence values, used to check for GPU lockups */
-- for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-- struct amdgpu_ring *ring = adev->rings[i];
-+ struct amdgpu_device *adev = ring->adev;
-+ long r = 0;
-+ bool signaled = false;
-
-- if (!ring || !target_seq[i])
-- continue;
-+ BUG_ON(!ring);
-+ if (seq > ring->fence_drv.sync_seq[ring->idx])
-+ return -EINVAL;
-
-- last_seq[i] = atomic64_read(&ring->fence_drv.last_seq);
-- trace_amdgpu_fence_wait_begin(adev->ddev, i, target_seq[i]);
-- }
-+ if (atomic64_read(&ring->fence_drv.last_seq) >= seq)
-+ return timeout;
-
-+ while (1) {
- if (intr) {
-- r = wait_event_interruptible_timeout(adev->fence_queue, (
-- (signaled = amdgpu_fence_any_seq_signaled(adev, target_seq))
-- || adev->needs_reset), AMDGPU_FENCE_JIFFIES_TIMEOUT);
-+ r = wait_event_interruptible_timeout(ring->fence_drv.fence_queue, (
-+ (signaled = amdgpu_fence_seq_signaled(ring, seq))
-+ || adev->needs_reset), AMDGPU_FENCE_JIFFIES_TIMEOUT);
-+
-+ if (r == -ERESTARTSYS) /* interrupted */
-+ return r;
- } else {
-- r = wait_event_timeout(adev->fence_queue, (
-- (signaled = amdgpu_fence_any_seq_signaled(adev, target_seq))
-- || adev->needs_reset), AMDGPU_FENCE_JIFFIES_TIMEOUT);
-+ r = wait_event_timeout(ring->fence_drv.fence_queue, (
-+ (signaled = amdgpu_fence_seq_signaled(ring, seq))
-+ || adev->needs_reset), AMDGPU_FENCE_JIFFIES_TIMEOUT);
- }
-
-- for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-- struct amdgpu_ring *ring = adev->rings[i];
--
-- if (!ring || !target_seq[i])
-- continue;
--
-- trace_amdgpu_fence_wait_end(adev->ddev, i, target_seq[i]);
-+ if (signaled) {
-+ /* seq signaled */
-+ if (timeout == MAX_SCHEDULE_TIMEOUT)
-+ return timeout;
-+ return (timeout - AMDGPU_FENCE_JIFFIES_TIMEOUT - r);
-+ }
-+ else if (adev->needs_reset) {
-+ return -EDEADLK;
- }
-
-- if (unlikely(r < 0))
-- return r;
--
-- if (unlikely(!signaled)) {
--
-- if (adev->needs_reset)
-- return -EDEADLK;
--
-- /* we were interrupted for some reason and fence
-- * isn't signaled yet, resume waiting */
-- if (r)
-- continue;
--
-- for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-- struct amdgpu_ring *ring = adev->rings[i];
--
-- if (!ring || !target_seq[i])
-- continue;
--
-- if (last_seq[i] != atomic64_read(&ring->fence_drv.last_seq))
-- break;
-- }
--
-- if (i != AMDGPU_MAX_RINGS)
-- continue;
--
-- for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-- if (!adev->rings[i] || !target_seq[i])
-- continue;
--
-- if (amdgpu_ring_is_lockup(adev->rings[i]))
-- break;
-- }
--
-- if (i < AMDGPU_MAX_RINGS) {
-- /* good news we believe it's a lockup */
-- dev_warn(adev->dev, "GPU lockup (waiting for "
-+ /* check if it's a lockup */
-+ if (amdgpu_ring_is_lockup(ring)) {
-+ uint64_t last_seq = atomic64_read(&ring->fence_drv.last_seq);
-+ /* ring lookup */
-+ dev_warn(adev->dev, "GPU lockup (waiting for "
- "0x%016llx last fence id 0x%016llx on"
- " ring %d)\n",
-- target_seq[i], last_seq[i], i);
--
-- /* remember that we need an reset */
-- adev->needs_reset = true;
-- wake_up_all(&adev->fence_queue);
-- return -EDEADLK;
-- }
-+ seq, last_seq, ring->idx);
-+ wake_up_all(&ring->fence_drv.fence_queue);
-+ return -EDEADLK;
-+ }
-
-- if (timeout < MAX_SCHEDULE_TIMEOUT) {
-- timeout -= AMDGPU_FENCE_JIFFIES_TIMEOUT;
-- if (timeout <= 0) {
-- return 0;
-- }
-- }
-+ if (timeout < MAX_SCHEDULE_TIMEOUT) {
-+ timeout -= AMDGPU_FENCE_JIFFIES_TIMEOUT;
-+ if (timeout < 1)
-+ return 0;
- }
- }
-- return timeout;
- }
-
-+
- /**
- * amdgpu_fence_wait - wait for a fence to signal
- *
-@@ -642,18 +570,15 @@ int amdgpu_fence_wait(struct amdgpu_fence *fence, bool intr)
- */
- int amdgpu_fence_wait_next(struct amdgpu_ring *ring)
- {
-- uint64_t seq[AMDGPU_MAX_RINGS] = {};
- long r;
-
-- seq[ring->idx] = atomic64_read(&ring->fence_drv.last_seq) + 1ULL;
-- if (seq[ring->idx] >= ring->fence_drv.sync_seq[ring->idx]) {
-- /* nothing to wait for, last_seq is
-- already the last emited fence */
-+ uint64_t seq = atomic64_read(&ring->fence_drv.last_seq) + 1ULL;
-+ if (seq >= ring->fence_drv.sync_seq[ring->idx])
- return -ENOENT;
-- }
-- r = amdgpu_fence_wait_seq_timeout(ring->adev, seq, false, MAX_SCHEDULE_TIMEOUT);
-+ r = amdgpu_fence_ring_wait_seq_timeout(ring, seq, false, MAX_SCHEDULE_TIMEOUT);
- if (r < 0)
- return r;
-+
- return 0;
- }
-
-@@ -669,21 +594,20 @@ int amdgpu_fence_wait_next(struct amdgpu_ring *ring)
- */
- int amdgpu_fence_wait_empty(struct amdgpu_ring *ring)
- {
-- struct amdgpu_device *adev = ring->adev;
-- uint64_t seq[AMDGPU_MAX_RINGS] = {};
- long r;
-
-- seq[ring->idx] = ring->fence_drv.sync_seq[ring->idx];
-- if (!seq[ring->idx])
-+ uint64_t seq = ring->fence_drv.sync_seq[ring->idx];
-+ if (!seq)
- return 0;
-
-- r = amdgpu_fence_wait_seq_timeout(adev, seq, false, MAX_SCHEDULE_TIMEOUT);
-+ r = amdgpu_fence_ring_wait_seq_timeout(ring, seq, false, MAX_SCHEDULE_TIMEOUT);
-+
- if (r < 0) {
- if (r == -EDEADLK)
- return -EDEADLK;
-
-- dev_err(adev->dev, "error waiting for ring[%d] to become idle (%ld)\n",
-- ring->idx, r);
-+ dev_err(ring->adev->dev, "error waiting for ring[%d] to become idle (%ld)\n",
-+ ring->idx, r);
- }
- return 0;
- }
-@@ -898,7 +822,6 @@ void amdgpu_fence_driver_init_ring(struct amdgpu_ring *ring)
- */
- int amdgpu_fence_driver_init(struct amdgpu_device *adev)
- {
-- init_waitqueue_head(&adev->fence_queue);
- if (amdgpu_debugfs_fence_init(adev))
- dev_err(adev->dev, "fence debugfs file creation failed\n");
-
-@@ -927,7 +850,7 @@ void amdgpu_fence_driver_fini(struct amdgpu_device *adev)
- /* no need to trigger GPU reset as we are unloading */
- amdgpu_fence_driver_force_completion(adev);
- }
-- wake_up_all(&adev->fence_queue);
-+ wake_up_all(&ring->fence_drv.fence_queue);
- amdgpu_irq_put(adev, ring->fence_drv.irq_src,
- ring->fence_drv.irq_type);
- if (ring->scheduler)
-diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ring.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ring.c
-index 1e68a56..7d442c5 100644
---- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ring.c
-+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ring.c
-@@ -342,6 +342,8 @@ int amdgpu_ring_init(struct amdgpu_device *adev, struct amdgpu_ring *ring,
- amdgpu_fence_driver_init_ring(ring);
- }
-
-+ init_waitqueue_head(&ring->fence_drv.fence_queue);
-+
- r = amdgpu_wb_get(adev, &ring->rptr_offs);
- if (r) {
- dev_err(adev->dev, "(%d) ring rptr_offs wb alloc failed\n", r);
---
-1.9.1
-