From: Russell King Date: Mon, 30 Jul 2018 10:52:34 +0000 (+0100) Subject: drm/armada: push responsibility for clock management to backend X-Git-Tag: for-linus-4.19b-rc1b-tag~59^2~9^2~11 X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=a0fbb35ecde52aa5abf5975d117d29e3b30f7b91;p=users%2Fdwmw2%2Flinux.git drm/armada: push responsibility for clock management to backend Push responsibility for managing the clock during DPMS down into the variant backend, rather than the CRTC layer having knowledge of its state. Signed-off-by: Russell King --- diff --git a/drivers/gpu/drm/armada/armada_510.c b/drivers/gpu/drm/armada/armada_510.c index 9a4fbb6a24b8f..2f7c048c53613 100644 --- a/drivers/gpu/drm/armada/armada_510.c +++ b/drivers/gpu/drm/armada/armada_510.c @@ -79,8 +79,27 @@ static int armada510_crtc_compute_clock(struct armada_crtc *dcrtc, return 0; } +static void armada510_crtc_disable(struct armada_crtc *dcrtc) +{ + if (!IS_ERR(dcrtc->clk)) { + clk_disable_unprepare(dcrtc->clk); + dcrtc->clk = ERR_PTR(-EINVAL); + } +} + +static void armada510_crtc_enable(struct armada_crtc *dcrtc, + const struct drm_display_mode *mode) +{ + if (IS_ERR(dcrtc->clk)) { + dcrtc->clk = dcrtc->extclk[0]; + WARN_ON(clk_prepare_enable(dcrtc->clk)); + } +} + const struct armada_variant armada510_ops = { .has_spu_adv_reg = true, .init = armada510_crtc_init, .compute_clock = armada510_crtc_compute_clock, + .disable = armada510_crtc_disable, + .enable = armada510_crtc_enable, }; diff --git a/drivers/gpu/drm/armada/armada_crtc.c b/drivers/gpu/drm/armada/armada_crtc.c index a0c67ec892cf5..5d8fdcda27ee8 100644 --- a/drivers/gpu/drm/armada/armada_crtc.c +++ b/drivers/gpu/drm/armada/armada_crtc.c @@ -253,14 +253,14 @@ static void armada_drm_crtc_dpms(struct drm_crtc *crtc, int dpms) if (dpms_blanked(dcrtc->dpms) != dpms_blanked(dpms)) { if (dpms_blanked(dpms)) armada_drm_vblank_off(dcrtc); - else if (!IS_ERR(dcrtc->clk)) - WARN_ON(clk_prepare_enable(dcrtc->clk)); + else if (dcrtc->variant->enable) + dcrtc->variant->enable(dcrtc, &crtc->hwmode); dcrtc->dpms = dpms; armada_drm_crtc_update(dcrtc); if (!dpms_blanked(dpms)) drm_crtc_vblank_on(&dcrtc->crtc); - else if (!IS_ERR(dcrtc->clk)) - clk_disable_unprepare(dcrtc->clk); + else if (dcrtc->variant->disable) + dcrtc->variant->disable(dcrtc); } else if (dcrtc->dpms != dpms) { dcrtc->dpms = dpms; } @@ -462,13 +462,6 @@ static void armada_drm_crtc_mode_set_nofb(struct drm_crtc *crtc) adj->type, adj->flags); DRM_DEBUG_KMS("lm %d rm %d tm %d bm %d\n", lm, rm, tm, bm); - /* - * If we are blanked, we would have disabled the clock. Re-enable - * it so that compute_clock() does the right thing. - */ - if (!IS_ERR(dcrtc->clk) && dpms_blanked(dcrtc->dpms)) - WARN_ON(clk_prepare_enable(dcrtc->clk)); - /* Now compute the divider for real */ dcrtc->variant->compute_clock(dcrtc, adj, &sclk); @@ -824,8 +817,8 @@ static void armada_drm_crtc_destroy(struct drm_crtc *crtc) priv->dcrtc[dcrtc->num] = NULL; drm_crtc_cleanup(&dcrtc->crtc); - if (!IS_ERR(dcrtc->clk)) - clk_disable_unprepare(dcrtc->clk); + if (dcrtc->variant->disable) + dcrtc->variant->disable(dcrtc); writel_relaxed(0, dcrtc->base + LCD_SPU_IRQ_ENA); diff --git a/drivers/gpu/drm/armada/armada_drm.h b/drivers/gpu/drm/armada/armada_drm.h index a6f919b0084c6..9658be917ea1e 100644 --- a/drivers/gpu/drm/armada/armada_drm.h +++ b/drivers/gpu/drm/armada/armada_drm.h @@ -46,6 +46,8 @@ struct armada_variant { int (*compute_clock)(struct armada_crtc *, const struct drm_display_mode *, uint32_t *); + void (*disable)(struct armada_crtc *); + void (*enable)(struct armada_crtc *, const struct drm_display_mode *); }; /* Variant ops */