From e178b99b224844d7ea7aac2be292a333439ff254 Mon Sep 17 00:00:00 2001 From: Yong Zhao Date: Tue, 9 Aug 2016 13:00:49 -0400 Subject: [PATCH 1485/4131] drm/amdkfd: Reorganize functions involving process exit Change-Id: Id077e26a6cf9f29f62fd08f3b2f9c1ca320bc2ee Signed-off-by: Yong Zhao --- drivers/gpu/drm/amd/amdkfd/kfd_process.c | 64 ++++++++++++++++++++------------ 1 file changed, 40 insertions(+), 24 deletions(-) diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_process.c b/drivers/gpu/drm/amd/amdkfd/kfd_process.c index 098787a..65099bb 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_process.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_process.c @@ -412,40 +412,21 @@ int restore(struct kfd_dev *kfd) return 0; } -/* No process locking is needed in this function, because the process - * is not findable any more. We must assume that no other thread is - * using it any more, otherwise we couldn't safely free the process - * stucture in the end. */ -static void kfd_process_ref_release(struct kref *ref) +static void kfd_process_free_outstanding_kfd_bos(struct kfd_process *p) { - struct kfd_process *p = container_of(ref, struct kfd_process, ref); - struct kfd_process_device *pdd, *temp, *peer_pdd; + struct kfd_process_device *pdd, *peer_pdd; struct kfd_bo *buf_obj; int id; - pr_debug("Releasing process (pasid %d)\n", - p->pasid); - list_for_each_entry(pdd, &p->per_device_data, per_device_list) { - pr_debug("Releasing pdd (topology id %d) for process (pasid %d)\n", - pdd->dev->id, p->pasid); - - if (pdd->dev->device_info->is_need_iommu_device) { - if (pdd->bound == PDD_BOUND) { - amd_iommu_unbind_pasid(pdd->dev->pdev, - p->pasid); - pdd->bound = PDD_UNBOUND; - } - } - /* * Remove all handles from idr and release appropriate * local memory object */ idr_for_each_entry(&pdd->alloc_idr, buf_obj, id) { - list_for_each_entry(peer_pdd, - &p->per_device_data, per_device_list) { - pdd->dev->kfd2kgd->unmap_memory_to_gpu( + list_for_each_entry(peer_pdd, &p->per_device_data, + per_device_list) { + peer_pdd->dev->kfd2kgd->unmap_memory_to_gpu( peer_pdd->dev->kgd, buf_obj->mem, peer_pdd->vm); } @@ -456,6 +437,11 @@ static void kfd_process_ref_release(struct kref *ref) kfd_process_device_remove_obj_handle(pdd, id); } } +} + +static void kfd_process_destroy_pdds(struct kfd_process *p) +{ + struct kfd_process_device *pdd, *temp; list_for_each_entry_safe(pdd, temp, &p->per_device_data, per_device_list) { @@ -467,6 +453,36 @@ static void kfd_process_ref_release(struct kref *ref) list_del(&pdd->per_device_list); kfree(pdd); } +} + +/* No process locking is needed in this function, because the process + * is not findable any more. We must assume that no other thread is + * using it any more, otherwise we couldn't safely free the process + * stucture in the end. */ +static void kfd_process_ref_release(struct kref *ref) +{ + struct kfd_process *p = container_of(ref, struct kfd_process, ref); + struct kfd_process_device *pdd; + + pr_debug("Releasing process (pasid %d)\n", + p->pasid); + + list_for_each_entry(pdd, &p->per_device_data, per_device_list) { + pr_debug("Releasing pdd (topology id %d) for process (pasid %d)\n", + pdd->dev->id, p->pasid); + + if (pdd->dev->device_info->is_need_iommu_device) { + if (pdd->bound == PDD_BOUND) { + amd_iommu_unbind_pasid(pdd->dev->pdev, + p->pasid); + pdd->bound = PDD_UNBOUND; + } + } + } + + kfd_process_free_outstanding_kfd_bos(p); + + kfd_process_destroy_pdds(p); kfd_event_free_process(p); -- 2.7.4