diff --git a/drivers/video/rockchip/mpp/mpp_common.c b/drivers/video/rockchip/mpp/mpp_common.c index 5f186d688e8f..4fcced94c450 100644 --- a/drivers/video/rockchip/mpp/mpp_common.c +++ b/drivers/video/rockchip/mpp/mpp_common.c @@ -138,11 +138,12 @@ mpp_taskqueue_get_pending_task(struct mpp_taskqueue *queue) static bool mpp_taskqueue_is_running(struct mpp_taskqueue *queue) { + unsigned long flags; bool flag; - mutex_lock(&queue->running_lock); + spin_lock_irqsave(&queue->running_lock, flags); flag = !list_empty(&queue->running_list); - mutex_unlock(&queue->running_lock); + spin_unlock_irqrestore(&queue->running_lock, flags); return flag; } @@ -151,10 +152,13 @@ static int mpp_taskqueue_pending_to_run(struct mpp_taskqueue *queue, struct mpp_task *task) { + unsigned long flags; + mutex_lock(&queue->pending_lock); - mutex_lock(&queue->running_lock); + spin_lock_irqsave(&queue->running_lock, flags); list_move_tail(&task->queue_link, &queue->running_list); - mutex_unlock(&queue->running_lock); + spin_unlock_irqrestore(&queue->running_lock, flags); + mutex_unlock(&queue->pending_lock); return 0; @@ -163,13 +167,14 @@ mpp_taskqueue_pending_to_run(struct mpp_taskqueue *queue, static struct mpp_task * mpp_taskqueue_get_running_task(struct mpp_taskqueue *queue) { + unsigned long flags; struct mpp_task *task = NULL; - mutex_lock(&queue->running_lock); + spin_lock_irqsave(&queue->running_lock, flags); task = list_first_entry_or_null(&queue->running_list, struct mpp_task, queue_link); - mutex_unlock(&queue->running_lock); + spin_unlock_irqrestore(&queue->running_lock, flags); return task; } @@ -178,12 +183,14 @@ static int mpp_taskqueue_pop_running(struct mpp_taskqueue *queue, struct mpp_task *task) { + unsigned long flags; + if (!task->session || !task->session->mpp) return -EINVAL; - mutex_lock(&queue->running_lock); + spin_lock_irqsave(&queue->running_lock, flags); list_del_init(&task->queue_link); - mutex_unlock(&queue->running_lock); + spin_unlock_irqrestore(&queue->running_lock, flags); kref_put(&task->ref, mpp_free_task); return 0; @@ -932,7 +939,7 @@ struct mpp_taskqueue *mpp_taskqueue_init(struct device *dev) mutex_init(&queue->session_lock); mutex_init(&queue->pending_lock); - mutex_init(&queue->running_lock); + spin_lock_init(&queue->running_lock); mutex_init(&queue->mmu_lock); mutex_init(&queue->dev_lock); INIT_LIST_HEAD(&queue->session_attach); diff --git a/drivers/video/rockchip/mpp/mpp_common.h b/drivers/video/rockchip/mpp/mpp_common.h index c4cc8aac9d5b..b7d02b0a417d 100644 --- a/drivers/video/rockchip/mpp/mpp_common.h +++ b/drivers/video/rockchip/mpp/mpp_common.h @@ -430,7 +430,7 @@ struct mpp_taskqueue { struct mutex pending_lock; struct list_head pending_list; /* lock for running list */ - struct mutex running_lock; + spinlock_t running_lock; struct list_head running_list; /* point to MPP Service */ diff --git a/drivers/video/rockchip/mpp/mpp_rkvdec.c b/drivers/video/rockchip/mpp/mpp_rkvdec.c index dd261497b5b4..8f7e069333cd 100644 --- a/drivers/video/rockchip/mpp/mpp_rkvdec.c +++ b/drivers/video/rockchip/mpp/mpp_rkvdec.c @@ -853,12 +853,13 @@ fail: static void *rkvdec_prepare_with_reset(struct mpp_dev *mpp, struct mpp_task *mpp_task) { + unsigned long flags; struct mpp_task *out_task = NULL; struct rkvdec_dev *dec = to_rkvdec_dev(mpp); - mutex_lock(&mpp->queue->running_lock); + spin_lock_irqsave(&mpp->queue->running_lock, flags); out_task = list_empty(&mpp->queue->running_list) ? mpp_task : NULL; - mutex_unlock(&mpp->queue->running_lock); + spin_unlock_irqrestore(&mpp->queue->running_lock, flags); if (out_task && !dec->had_reset) { struct rkvdec_task *task = to_rkvdec_task(out_task);