[PATCH v3 4/4] drm/xe/multi_queue: replay dynamic CGP updates lost during VF migration
Niranjana Vishwanathapura <[email protected]> Mon, 3 Aug 2026 16:05:33 -0700
| Newsgroups | org.freedesktop.lists.intel-xe |
|---|---|
| Message-ID | <[email protected]> |
When guc_exec_queue_revert_pending_state_change() sets needs_cgp_sync for a queue, replay that update during unpause by injecting a CGP_SYNC_MSG static message at the head of the scheduler queue. The message handler __guc_exec_queue_process_msg_cgp_sync() calls guc_exec_queue_send_cgp_sync() which re-reads the current priority from q->multi_queue.priority and re-issues the CGP write + CGP_SYNC H2G, so the queue's CGP entry is restored to the correct value after migration. Assisted-by: Github-Copilot:Claude-opus-4.8 Signed-off-by: Niranjana Vishwanathapura <[email protected]> Reviewed-by: Matthew Brost <[email protected]> --- drivers/gpu/drm/xe/xe_guc_exec_queue_types.h | 2 +- drivers/gpu/drm/xe/xe_guc_submit.c | 28 ++++++++++++++++++++ 2 files changed, 29 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/xe/xe_guc_exec_queue_types.h b/drivers/gpu/drm/xe/xe_guc_exec_queue_types.h index 573b920edb41..d27826b36649 100644 --- a/drivers/gpu/drm/xe/xe_guc_exec_queue_types.h +++ b/drivers/gpu/drm/xe/xe_guc_exec_queue_types.h @@ -36,7 +36,7 @@ struct xe_guc_exec_queue { * a message needs to sent through the GPU scheduler but memory * allocations are not allowed. */ -#define MAX_STATIC_MSG_TYPE 3 +#define MAX_STATIC_MSG_TYPE 4 struct xe_sched_msg static_msgs[MAX_STATIC_MSG_TYPE]; /** @destroy_async: do final destroy async from this worker */ struct work_struct destroy_async; diff --git a/drivers/gpu/drm/xe/xe_guc_submit.c b/drivers/gpu/drm/xe/xe_guc_submit.c index c018bc0d8d6f..9036f89dff7d 100644 --- a/drivers/gpu/drm/xe/xe_guc_submit.c +++ b/drivers/gpu/drm/xe/xe_guc_submit.c @@ -1960,11 +1960,25 @@ static void __guc_exec_queue_process_msg_set_multi_queue_priority(struct xe_sche kfree(msg); } +static void __guc_exec_queue_process_msg_cgp_sync(struct xe_sched_msg *msg) +{ + struct xe_exec_queue *q = msg->private_data; + + /* + * Replay a dynamic CGP update lost across VF migration by re-issuing the + * CGP update + CGP_SYNC (re-applies the current priority from + * q->multi_queue.priority). + */ + if (guc_exec_queue_allowed_to_change_state(q)) + guc_exec_queue_send_cgp_sync(q, 0); +} + #define CLEANUP 1 /* Non-zero values to catch uninitialized msg */ #define SET_SCHED_PROPS 2 #define SUSPEND 3 #define RESUME 4 #define SET_MULTI_QUEUE_PRIORITY 5 +#define CGP_SYNC_MSG 6 #define OPCODE_MASK 0xf #define MSG_LOCKED BIT(8) #define MSG_HEAD BIT(9) @@ -1991,6 +2005,9 @@ static void guc_exec_queue_process_msg(struct xe_sched_msg *msg) case SET_MULTI_QUEUE_PRIORITY: __guc_exec_queue_process_msg_set_multi_queue_priority(msg); break; + case CGP_SYNC_MSG: + __guc_exec_queue_process_msg_cgp_sync(msg); + break; default: XE_WARN_ON("Unknown message type"); } @@ -2160,6 +2177,7 @@ static bool guc_exec_queue_try_add_msg(struct xe_exec_queue *q, #define STATIC_MSG_CLEANUP 0 #define STATIC_MSG_SUSPEND 1 #define STATIC_MSG_RESUME 2 +#define STATIC_MSG_CGP_SYNC 3 static void guc_exec_queue_destroy(struct xe_exec_queue *q) { struct xe_sched_msg *msg = q->guc->static_msgs + STATIC_MSG_CLEANUP; @@ -3024,6 +3042,16 @@ static void guc_exec_queue_replay_pending_state_change(struct xe_exec_queue *q) struct xe_gpu_scheduler *sched = &q->guc->sched; struct xe_sched_msg *msg; + if (q->guc->multi_queue.needs_cgp_sync) { + msg = q->guc->static_msgs + STATIC_MSG_CGP_SYNC; + + xe_sched_msg_lock(sched); + guc_exec_queue_try_add_msg_head(q, msg, CGP_SYNC_MSG); + xe_sched_msg_unlock(sched); + + q->guc->multi_queue.needs_cgp_sync = false; + } + if (q->guc->needs_cleanup) { msg = q->guc->static_msgs + STATIC_MSG_CLEANUP; -- 2.43.0