summaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/mediatek/mtk_drm_crtc.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/mediatek/mtk_drm_crtc.c')
-rw-r--r--drivers/gpu/drm/mediatek/mtk_drm_crtc.c27
1 files changed, 20 insertions, 7 deletions
diff --git a/drivers/gpu/drm/mediatek/mtk_drm_crtc.c b/drivers/gpu/drm/mediatek/mtk_drm_crtc.c
index d661edf7e0fe..ede435d2c1ef 100644
--- a/drivers/gpu/drm/mediatek/mtk_drm_crtc.c
+++ b/drivers/gpu/drm/mediatek/mtk_drm_crtc.c
@@ -12,7 +12,6 @@
#include <linux/soc/mediatek/mtk-mutex.h>
#include <asm/barrier.h>
-#include <soc/mediatek/smi.h>
#include <drm/drm_atomic.h>
#include <drm/drm_atomic_helper.h>
@@ -56,6 +55,7 @@ struct mtk_drm_crtc {
struct cmdq_pkt cmdq_handle;
u32 cmdq_event;
u32 cmdq_vblank_cnt;
+ wait_queue_head_t cb_blocking_queue;
#endif
struct device *mmsys_dev;
@@ -314,6 +314,7 @@ static void ddp_cmdq_cb(struct mbox_client *cl, void *mssg)
}
mtk_crtc->cmdq_vblank_cnt = 0;
+ wake_up(&mtk_crtc->cb_blocking_queue);
}
#endif
@@ -661,15 +662,15 @@ static void mtk_drm_crtc_atomic_enable(struct drm_crtc *crtc,
DRM_DEBUG_DRIVER("%s %d\n", __func__, crtc->base.id);
- ret = mtk_smi_larb_get(comp->larb_dev);
- if (ret) {
- DRM_ERROR("Failed to get larb: %d\n", ret);
+ ret = pm_runtime_resume_and_get(comp->dev);
+ if (ret < 0) {
+ DRM_DEV_ERROR(comp->dev, "Failed to enable power domain: %d\n", ret);
return;
}
ret = mtk_crtc_ddp_hw_init(mtk_crtc);
if (ret) {
- mtk_smi_larb_put(comp->larb_dev);
+ pm_runtime_put(comp->dev);
return;
}
@@ -682,7 +683,7 @@ static void mtk_drm_crtc_atomic_disable(struct drm_crtc *crtc,
{
struct mtk_drm_crtc *mtk_crtc = to_mtk_crtc(crtc);
struct mtk_ddp_comp *comp = mtk_crtc->ddp_comp[0];
- int i;
+ int i, ret;
DRM_DEBUG_DRIVER("%s %d\n", __func__, crtc->base.id);
if (!mtk_crtc->enabled)
@@ -700,12 +701,21 @@ static void mtk_drm_crtc_atomic_disable(struct drm_crtc *crtc,
mtk_crtc->pending_planes = true;
mtk_drm_crtc_update_config(mtk_crtc, false);
+#if IS_REACHABLE(CONFIG_MTK_CMDQ)
+ /* Wait for planes to be disabled by cmdq */
+ if (mtk_crtc->cmdq_client.chan)
+ wait_event_timeout(mtk_crtc->cb_blocking_queue,
+ mtk_crtc->cmdq_vblank_cnt == 0,
+ msecs_to_jiffies(500));
+#endif
/* Wait for planes to be disabled */
drm_crtc_wait_one_vblank(crtc);
drm_crtc_vblank_off(crtc);
mtk_crtc_ddp_hw_fini(mtk_crtc);
- mtk_smi_larb_put(comp->larb_dev);
+ ret = pm_runtime_put(comp->dev);
+ if (ret < 0)
+ DRM_DEV_ERROR(comp->dev, "Failed to disable power domain: %d\n", ret);
mtk_crtc->enabled = false;
}
@@ -976,6 +986,9 @@ int mtk_drm_crtc_create(struct drm_device *drm_dev,
mtk_crtc->cmdq_client.chan = NULL;
}
}
+
+ /* for sending blocking cmd in crtc disable */
+ init_waitqueue_head(&mtk_crtc->cb_blocking_queue);
}
#endif
return 0;