Skip to content

Commit db7f92a

Browse files
matt-auldlucasdemarchi
authored andcommitted
drm/xe/ct: prevent UAF in send_recv()
Ensure we serialize with completion side to prevent UAF with fence going out of scope on the stack, since we have no clue if it will fire after the timeout before we can erase from the xa. Also we have some dependent loads and stores for which we need the correct ordering, and we lack the needed barriers. Fix this by grabbing the ct->lock after the wait, which is also held by the completion side. v2 (Badal): - Also print done after acquiring the lock and seeing timeout. Fixes: dd08ebf ("drm/xe: Introduce a new DRM driver for Intel GPUs") Signed-off-by: Matthew Auld <[email protected]> Cc: Matthew Brost <[email protected]> Cc: Badal Nilawar <[email protected]> Cc: <[email protected]> # v6.8+ Reviewed-by: Badal Nilawar <[email protected]> Link: https://patchwork.freedesktop.org/patch/msgid/[email protected] (cherry picked from commit 52789ce) Signed-off-by: Lucas De Marchi <[email protected]>
1 parent 8cf0b93 commit db7f92a

File tree

1 file changed

+18
-3
lines changed

1 file changed

+18
-3
lines changed

drivers/gpu/drm/xe/xe_guc_ct.c

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -903,16 +903,26 @@ static int guc_ct_send_recv(struct xe_guc_ct *ct, const u32 *action, u32 len,
903903
}
904904

905905
ret = wait_event_timeout(ct->g2h_fence_wq, g2h_fence.done, HZ);
906+
907+
/*
908+
* Ensure we serialize with completion side to prevent UAF with fence going out of scope on
909+
* the stack, since we have no clue if it will fire after the timeout before we can erase
910+
* from the xa. Also we have some dependent loads and stores below for which we need the
911+
* correct ordering, and we lack the needed barriers.
912+
*/
913+
mutex_lock(&ct->lock);
906914
if (!ret) {
907-
xe_gt_err(gt, "Timed out wait for G2H, fence %u, action %04x",
908-
g2h_fence.seqno, action[0]);
915+
xe_gt_err(gt, "Timed out wait for G2H, fence %u, action %04x, done %s",
916+
g2h_fence.seqno, action[0], str_yes_no(g2h_fence.done));
909917
xa_erase_irq(&ct->fence_lookup, g2h_fence.seqno);
918+
mutex_unlock(&ct->lock);
910919
return -ETIME;
911920
}
912921

913922
if (g2h_fence.retry) {
914923
xe_gt_dbg(gt, "H2G action %#x retrying: reason %#x\n",
915924
action[0], g2h_fence.reason);
925+
mutex_unlock(&ct->lock);
916926
goto retry;
917927
}
918928
if (g2h_fence.fail) {
@@ -921,7 +931,12 @@ static int guc_ct_send_recv(struct xe_guc_ct *ct, const u32 *action, u32 len,
921931
ret = -EIO;
922932
}
923933

924-
return ret > 0 ? response_buffer ? g2h_fence.response_len : g2h_fence.response_data : ret;
934+
if (ret > 0)
935+
ret = response_buffer ? g2h_fence.response_len : g2h_fence.response_data;
936+
937+
mutex_unlock(&ct->lock);
938+
939+
return ret;
925940
}
926941

927942
/**

0 commit comments

Comments
 (0)