On Mon, Aug 31, 2026 at 9:01 AM Mario Limonciello
<[email protected]> wrote:
>
> Reading /sys/kernel/debug/kfd/mqds while a process holds an active KFD
> queue triggers a NULL pointer dereference because the for loop that
> calls mqd_mgr->debugfs_show_mqd() is incorrectly placed outside the
> if (pqn->q) block that initializes mqd_mgr.
>
> The queue list can contain entries where pqn->q is NULL (kernel queues
> where only pqn->kq is valid). In the original code:
>
>   if (pqn->q) {
>       ...
>       mqd_mgr = q->device->dqm->mqd_mgrs[mqd_type];
>       size = mqd_mgr->mqd_stride(...);
>   }
>
>   for (xcc = 0; xcc < num_xccs; xcc++) {  // WRONG: outside if block
>       mqd = q->mqd + size * xcc;
>       r = mqd_mgr->debugfs_show_mqd(m, mqd);
>   }
>
> When iterating over a queue node where pqn->q is NULL:
> 1. The if (pqn->q) block is skipped
> 2. mqd_mgr remains uninitialized (NULL from declaration)
> 3. The for loop executes anyway
> 4. mqd_mgr->debugfs_show_mqd(m, mqd) dereferences NULL
>
> The crash manifests as:
>
>   BUG: kernel NULL pointer dereference, address: 0000000000000000
>   #PF: supervisor instruction fetch in kernel mode
>   RIP: 0010:0x0
>   Call Trace:
>    pqm_debugfs_mqds+0x10c/0x1d0 [amdgpu]
>    kfd_debugfs_mqds_by_process+0x9b/0x110 [amdgpu]
>    seq_read_iter+0x132/0x4b0
>    ...
>
> Fix by moving the for loop inside the if (pqn->q) block, so mqd_mgr
> and related variables are only used when properly initialized.
>
> Cc: [email protected]
> Closes: https://gitlab.freedesktop.org/drm/amd/-/work_items/5689
> Signed-off-by: Mario Limonciello <[email protected]>

Reviewed-by: Alex Deucher <[email protected]>

> ---
>  .../gpu/drm/amd/amdkfd/kfd_process_queue_manager.c   | 12 ++++++------
>  1 file changed, 6 insertions(+), 6 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c 
> b/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
> index 9e607098c3a09..fb2d8ad9c2c5e 100644
> --- a/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
> +++ b/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
> @@ -1170,13 +1170,13 @@ int pqm_debugfs_mqds(struct seq_file *m, void *data)
>                         mqd_mgr = q->device->dqm->mqd_mgrs[mqd_type];
>                         size = mqd_mgr->mqd_stride(mqd_mgr,
>                                                         &q->properties);
> -               }
>
> -               for (xcc = 0; xcc < num_xccs; xcc++) {
> -                       mqd = q->mqd + size * xcc;
> -                       r = mqd_mgr->debugfs_show_mqd(m, mqd);
> -                       if (r != 0)
> -                               break;
> +                       for (xcc = 0; xcc < num_xccs; xcc++) {
> +                               mqd = q->mqd + size * xcc;
> +                               r = mqd_mgr->debugfs_show_mqd(m, mqd);
> +                               if (r != 0)
> +                                       break;
> +                       }
>                 }
>         }
>
> --
> 2.43.0
>

Reply via email to