mirror of
https://github.com/revyos/thead-kernel.git
synced 2026-09-16 12:22:33 +02:00
drm/etnaviv: split fence lock
The fence lock currently protects two distinct things. It protects the fence IDR from concurrent inserts and removes and also keeps drm_sched_job_arm and drm_sched_entity_push_job in one atomic section to guarantee the fence seqno monotonicity. Split the lock into those two functions. Signed-off-by: Lucas Stach <l.stach@pengutronix.de> Reviewed-by: Philipp Zabel <p.zabel@pengutronix.de>
This commit is contained in:
committed by
Han Gao/Revy/Rabenda
parent
c32beb855f
commit
880ab177a1
@@ -407,9 +407,9 @@ static void submit_cleanup(struct kref *kref)
|
||||
dma_fence_put(submit->in_fence);
|
||||
if (submit->out_fence) {
|
||||
/* first remove from IDR, so fence can not be found anymore */
|
||||
mutex_lock(&submit->gpu->fence_lock);
|
||||
mutex_lock(&submit->gpu->idr_lock);
|
||||
idr_remove(&submit->gpu->fence_idr, submit->out_fence_id);
|
||||
mutex_unlock(&submit->gpu->fence_lock);
|
||||
mutex_unlock(&submit->gpu->idr_lock);
|
||||
dma_fence_put(submit->out_fence);
|
||||
}
|
||||
|
||||
|
||||
@@ -1821,7 +1821,8 @@ static int etnaviv_gpu_platform_probe(struct platform_device *pdev)
|
||||
|
||||
gpu->dev = &pdev->dev;
|
||||
mutex_init(&gpu->lock);
|
||||
mutex_init(&gpu->fence_lock);
|
||||
mutex_init(&gpu->sched_lock);
|
||||
mutex_init(&gpu->idr_lock);
|
||||
|
||||
/* Map registers: */
|
||||
gpu->mmio = devm_platform_ioremap_resource(pdev, 0);
|
||||
|
||||
@@ -99,6 +99,7 @@ struct etnaviv_gpu {
|
||||
struct etnaviv_chip_identity identity;
|
||||
enum etnaviv_sec_mode sec_mode;
|
||||
struct workqueue_struct *wq;
|
||||
struct mutex sched_lock;
|
||||
struct drm_gpu_scheduler sched;
|
||||
bool initialized;
|
||||
bool fe_running;
|
||||
@@ -116,7 +117,7 @@ struct etnaviv_gpu {
|
||||
u32 idle_mask;
|
||||
|
||||
/* Fencing support */
|
||||
struct mutex fence_lock;
|
||||
struct mutex idr_lock;
|
||||
struct idr fence_idr;
|
||||
u32 next_fence;
|
||||
u32 completed_fence;
|
||||
|
||||
@@ -146,14 +146,16 @@ static const struct drm_sched_backend_ops etnaviv_sched_ops = {
|
||||
int etnaviv_sched_push_job(struct drm_sched_entity *sched_entity,
|
||||
struct etnaviv_gem_submit *submit)
|
||||
{
|
||||
struct etnaviv_gpu *gpu = submit->gpu;
|
||||
int ret = 0;
|
||||
|
||||
/*
|
||||
* Hold the fence lock across the whole operation to avoid jobs being
|
||||
* Hold the sched lock across the whole operation to avoid jobs being
|
||||
* pushed out of order with regard to their sched fence seqnos as
|
||||
* allocated in drm_sched_job_init.
|
||||
*/
|
||||
mutex_lock(&submit->gpu->fence_lock);
|
||||
mutex_lock(&gpu->sched_lock);
|
||||
|
||||
ret = drm_sched_job_init(&submit->sched_job, sched_entity,
|
||||
submit->ctx);
|
||||
@@ -161,9 +163,11 @@ int etnaviv_sched_push_job(struct drm_sched_entity *sched_entity,
|
||||
goto out_unlock;
|
||||
|
||||
submit->out_fence = dma_fence_get(&submit->sched_job.s_fence->finished);
|
||||
submit->out_fence_id = idr_alloc_cyclic(&submit->gpu->fence_idr,
|
||||
mutex_lock(&gpu->idr_lock);
|
||||
submit->out_fence_id = idr_alloc_cyclic(&gpu->fence_idr,
|
||||
submit->out_fence, 0,
|
||||
INT_MAX, GFP_KERNEL);
|
||||
mutex_unlock(&gpu->idr_lock);
|
||||
if (submit->out_fence_id < 0) {
|
||||
drm_sched_job_cleanup(&submit->sched_job);
|
||||
ret = -ENOMEM;
|
||||
@@ -176,7 +180,7 @@ int etnaviv_sched_push_job(struct drm_sched_entity *sched_entity,
|
||||
drm_sched_entity_push_job(&submit->sched_job, sched_entity);
|
||||
|
||||
out_unlock:
|
||||
mutex_unlock(&submit->gpu->fence_lock);
|
||||
mutex_unlock(&gpu->sched_lock);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user