I found out about that fix only after I had created this patch, but I still want to state that the fix is not full: it unwedges the device, but not the tasks already waiting. Those stay in an uninterruptible wait, holding the debug BO and the command, and cannot be killed. tdr_timeout_ms bounds that at 2 s by default; with tdr_timeout_ms=0 it is unbounded.

I am still researching whether any race conditions can happen in the current driver state.

Taimuraz

On 8/26/26 20:34, Lizhi Hou wrote:
On 8/26/26 08:07, Taimuraz Kaitmazov wrote:
aie2_cmd_wait() waits with dma_fence_wait_timeout(..., false,
MAX_SCHEDULE_TIMEOUT): uninterruptible and unbounded. Both callers reach
it from an ioctl holding xdna->dev_lock, and the only thing that can
signal the fence when firmware does not answer is
aie2_sched_job_timedout(), which takes that same lock. A debug BO command
that never completes therefore blocks the ioctl forever, leaves the task
unkillable, and stalls every other ioctl on the device behind dev_lock.

Wait interruptibly and propagate the result. This does not remove the
lock dependency, it makes it survivable.

This is fixed by https://lore.kernel.org/all/[email protected]/

could you sync to drm-misc-fixes or the latest upstream kernel?

Thanks,

Lizhi

Signed-off-by: Taimuraz Kaitmazov <[email protected]>
---
  drivers/accel/amdxdna/aie2_ctx.c | 19 ++++++++++++++-----
  1 file changed, 14 insertions(+), 5 deletions(-)

diff --git a/drivers/accel/amdxdna/aie2_ctx.c b/drivers/accel/amdxdna/aie2_ctx.c
index 54486960cbf5..1f910ee4941c 100644
--- a/drivers/accel/amdxdna/aie2_ctx.c
+++ b/drivers/accel/amdxdna/aie2_ctx.c
@@ -897,17 +897,20 @@ static int aie2_hwctx_cu_config(struct amdxdna_hwctx *hwctx, void *buf, u32 size
      return ret;
  }
  -static void aie2_cmd_wait(struct amdxdna_hwctx *hwctx, u64 seq)
+static int aie2_cmd_wait(struct amdxdna_hwctx *hwctx, u64 seq)
  {
      struct dma_fence *out_fence = aie2_cmd_get_out_fence(hwctx, seq);
+    long ret;
        if (!out_fence) {
          XDNA_ERR(hwctx->client->xdna, "Failed to get fence");
-        return;
+        return -EINVAL;
      }
  -    dma_fence_wait_timeout(out_fence, false, MAX_SCHEDULE_TIMEOUT);
+    ret = dma_fence_wait_timeout(out_fence, true, MAX_SCHEDULE_TIMEOUT);
      dma_fence_put(out_fence);
+
+    return ret < 0 ? ret : 0;
  }
    static int aie2_hwctx_cfg_debug_bo(struct amdxdna_hwctx *hwctx, u32 bo_hdl, @@ -954,7 +957,10 @@ static int aie2_hwctx_cfg_debug_bo(struct amdxdna_hwctx *hwctx, u32 bo_hdl,
          goto put_cmd;
      }
  -    aie2_cmd_wait(hwctx, seq);
+    ret = aie2_cmd_wait(hwctx, seq);
+    if (ret)
+        goto put_cmd;
+
      if (cmd->result) {
          XDNA_ERR(xdna, "Response failure 0x%x", cmd->result);
          ret = -EINVAL;
@@ -1014,7 +1020,10 @@ int aie2_hwctx_sync_debug_bo(struct amdxdna_hwctx *hwctx, u32 debug_bo_hdl)
          goto put_cmd;
      }
  -    aie2_cmd_wait(hwctx, seq);
+    ret = aie2_cmd_wait(hwctx, seq);
+    if (ret)
+        goto put_cmd;
+
      if (cmd->result) {
          XDNA_ERR(xdna, "Response failure 0x%x", cmd->result);
          ret = -EINVAL;

Reply via email to