From 74a27e95a02db904c452f4b06b0e976cbecf113e Mon Sep 17 00:00:00 2001 From: Alexey Sheplyakov Date: Thu, 28 Jan 2021 18:44:36 +0400 Subject: [PATCH 618/625] baikal_vdu: avoid using SMC calls for updating framebuffer address (from SDK-M 4.4) --- drivers/gpu/drm/baikal/baikal_vdu_drm.h | 16 ----- drivers/gpu/drm/baikal/baikal_vdu_drv.c | 2 - drivers/gpu/drm/baikal/baikal_vdu_plane.c | 88 ++++++++--------------- 3 files changed, 28 insertions(+), 78 deletions(-) diff --git a/drivers/gpu/drm/baikal/baikal_vdu_drm.h b/drivers/gpu/drm/baikal/baikal_vdu_drm.h index d049335dab1d..2db3fb73c9e7 100644 --- a/drivers/gpu/drm/baikal/baikal_vdu_drm.h +++ b/drivers/gpu/drm/baikal/baikal_vdu_drm.h @@ -22,23 +22,12 @@ #include #include -#include struct clk; struct drm_device; struct drm_fbdev_cma; struct drm_panel; -/*struct baikal_vdu_framebuffer { - u32 base; - u32 size; - u32 index; - u32 reg_base; - u32 reg_size; - u32 reg_width; - u32 reg_height; -};*/ - struct baikal_vdu_drm_connector { struct drm_connector connector; struct drm_panel *panel; @@ -61,8 +50,6 @@ struct baikal_vdu_private { u32 fb_addr; u32 fb_end; - - struct delayed_work update_work; }; #define to_baikal_vdu_drm_connector(x) \ @@ -89,7 +76,4 @@ int baikal_vdu_dumb_create(struct drm_file *file_priv, void baikal_vdu_debugfs_init(struct drm_minor *minor); -/* Worker functions */ -void baikal_vdu_update_work(struct work_struct *work); - #endif /* __BAIKAL_VDU_DRM_H__ */ diff --git a/drivers/gpu/drm/baikal/baikal_vdu_drv.c b/drivers/gpu/drm/baikal/baikal_vdu_drv.c index 0caa97dcb2e9..5deab510ea57 100644 --- a/drivers/gpu/drm/baikal/baikal_vdu_drv.c +++ b/drivers/gpu/drm/baikal/baikal_vdu_drv.c @@ -152,8 +152,6 @@ static int vdu_modeset_init(struct drm_device *dev) } arm_smccc_smc(BAIKAL_SMC_SCP_LOG_DISABLE, 0, 0, 0, 0, 0, 0, 0, &res); - INIT_DEFERRABLE_WORK(&priv->update_work, - baikal_vdu_update_work); drm_mode_config_reset(dev); diff --git a/drivers/gpu/drm/baikal/baikal_vdu_plane.c b/drivers/gpu/drm/baikal/baikal_vdu_plane.c index 9817af3c6de8..5a047835e154 100644 --- a/drivers/gpu/drm/baikal/baikal_vdu_plane.c +++ b/drivers/gpu/drm/baikal/baikal_vdu_plane.c @@ -17,7 +17,6 @@ * */ -#include #include #include #include @@ -32,42 +31,6 @@ #include "baikal_vdu_drm.h" #include "baikal_vdu_regs.h" -#define BAIKAL_SMC_VDU_UPDATE_HDMI 0x82000100 - -void baikal_vdu_update_work(struct work_struct *work) -{ - struct arm_smccc_res res; - unsigned long flags; - struct baikal_vdu_private *priv = container_of(work, struct baikal_vdu_private, - update_work.work); - int count = 0; - u64 t1, t2; - t1 = read_sysreg(CNTVCT_EL0); - spin_lock_irqsave(&priv->lock, flags); - arm_smccc_smc(BAIKAL_SMC_VDU_UPDATE_HDMI, priv->fb_addr, priv->fb_end, 0, 0, 0, 0, 0, &res); - spin_unlock_irqrestore(&priv->lock, flags); - if (res.a0 == -EBUSY) - priv->counters[15]++; - else - priv->counters[16]++; - while (res.a0 == -EBUSY && count < 10) { - count++; - usleep_range(10000, 20000); - res.a0 = 0; - spin_lock_irqsave(&priv->lock, flags); - arm_smccc_smc(BAIKAL_SMC_VDU_UPDATE_HDMI, priv->fb_addr, priv->fb_end, 0, 0, 0, 0, 0, &res); - spin_unlock_irqrestore(&priv->lock, flags); - if (res.a0 == -EBUSY) - priv->counters[15]++; - else - priv->counters[16]++; - } - t2 = read_sysreg(CNTVCT_EL0); - priv->counters[17] = t2 - t1; - priv->counters[18] = count; - priv->counters[19]++; -} - static int baikal_vdu_primary_plane_atomic_check(struct drm_plane *plane, struct drm_plane_state *state) { @@ -76,6 +39,7 @@ static int baikal_vdu_primary_plane_atomic_check(struct drm_plane *plane, struct drm_crtc_state *crtc_state; struct drm_display_mode *mode; int rate, ret; + u32 cntl; if (!state->crtc) return 0; @@ -86,6 +50,9 @@ static int baikal_vdu_primary_plane_atomic_check(struct drm_plane *plane, if (rate == clk_get_rate(priv->clk)) return 0; + /* hold clock domain reset; disable clocking */ + writel(0, priv->regs + PCTR); + if (__clk_is_enabled(priv->clk)) clk_disable_unprepare(priv->clk); ret = clk_set_rate(priv->clk, rate); @@ -94,15 +61,23 @@ static int baikal_vdu_primary_plane_atomic_check(struct drm_plane *plane, if (ret < 0) { DRM_ERROR("Cannot set desired pixel clock (%d Hz)\n", rate); - return -EINVAL; - } - clk_prepare_enable(priv->clk); - if (!__clk_is_enabled(priv->clk)) { - DRM_ERROR("PLL could not lock at desired frequency (%d Hz)\n", + ret = -EINVAL; + } else { + clk_prepare_enable(priv->clk); + if (__clk_is_enabled(priv->clk)) + ret = 0; + else { + DRM_ERROR("PLL could not lock at desired frequency (%d Hz)\n", rate); - return -EINVAL; + ret = -EINVAL; + } } - return 0; + + /* release clock domain reset; enable clocking */ + cntl = readl(priv->regs + PCTR); + cntl |= PCTR_PCR + PCTR_PCI; + + return ret; } static void baikal_vdu_primary_plane_atomic_update(struct drm_plane *plane, @@ -112,28 +87,13 @@ static void baikal_vdu_primary_plane_atomic_update(struct drm_plane *plane, struct baikal_vdu_private *priv = dev->dev_private; struct drm_plane_state *state = plane->state; struct drm_framebuffer *fb = state->fb; - struct arm_smccc_res res; u32 cntl, addr, end; - unsigned long flags; if (!fb) return; addr = drm_fb_cma_get_gem_addr(fb, state, 0); - end = ((addr + fb->height * fb->pitches[0] - 1) & MRR_DEAR_MRR_MASK) | MRR_OUTSTND_RQ(4); - - spin_lock_irqsave(&priv->lock, flags); - arm_smccc_smc(BAIKAL_SMC_VDU_UPDATE_HDMI, addr, end, 0, 0, 0, 0, 0, &res); - spin_unlock_irqrestore(&priv->lock, flags); - - if (res.a0 == -EBUSY) { - priv->counters[15]++; - priv->fb_addr = addr; - priv->fb_end = end; - smp_wmb(); - schedule_delayed_work(&priv->update_work, usecs_to_jiffies(250)); - } else - priv->counters[16]++; + priv->fb_addr = addr & 0xfffffff8; cntl = readl(priv->regs + CR1); cntl &= ~CR1_BPP_MASK; @@ -178,6 +138,14 @@ static void baikal_vdu_primary_plane_atomic_update(struct drm_plane *plane, break; } + writel(priv->fb_addr, priv->regs + DBAR); + end = ((priv->fb_addr + fb->height * fb->pitches[0] - 1) & MRR_DEAR_MRR_MASK) | \ + MRR_OUTSTND_RQ(4); + + if (priv->fb_end < end) { + writel(end, priv->regs + MRR); + priv->fb_end = end; + } writel(cntl, priv->regs + CR1); } -- 2.31.1