On the LSDMA path amdgpu_ualink_send_command() ignored the return of amdgpu_lsdma_copy_mem() and polled the remote completion for the full timeout even when the copy failed. With a peer down, every NPA-REVOKE send in amdgpu_ualink_exp_cleanup_worker() wasted ~2s, and the peer stayed ESTABLISHED so each subsequent handle cleanup timed out again, piling up past the 120s hung-task threshold.
Return immediately when an LSDMA copy fails, and mark the connection NOT_READY on a failed revoke send so other cleanups skip the unreachable peer via amdgpu_ualink_check_conn_ready(). Signed-off-by: Mukul Joshi <[email protected]> --- drivers/gpu/drm/amd/amdgpu/amdgpu_ualink.c | 29 +++++++++++++++++++--- 1 file changed, 26 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ualink.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ualink.c index f5e1e5217fa5..f5865c5fe93e 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ualink.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ualink.c @@ -2903,7 +2903,8 @@ static void amdgpu_ualink_exp_cleanup_worker(struct work_struct *work) } /* Send NPA-REVOKE to all importers which have imported this memory. - * On send failure clear the bit (no response will arrive). + * On send failure clear the bit (no response will arrive) and mark the + * connection NOT_READY so other cleanups skip this unreachable peer. */ for_each_set_bit(remote_acc_id, exp_xa_node->importers_bitmap, AMDGPU_UALINK_ACCEL_MAX) { @@ -2916,6 +2917,11 @@ static void amdgpu_ualink_exp_cleanup_worker(struct work_struct *work) "EXP-CLEANUP: NPA-REVOKE send failed to remote:%u\n", remote_acc_id); clear_bit(remote_acc_id, exp_xa_node->npa_release_bitmap); + + imp_entry = &exp_xa_node->importer_entries[remote_acc_id]; + amdgpu_ualink_handle_connection_reset(adev, remote_acc_id, + AMDGPU_UALINK_CONN_NOT_READY, + imp_entry->generation_count); } } @@ -5623,10 +5629,27 @@ static int amdgpu_ualink_send_command(struct amdgpu_device *adev, r = amdgpu_lsdma_copy_mem(adev, src, ring->rb_npa_gart + (ring->wptr % ring->rb_size) * 64, 64); - r = amdgpu_lsdma_copy_mem(adev, src + 64, ring->wptr_npa_gart, 8); + if (!r) + r = amdgpu_lsdma_copy_mem(adev, src + 64, + ring->wptr_npa_gart, 8); + if (!r) + r = amdgpu_lsdma_copy_mem(adev, src + 72, + doorbell_npa_gart, 4); - r = amdgpu_lsdma_copy_mem(adev, src + 72, doorbell_npa_gart, 4); amdgpu_job_free(job); + + /* Copy failed: command never reached the remote, so no + * writeback will arrive. Return now instead of polling the + * completion for the full remote timeout. + */ + if (r) { + dev_dbg(adev->dev, + "remote %u lsdma copy failed (r %d), skip completion wait\n", + remote_accel_id, r); + mutex_unlock(&peer->lock); + return r; + } + goto out_wait_complete; } -- 2.54.0
