diff options
author | Jonathan Gray <jsg@cvs.openbsd.org> | 2021-07-19 10:33:04 +0000 |
---|---|---|
committer | Jonathan Gray <jsg@cvs.openbsd.org> | 2021-07-19 10:33:04 +0000 |
commit | 9353a94b6e2ca3817bcff2413ba9116d48d4859a (patch) | |
tree | 81b2062eb1176c0813d965ac235f9f2a10889cbd /sys | |
parent | a2c566dbc7e7a51b3f285958b869758f3f51850c (diff) |
drm/amdkfd: Walk through list with dqm lock hold
From xinhui pan
4cd713e48c272a80af935424afaa607ea125aed4 in linux 5.10.y/5.10.51
56f221b6389e7ab99c30bbf01c71998ae92fc584 in mainline linux
Diffstat (limited to 'sys')
-rw-r--r-- | sys/dev/pci/drm/amd/amdkfd/kfd_device_queue_manager.c | 22 |
1 files changed, 12 insertions, 10 deletions
diff --git a/sys/dev/pci/drm/amd/amdkfd/kfd_device_queue_manager.c b/sys/dev/pci/drm/amd/amdkfd/kfd_device_queue_manager.c index ffb3d37881a..352a32dc609 100644 --- a/sys/dev/pci/drm/amd/amdkfd/kfd_device_queue_manager.c +++ b/sys/dev/pci/drm/amd/amdkfd/kfd_device_queue_manager.c @@ -1712,7 +1712,7 @@ static int process_termination_cpsch(struct device_queue_manager *dqm, struct qcm_process_device *qpd) { int retval; - struct queue *q, *next; + struct queue *q; struct kernel_queue *kq, *kq_next; struct mqd_manager *mqd_mgr; struct device_process_node *cur, *next_dpn; @@ -1769,24 +1769,26 @@ static int process_termination_cpsch(struct device_queue_manager *dqm, qpd->reset_wavefronts = false; } - dqm_unlock(dqm); - - /* Outside the DQM lock because under the DQM lock we can't do - * reclaim or take other locks that others hold while reclaiming. - */ - if (found) - kfd_dec_compute_active(dqm->dev); - /* Lastly, free mqd resources. * Do free_mqd() after dqm_unlock to avoid circular locking. */ - list_for_each_entry_safe(q, next, &qpd->queues_list, list) { + while (!list_empty(&qpd->queues_list)) { + q = list_first_entry(&qpd->queues_list, struct queue, list); mqd_mgr = dqm->mqd_mgrs[get_mqd_type_from_queue_type( q->properties.type)]; list_del(&q->list); qpd->queue_count--; + dqm_unlock(dqm); mqd_mgr->free_mqd(mqd_mgr, q->mqd, q->mqd_mem_obj); + dqm_lock(dqm); } + dqm_unlock(dqm); + + /* Outside the DQM lock because under the DQM lock we can't do + * reclaim or take other locks that others hold while reclaiming. + */ + if (found) + kfd_dec_compute_active(dqm->dev); return retval; } |