msm: sde: Reduce SDE rotator done signaling time

When rotator job finished, driver needs to send out done signaling to
notify fbdev driver to perform a commit. However, there are occasions
that the SMMU disabling take quite long time and delaying the fbdev
commit time. To reduce this unpredict latency, move the SMMU disabling
much later in the rotator done handling, and also remove unnecessary
SMMU disabling call during commit phase.

CRs-Fixed: 1100633
Change-Id: I76ad017661aa6f760a2adc3579f59a7b66ab8e40
Signed-off-by: Benjamin Chan <bkchan@codeaurora.org>
This commit is contained in:
Benjamin Chan 2016-12-22 18:42:34 -05:00
parent 8e761d5f69
commit e43aa01402
2 changed files with 17 additions and 10 deletions

View file

@ -1,4 +1,4 @@
/* Copyright (c) 2015-2016, The Linux Foundation. All rights reserved. /* Copyright (c) 2015-2017, The Linux Foundation. All rights reserved.
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and * it under the terms of the GNU General Public License version 2 and
@ -1390,6 +1390,14 @@ static void sde_rotator_commit_handler(struct work_struct *work)
entry->item.dst_rect.x, entry->item.dst_rect.y, entry->item.dst_rect.x, entry->item.dst_rect.y,
entry->item.dst_rect.w, entry->item.dst_rect.h); entry->item.dst_rect.w, entry->item.dst_rect.h);
ATRACE_INT("sde_smmu_ctrl", 0);
ret = sde_smmu_ctrl(1);
if (IS_ERR_VALUE(ret)) {
SDEROT_ERR("IOMMU attach failed\n");
goto smmu_error;
}
ATRACE_INT("sde_smmu_ctrl", 1);
ret = sde_rotator_map_and_check_data(entry); ret = sde_rotator_map_and_check_data(entry);
if (ret) { if (ret) {
SDEROT_ERR("fail to prepare input/output data %d\n", ret); SDEROT_ERR("fail to prepare input/output data %d\n", ret);
@ -1415,6 +1423,8 @@ static void sde_rotator_commit_handler(struct work_struct *work)
sde_rot_mgr_unlock(mgr); sde_rot_mgr_unlock(mgr);
return; return;
error: error:
sde_smmu_ctrl(0);
smmu_error:
sde_rotator_put_hw_resource(entry->commitq, entry, hw); sde_rotator_put_hw_resource(entry->commitq, entry, hw);
get_hw_res_err: get_hw_res_err:
sde_rotator_signal_output(entry); sde_rotator_signal_output(entry);
@ -1491,6 +1501,7 @@ static void sde_rotator_done_handler(struct work_struct *work)
sde_rot_mgr_lock(mgr); sde_rot_mgr_lock(mgr);
sde_rotator_put_hw_resource(entry->commitq, entry, entry->commitq->hw); sde_rotator_put_hw_resource(entry->commitq, entry, entry->commitq->hw);
sde_rotator_signal_output(entry); sde_rotator_signal_output(entry);
ATRACE_INT("sde_rot_done", 1);
sde_rotator_release_entry(mgr, entry); sde_rotator_release_entry(mgr, entry);
atomic_dec(&request->pending_count); atomic_dec(&request->pending_count);
if (request->retireq && request->retire_work) if (request->retireq && request->retire_work)
@ -1498,6 +1509,10 @@ static void sde_rotator_done_handler(struct work_struct *work)
if (entry->item.ts) if (entry->item.ts)
entry->item.ts[SDE_ROTATOR_TS_RETIRE] = ktime_get(); entry->item.ts[SDE_ROTATOR_TS_RETIRE] = ktime_get();
sde_rot_mgr_unlock(mgr); sde_rot_mgr_unlock(mgr);
ATRACE_INT("sde_smmu_ctrl", 3);
sde_smmu_ctrl(0);
ATRACE_INT("sde_smmu_ctrl", 4);
} }
static bool sde_rotator_verify_format(struct sde_rot_mgr *mgr, static bool sde_rotator_verify_format(struct sde_rot_mgr *mgr,

View file

@ -1089,6 +1089,7 @@ static u32 sde_hw_rotator_wait_done_regdma(
!sde_hw_rotator_pending_swts(rot, ctx, &swts), !sde_hw_rotator_pending_swts(rot, ctx, &swts),
KOFF_TIMEOUT); KOFF_TIMEOUT);
ATRACE_INT("sde_rot_done", 0);
spin_lock_irqsave(&rot->rotisr_lock, flags); spin_lock_irqsave(&rot->rotisr_lock, flags);
last_isr = ctx->last_regdma_isr_status; last_isr = ctx->last_regdma_isr_status;
@ -1769,7 +1770,6 @@ static int sde_hw_rotator_kickoff(struct sde_rot_hw_resource *hw,
struct sde_hw_rotator *rot; struct sde_hw_rotator *rot;
struct sde_hw_rotator_resource_info *resinfo; struct sde_hw_rotator_resource_info *resinfo;
struct sde_hw_rotator_context *ctx; struct sde_hw_rotator_context *ctx;
int ret = 0;
if (!hw || !entry) { if (!hw || !entry) {
SDEROT_ERR("null hw resource/entry\n"); SDEROT_ERR("null hw resource/entry\n");
@ -1787,12 +1787,6 @@ static int sde_hw_rotator_kickoff(struct sde_rot_hw_resource *hw,
return -EINVAL; return -EINVAL;
} }
ret = sde_smmu_ctrl(1);
if (IS_ERR_VALUE(ret)) {
SDEROT_ERR("IOMMU attach failed\n");
return ret;
}
rot->ops.start_rotator(ctx, ctx->q_id); rot->ops.start_rotator(ctx, ctx->q_id);
return 0; return 0;
@ -1832,8 +1826,6 @@ static int sde_hw_rotator_wait4done(struct sde_rot_hw_resource *hw,
ret = rot->ops.wait_rotator_done(ctx, ctx->q_id, 0); ret = rot->ops.wait_rotator_done(ctx, ctx->q_id, 0);
sde_smmu_ctrl(0);
if (rot->dbgmem) { if (rot->dbgmem) {
sde_hw_rotator_unmap_vaddr(&ctx->src_dbgbuf); sde_hw_rotator_unmap_vaddr(&ctx->src_dbgbuf);
sde_hw_rotator_unmap_vaddr(&ctx->dst_dbgbuf); sde_hw_rotator_unmap_vaddr(&ctx->dst_dbgbuf);