diff options
Diffstat (limited to 'drivers/gpu/drm/i915/intel_ddi.c')
-rw-r--r-- | drivers/gpu/drm/i915/intel_ddi.c | 321 |
1 files changed, 153 insertions, 168 deletions
diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 98cea1f4b3bf..f181c26f62fd 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -26,9 +26,19 @@ */ #include <drm/drm_scdc_helper.h> + #include "i915_drv.h" +#include "intel_audio.h" +#include "intel_connector.h" +#include "intel_ddi.h" +#include "intel_dp.h" #include "intel_drv.h" #include "intel_dsi.h" +#include "intel_hdcp.h" +#include "intel_hdmi.h" +#include "intel_lspcon.h" +#include "intel_panel.h" +#include "intel_psr.h" struct ddi_buf_trans { u32 trans1; /* balance leg enable, de-emph level */ @@ -851,7 +861,7 @@ static int intel_ddi_hdmi_level(struct drm_i915_private *dev_priv, enum port por level = dev_priv->vbt.ddi_port_info[port].hdmi_level_shift; - if (IS_ICELAKE(dev_priv)) { + if (INTEL_GEN(dev_priv) >= 11) { if (intel_port_is_combophy(dev_priv, port)) icl_get_combo_buf_trans(dev_priv, port, INTEL_OUTPUT_HDMI, 0, &n_entries); @@ -1240,24 +1250,15 @@ static int hsw_ddi_calc_wrpll_link(struct drm_i915_private *dev_priv, return (refclk * n * 100) / (p * r); } -static int skl_calc_wrpll_link(struct drm_i915_private *dev_priv, - enum intel_dpll_id pll_id) +static int skl_calc_wrpll_link(const struct intel_dpll_hw_state *pll_state) { - i915_reg_t cfgcr1_reg, cfgcr2_reg; - u32 cfgcr1_val, cfgcr2_val; u32 p0, p1, p2, dco_freq; - cfgcr1_reg = DPLL_CFGCR1(pll_id); - cfgcr2_reg = DPLL_CFGCR2(pll_id); - - cfgcr1_val = I915_READ(cfgcr1_reg); - cfgcr2_val = I915_READ(cfgcr2_reg); - - p0 = cfgcr2_val & DPLL_CFGCR2_PDIV_MASK; - p2 = cfgcr2_val & DPLL_CFGCR2_KDIV_MASK; + p0 = pll_state->cfgcr2 & DPLL_CFGCR2_PDIV_MASK; + p2 = pll_state->cfgcr2 & DPLL_CFGCR2_KDIV_MASK; - if (cfgcr2_val & DPLL_CFGCR2_QDIV_MODE(1)) - p1 = (cfgcr2_val & DPLL_CFGCR2_QDIV_RATIO_MASK) >> 8; + if (pll_state->cfgcr2 & DPLL_CFGCR2_QDIV_MODE(1)) + p1 = (pll_state->cfgcr2 & DPLL_CFGCR2_QDIV_RATIO_MASK) >> 8; else p1 = 1; @@ -1292,10 +1293,11 @@ static int skl_calc_wrpll_link(struct drm_i915_private *dev_priv, break; } - dco_freq = (cfgcr1_val & DPLL_CFGCR1_DCO_INTEGER_MASK) * 24 * 1000; + dco_freq = (pll_state->cfgcr1 & DPLL_CFGCR1_DCO_INTEGER_MASK) + * 24 * 1000; - dco_freq += (((cfgcr1_val & DPLL_CFGCR1_DCO_FRACTION_MASK) >> 9) * 24 * - 1000) / 0x8000; + dco_freq += (((pll_state->cfgcr1 & DPLL_CFGCR1_DCO_FRACTION_MASK) >> 9) + * 24 * 1000) / 0x8000; if (WARN_ON(p0 == 0 || p1 == 0 || p2 == 0)) return 0; @@ -1304,24 +1306,15 @@ static int skl_calc_wrpll_link(struct drm_i915_private *dev_priv, } int cnl_calc_wrpll_link(struct drm_i915_private *dev_priv, - enum intel_dpll_id pll_id) + struct intel_dpll_hw_state *pll_state) { - u32 cfgcr0, cfgcr1; u32 p0, p1, p2, dco_freq, ref_clock; - if (INTEL_GEN(dev_priv) >= 11) { - cfgcr0 = I915_READ(ICL_DPLL_CFGCR0(pll_id)); - cfgcr1 = I915_READ(ICL_DPLL_CFGCR1(pll_id)); - } else { - cfgcr0 = I915_READ(CNL_DPLL_CFGCR0(pll_id)); - cfgcr1 = I915_READ(CNL_DPLL_CFGCR1(pll_id)); - } - - p0 = cfgcr1 & DPLL_CFGCR1_PDIV_MASK; - p2 = cfgcr1 & DPLL_CFGCR1_KDIV_MASK; + p0 = pll_state->cfgcr1 & DPLL_CFGCR1_PDIV_MASK; + p2 = pll_state->cfgcr1 & DPLL_CFGCR1_KDIV_MASK; - if (cfgcr1 & DPLL_CFGCR1_QDIV_MODE(1)) - p1 = (cfgcr1 & DPLL_CFGCR1_QDIV_RATIO_MASK) >> + if (pll_state->cfgcr1 & DPLL_CFGCR1_QDIV_MODE(1)) + p1 = (pll_state->cfgcr1 & DPLL_CFGCR1_QDIV_RATIO_MASK) >> DPLL_CFGCR1_QDIV_RATIO_SHIFT; else p1 = 1; @@ -1349,16 +1342,17 @@ int cnl_calc_wrpll_link(struct drm_i915_private *dev_priv, case DPLL_CFGCR1_KDIV_2: p2 = 2; break; - case DPLL_CFGCR1_KDIV_4: - p2 = 4; + case DPLL_CFGCR1_KDIV_3: + p2 = 3; break; } ref_clock = cnl_hdmi_pll_ref_clock(dev_priv); - dco_freq = (cfgcr0 & DPLL_CFGCR0_DCO_INTEGER_MASK) * ref_clock; + dco_freq = (pll_state->cfgcr0 & DPLL_CFGCR0_DCO_INTEGER_MASK) + * ref_clock; - dco_freq += (((cfgcr0 & DPLL_CFGCR0_DCO_FRACTION_MASK) >> + dco_freq += (((pll_state->cfgcr0 & DPLL_CFGCR0_DCO_FRACTION_MASK) >> DPLL_CFGCR0_DCO_FRACTION_SHIFT) * ref_clock) / 0x8000; if (WARN_ON(p0 == 0 || p1 == 0 || p2 == 0)) @@ -1390,25 +1384,21 @@ static int icl_calc_tbt_pll_link(struct drm_i915_private *dev_priv, } static int icl_calc_mg_pll_link(struct drm_i915_private *dev_priv, - enum port port) + const struct intel_dpll_hw_state *pll_state) { - enum tc_port tc_port = intel_port_to_tc(dev_priv, port); - u32 mg_pll_div0, mg_clktop_hsclkctl; - u32 m1, m2_int, m2_frac, div1, div2, refclk; + u32 m1, m2_int, m2_frac, div1, div2, ref_clock; u64 tmp; - refclk = dev_priv->cdclk.hw.ref; - - mg_pll_div0 = I915_READ(MG_PLL_DIV0(tc_port)); - mg_clktop_hsclkctl = I915_READ(MG_CLKTOP2_HSCLKCTL(tc_port)); + ref_clock = dev_priv->cdclk.hw.ref; - m1 = I915_READ(MG_PLL_DIV1(tc_port)) & MG_PLL_DIV1_FBPREDIV_MASK; - m2_int = mg_pll_div0 & MG_PLL_DIV0_FBDIV_INT_MASK; - m2_frac = (mg_pll_div0 & MG_PLL_DIV0_FRACNEN_H) ? - (mg_pll_div0 & MG_PLL_DIV0_FBDIV_FRAC_MASK) >> - MG_PLL_DIV0_FBDIV_FRAC_SHIFT : 0; + m1 = pll_state->mg_pll_div1 & MG_PLL_DIV1_FBPREDIV_MASK; + m2_int = pll_state->mg_pll_div0 & MG_PLL_DIV0_FBDIV_INT_MASK; + m2_frac = (pll_state->mg_pll_div0 & MG_PLL_DIV0_FRACNEN_H) ? + (pll_state->mg_pll_div0 & MG_PLL_DIV0_FBDIV_FRAC_MASK) >> + MG_PLL_DIV0_FBDIV_FRAC_SHIFT : 0; - switch (mg_clktop_hsclkctl & MG_CLKTOP2_HSCLKCTL_HSDIV_RATIO_MASK) { + switch (pll_state->mg_clktop2_hsclkctl & + MG_CLKTOP2_HSCLKCTL_HSDIV_RATIO_MASK) { case MG_CLKTOP2_HSCLKCTL_HSDIV_RATIO_2: div1 = 2; break; @@ -1422,12 +1412,14 @@ static int icl_calc_mg_pll_link(struct drm_i915_private *dev_priv, div1 = 7; break; default: - MISSING_CASE(mg_clktop_hsclkctl); + MISSING_CASE(pll_state->mg_clktop2_hsclkctl); return 0; } - div2 = (mg_clktop_hsclkctl & MG_CLKTOP2_HSCLKCTL_DSDIV_RATIO_MASK) >> + div2 = (pll_state->mg_clktop2_hsclkctl & + MG_CLKTOP2_HSCLKCTL_DSDIV_RATIO_MASK) >> MG_CLKTOP2_HSCLKCTL_DSDIV_RATIO_SHIFT; + /* div2 value of 0 is same as 1 means no div */ if (div2 == 0) div2 = 1; @@ -1436,8 +1428,8 @@ static int icl_calc_mg_pll_link(struct drm_i915_private *dev_priv, * Adjust the original formula to delay the division by 2^22 in order to * minimize possible rounding errors. */ - tmp = (u64)m1 * m2_int * refclk + - (((u64)m1 * m2_frac * refclk) >> 22); + tmp = (u64)m1 * m2_int * ref_clock + + (((u64)m1 * m2_frac * ref_clock) >> 22); tmp = div_u64(tmp, 5 * div1 * div2); return tmp; @@ -1471,25 +1463,24 @@ static void icl_ddi_clock_get(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config) { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); + struct intel_dpll_hw_state *pll_state = &pipe_config->dpll_hw_state; enum port port = encoder->port; - int link_clock = 0; - u32 pll_id; + int link_clock; - pll_id = intel_get_shared_dpll_id(dev_priv, pipe_config->shared_dpll); if (intel_port_is_combophy(dev_priv, port)) { - if (intel_crtc_has_type(pipe_config, INTEL_OUTPUT_HDMI)) - link_clock = cnl_calc_wrpll_link(dev_priv, pll_id); - else - link_clock = icl_calc_dp_combo_pll_link(dev_priv, - pll_id); + link_clock = cnl_calc_wrpll_link(dev_priv, pll_state); } else { + enum intel_dpll_id pll_id = intel_get_shared_dpll_id(dev_priv, + pipe_config->shared_dpll); + if (pll_id == DPLL_ID_ICL_TBTPLL) link_clock = icl_calc_tbt_pll_link(dev_priv, port); else - link_clock = icl_calc_mg_pll_link(dev_priv, port); + link_clock = icl_calc_mg_pll_link(dev_priv, pll_state); } pipe_config->port_clock = link_clock; + ddi_dotclock_get(pipe_config); } @@ -1497,18 +1488,13 @@ static void cnl_ddi_clock_get(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config) { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - int link_clock = 0; - u32 cfgcr0; - enum intel_dpll_id pll_id; - - pll_id = intel_get_shared_dpll_id(dev_priv, pipe_config->shared_dpll); + struct intel_dpll_hw_state *pll_state = &pipe_config->dpll_hw_state; + int link_clock; - cfgcr0 = I915_READ(CNL_DPLL_CFGCR0(pll_id)); - - if (cfgcr0 & DPLL_CFGCR0_HDMI_MODE) { - link_clock = cnl_calc_wrpll_link(dev_priv, pll_id); + if (pll_state->cfgcr0 & DPLL_CFGCR0_HDMI_MODE) { + link_clock = cnl_calc_wrpll_link(dev_priv, pll_state); } else { - link_clock = cfgcr0 & DPLL_CFGCR0_LINK_RATE_MASK; + link_clock = pll_state->cfgcr0 & DPLL_CFGCR0_LINK_RATE_MASK; switch (link_clock) { case DPLL_CFGCR0_LINK_RATE_810: @@ -1548,22 +1534,20 @@ static void cnl_ddi_clock_get(struct intel_encoder *encoder, } static void skl_ddi_clock_get(struct intel_encoder *encoder, - struct intel_crtc_state *pipe_config) + struct intel_crtc_state *pipe_config) { - struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - int link_clock = 0; - u32 dpll_ctl1; - enum intel_dpll_id pll_id; - - pll_id = intel_get_shared_dpll_id(dev_priv, pipe_config->shared_dpll); + struct intel_dpll_hw_state *pll_state = &pipe_config->dpll_hw_state; + int link_clock; - dpll_ctl1 = I915_READ(DPLL_CTRL1); - - if (dpll_ctl1 & DPLL_CTRL1_HDMI_MODE(pll_id)) { - link_clock = skl_calc_wrpll_link(dev_priv, pll_id); + /* + * ctrl1 register is already shifted for each pll, just use 0 to get + * the internal shift for each field + */ + if (pll_state->ctrl1 & DPLL_CTRL1_HDMI_MODE(0)) { + link_clock = skl_calc_wrpll_link(pll_state); } else { - link_clock = dpll_ctl1 & DPLL_CTRL1_LINK_RATE_MASK(pll_id); - link_clock >>= DPLL_CTRL1_LINK_RATE_SHIFT(pll_id); + link_clock = pll_state->ctrl1 & DPLL_CTRL1_LINK_RATE_MASK(0); + link_clock >>= DPLL_CTRL1_LINK_RATE_SHIFT(0); switch (link_clock) { case DPLL_CTRL1_LINK_RATE_810: @@ -1643,24 +1627,17 @@ static void hsw_ddi_clock_get(struct intel_encoder *encoder, ddi_dotclock_get(pipe_config); } -static int bxt_calc_pll_link(struct intel_crtc_state *crtc_state) +static int bxt_calc_pll_link(const struct intel_dpll_hw_state *pll_state) { - struct intel_dpll_hw_state *state; struct dpll clock; - /* For DDI ports we always use a shared PLL. */ - if (WARN_ON(!crtc_state->shared_dpll)) - return 0; - - state = &crtc_state->dpll_hw_state; - clock.m1 = 2; - clock.m2 = (state->pll0 & PORT_PLL_M2_MASK) << 22; - if (state->pll3 & PORT_PLL_M2_FRAC_ENABLE) - clock.m2 |= state->pll2 & PORT_PLL_M2_FRAC_MASK; - clock.n = (state->pll1 & PORT_PLL_N_MASK) >> PORT_PLL_N_SHIFT; - clock.p1 = (state->ebb0 & PORT_PLL_P1_MASK) >> PORT_PLL_P1_SHIFT; - clock.p2 = (state->ebb0 & PORT_PLL_P2_MASK) >> PORT_PLL_P2_SHIFT; + clock.m2 = (pll_state->pll0 & PORT_PLL_M2_MASK) << 22; + if (pll_state->pll3 & PORT_PLL_M2_FRAC_ENABLE) + clock.m2 |= pll_state->pll2 & PORT_PLL_M2_FRAC_MASK; + clock.n = (pll_state->pll1 & PORT_PLL_N_MASK) >> PORT_PLL_N_SHIFT; + clock.p1 = (pll_state->ebb0 & PORT_PLL_P1_MASK) >> PORT_PLL_P1_SHIFT; + clock.p2 = (pll_state->ebb0 & PORT_PLL_P2_MASK) >> PORT_PLL_P2_SHIFT; return chv_calc_dpll_params(100000, &clock); } @@ -1668,7 +1645,8 @@ static int bxt_calc_pll_link(struct intel_crtc_state *crtc_state) static void bxt_ddi_clock_get(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config) { - pipe_config->port_clock = bxt_calc_pll_link(pipe_config); + pipe_config->port_clock = + bxt_calc_pll_link(&pipe_config->dpll_hw_state); ddi_dotclock_get(pipe_config); } @@ -1678,7 +1656,7 @@ static void intel_ddi_clock_get(struct intel_encoder *encoder, { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); - if (IS_ICELAKE(dev_priv)) + if (INTEL_GEN(dev_priv) >= 11) icl_ddi_clock_get(encoder, pipe_config); else if (IS_CANNONLAKE(dev_priv)) cnl_ddi_clock_get(encoder, pipe_config); @@ -1911,7 +1889,7 @@ bool intel_ddi_connector_get_hw_state(struct intel_connector *intel_connector) goto out; } - if (port == PORT_A) + if (HAS_TRANSCODER_EDP(dev_priv) && port == PORT_A) cpu_transcoder = TRANSCODER_EDP; else cpu_transcoder = (enum transcoder) pipe; @@ -1973,7 +1951,7 @@ static void intel_ddi_get_encoder_pipes(struct intel_encoder *encoder, if (!(tmp & DDI_BUF_CTL_ENABLE)) goto out; - if (port == PORT_A) { + if (HAS_TRANSCODER_EDP(dev_priv) && port == PORT_A) { tmp = I915_READ(TRANS_DDI_FUNC_CTL(TRANSCODER_EDP)); switch (tmp & TRANS_DDI_EDP_INPUT_MASK) { @@ -2224,7 +2202,7 @@ u8 intel_ddi_dp_voltage_max(struct intel_encoder *encoder) enum port port = encoder->port; int n_entries; - if (IS_ICELAKE(dev_priv)) { + if (INTEL_GEN(dev_priv) >= 11) { if (intel_port_is_combophy(dev_priv, port)) icl_get_combo_buf_trans(dev_priv, port, encoder->type, intel_dp->link_rate, &n_entries); @@ -2316,13 +2294,13 @@ static void cnl_ddi_vswing_program(struct intel_encoder *encoder, /* Program PORT_TX_DW4 */ /* We cannot write to GRP. It would overrite individual loadgen */ for (ln = 0; ln < 4; ln++) { - val = I915_READ(CNL_PORT_TX_DW4_LN(port, ln)); + val = I915_READ(CNL_PORT_TX_DW4_LN(ln, port)); val &= ~(POST_CURSOR_1_MASK | POST_CURSOR_2_MASK | CURSOR_COEFF_MASK); val |= POST_CURSOR_1(ddi_translations[level].dw4_post_cursor_1); val |= POST_CURSOR_2(ddi_translations[level].dw4_post_cursor_2); val |= CURSOR_COEFF(ddi_translations[level].dw4_cursor_coeff); - I915_WRITE(CNL_PORT_TX_DW4_LN(port, ln), val); + I915_WRITE(CNL_PORT_TX_DW4_LN(ln, port), val); } /* Program PORT_TX_DW5 */ @@ -2378,14 +2356,14 @@ static void cnl_ddi_vswing_sequence(struct intel_encoder *encoder, * > 6 GHz (LN0=0, LN1=0, LN2=0, LN3=0) */ for (ln = 0; ln <= 3; ln++) { - val = I915_READ(CNL_PORT_TX_DW4_LN(port, ln)); + val = I915_READ(CNL_PORT_TX_DW4_LN(ln, port)); val &= ~LOADGEN_SELECT; if ((rate <= 600000 && width == 4 && ln >= 1) || (rate <= 600000 && width < 4 && (ln == 1 || ln == 2))) { val |= LOADGEN_SELECT; } - I915_WRITE(CNL_PORT_TX_DW4_LN(port, ln), val); + I915_WRITE(CNL_PORT_TX_DW4_LN(ln, port), val); } /* 3. Set PORT_CL_DW5 SUS Clock Config to 11b */ @@ -2447,13 +2425,13 @@ static void icl_ddi_combo_vswing_program(struct drm_i915_private *dev_priv, /* Program PORT_TX_DW4 */ /* We cannot write to GRP. It would overwrite individual loadgen. */ for (ln = 0; ln <= 3; ln++) { - val = I915_READ(ICL_PORT_TX_DW4_LN(port, ln)); + val = I915_READ(ICL_PORT_TX_DW4_LN(ln, port)); val &= ~(POST_CURSOR_1_MASK | POST_CURSOR_2_MASK | CURSOR_COEFF_MASK); val |= POST_CURSOR_1(ddi_translations[level].dw4_post_cursor_1); val |= POST_CURSOR_2(ddi_translations[level].dw4_post_cursor_2); val |= CURSOR_COEFF(ddi_translations[level].dw4_cursor_coeff); - I915_WRITE(ICL_PORT_TX_DW4_LN(port, ln), val); + I915_WRITE(ICL_PORT_TX_DW4_LN(ln, port), val); } /* Program PORT_TX_DW7 */ @@ -2504,14 +2482,14 @@ static void icl_combo_phy_ddi_vswing_sequence(struct intel_encoder *encoder, * > 6 GHz (LN0=0, LN1=0, LN2=0, LN3=0) */ for (ln = 0; ln <= 3; ln++) { - val = I915_READ(ICL_PORT_TX_DW4_LN(port, ln)); + val = I915_READ(ICL_PORT_TX_DW4_LN(ln, port)); val &= ~LOADGEN_SELECT; if ((rate <= 600000 && width == 4 && ln >= 1) || (rate <= 600000 && width < 4 && (ln == 1 || ln == 2))) { val |= LOADGEN_SELECT; } - I915_WRITE(ICL_PORT_TX_DW4_LN(port, ln), val); + I915_WRITE(ICL_PORT_TX_DW4_LN(ln, port), val); } /* 3. Set PORT_CL_DW5 SUS Clock Config to 11b */ @@ -2554,33 +2532,33 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, /* Set MG_TX_LINK_PARAMS cri_use_fs32 to 0. */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_TX1_LINK_PARAMS(port, ln)); + val = I915_READ(MG_TX1_LINK_PARAMS(ln, port)); val &= ~CRI_USE_FS32; - I915_WRITE(MG_TX1_LINK_PARAMS(port, ln), val); + I915_WRITE(MG_TX1_LINK_PARAMS(ln, port), val); - val = I915_READ(MG_TX2_LINK_PARAMS(port, ln)); + val = I915_READ(MG_TX2_LINK_PARAMS(ln, port)); val &= ~CRI_USE_FS32; - I915_WRITE(MG_TX2_LINK_PARAMS(port, ln), val); + I915_WRITE(MG_TX2_LINK_PARAMS(ln, port), val); } /* Program MG_TX_SWINGCTRL with values from vswing table */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_TX1_SWINGCTRL(port, ln)); + val = I915_READ(MG_TX1_SWINGCTRL(ln, port)); val &= ~CRI_TXDEEMPH_OVERRIDE_17_12_MASK; val |= CRI_TXDEEMPH_OVERRIDE_17_12( ddi_translations[level].cri_txdeemph_override_17_12); - I915_WRITE(MG_TX1_SWINGCTRL(port, ln), val); + I915_WRITE(MG_TX1_SWINGCTRL(ln, port), val); - val = I915_READ(MG_TX2_SWINGCTRL(port, ln)); + val = I915_READ(MG_TX2_SWINGCTRL(ln, port)); val &= ~CRI_TXDEEMPH_OVERRIDE_17_12_MASK; val |= CRI_TXDEEMPH_OVERRIDE_17_12( ddi_translations[level].cri_txdeemph_override_17_12); - I915_WRITE(MG_TX2_SWINGCTRL(port, ln), val); + I915_WRITE(MG_TX2_SWINGCTRL(ln, port), val); } /* Program MG_TX_DRVCTRL with values from vswing table */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_TX1_DRVCTRL(port, ln)); + val = I915_READ(MG_TX1_DRVCTRL(ln, port)); val &= ~(CRI_TXDEEMPH_OVERRIDE_11_6_MASK | CRI_TXDEEMPH_OVERRIDE_5_0_MASK); val |= CRI_TXDEEMPH_OVERRIDE_5_0( @@ -2588,9 +2566,9 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, CRI_TXDEEMPH_OVERRIDE_11_6( ddi_translations[level].cri_txdeemph_override_11_6) | CRI_TXDEEMPH_OVERRIDE_EN; - I915_WRITE(MG_TX1_DRVCTRL(port, ln), val); + I915_WRITE(MG_TX1_DRVCTRL(ln, port), val); - val = I915_READ(MG_TX2_DRVCTRL(port, ln)); + val = I915_READ(MG_TX2_DRVCTRL(ln, port)); val &= ~(CRI_TXDEEMPH_OVERRIDE_11_6_MASK | CRI_TXDEEMPH_OVERRIDE_5_0_MASK); val |= CRI_TXDEEMPH_OVERRIDE_5_0( @@ -2598,7 +2576,7 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, CRI_TXDEEMPH_OVERRIDE_11_6( ddi_translations[level].cri_txdeemph_override_11_6) | CRI_TXDEEMPH_OVERRIDE_EN; - I915_WRITE(MG_TX2_DRVCTRL(port, ln), val); + I915_WRITE(MG_TX2_DRVCTRL(ln, port), val); /* FIXME: Program CRI_LOADGEN_SEL after the spec is updated */ } @@ -2609,17 +2587,17 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, * values from table for which TX1 and TX2 enabled. */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_CLKHUB(port, ln)); + val = I915_READ(MG_CLKHUB(ln, port)); if (link_clock < 300000) val |= CFG_LOW_RATE_LKREN_EN; else val &= ~CFG_LOW_RATE_LKREN_EN; - I915_WRITE(MG_CLKHUB(port, ln), val); + I915_WRITE(MG_CLKHUB(ln, port), val); } /* Program the MG_TX_DCC<LN, port being used> based on the link frequency */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_TX1_DCC(port, ln)); + val = I915_READ(MG_TX1_DCC(ln, port)); val &= ~CFG_AMI_CK_DIV_OVERRIDE_VAL_MASK; if (link_clock <= 500000) { val &= ~CFG_AMI_CK_DIV_OVERRIDE_EN; @@ -2627,9 +2605,9 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, val |= CFG_AMI_CK_DIV_OVERRIDE_EN | CFG_AMI_CK_DIV_OVERRIDE_VAL(1); } - I915_WRITE(MG_TX1_DCC(port, ln), val); + I915_WRITE(MG_TX1_DCC(ln, port), val); - val = I915_READ(MG_TX2_DCC(port, ln)); + val = I915_READ(MG_TX2_DCC(ln, port)); val &= ~CFG_AMI_CK_DIV_OVERRIDE_VAL_MASK; if (link_clock <= 500000) { val &= ~CFG_AMI_CK_DIV_OVERRIDE_EN; @@ -2637,18 +2615,18 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, val |= CFG_AMI_CK_DIV_OVERRIDE_EN | CFG_AMI_CK_DIV_OVERRIDE_VAL(1); } - I915_WRITE(MG_TX2_DCC(port, ln), val); + I915_WRITE(MG_TX2_DCC(ln, port), val); } /* Program MG_TX_PISO_READLOAD with values from vswing table */ for (ln = 0; ln < 2; ln++) { - val = I915_READ(MG_TX1_PISO_READLOAD(port, ln)); + val = I915_READ(MG_TX1_PISO_READLOAD(ln, port)); val |= CRI_CALCINIT; - I915_WRITE(MG_TX1_PISO_READLOAD(port, ln), val); + I915_WRITE(MG_TX1_PISO_READLOAD(ln, port), val); - val = I915_READ(MG_TX2_PISO_READLOAD(port, ln)); + val = I915_READ(MG_TX2_PISO_READLOAD(ln, port)); val |= CRI_CALCINIT; - I915_WRITE(MG_TX2_PISO_READLOAD(port, ln), val); + I915_WRITE(MG_TX2_PISO_READLOAD(ln, port), val); } } @@ -2697,7 +2675,7 @@ u32 bxt_signal_levels(struct intel_dp *intel_dp) struct intel_encoder *encoder = &dport->base; int level = intel_ddi_dp_level(intel_dp); - if (IS_ICELAKE(dev_priv)) + if (INTEL_GEN(dev_priv) >= 11) icl_ddi_vswing_sequence(encoder, intel_dp->link_rate, level, encoder->type); else if (IS_CANNONLAKE(dev_priv)) @@ -2866,7 +2844,7 @@ static void intel_ddi_clk_select(struct intel_encoder *encoder, mutex_lock(&dev_priv->dpll_lock); - if (IS_ICELAKE(dev_priv)) { + if (INTEL_GEN(dev_priv) >= 11) { if (!intel_port_is_combophy(dev_priv, port)) I915_WRITE(DDI_CLK_SEL(port), icl_pll_to_ddi_clk_sel(encoder, crtc_state)); @@ -2908,7 +2886,7 @@ static void intel_ddi_clk_disable(struct intel_encoder *encoder) struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); enum port port = encoder->port; - if (IS_ICELAKE(dev_priv)) { + if (INTEL_GEN(dev_priv) >= 11) { if (!intel_port_is_combophy(dev_priv, port)) I915_WRITE(DDI_CLK_SEL(port), DDI_CLK_SEL_NONE); } else if (IS_CANNONLAKE(dev_priv)) { @@ -2927,21 +2905,20 @@ static void icl_enable_phy_clock_gating(struct intel_digital_port *dig_port) struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev); enum port port = dig_port->base.port; enum tc_port tc_port = intel_port_to_tc(dev_priv, port); - i915_reg_t mg_regs[2] = { MG_DP_MODE(port, 0), MG_DP_MODE(port, 1) }; u32 val; - int i; + int ln; if (tc_port == PORT_TC_NONE) return; - for (i = 0; i < ARRAY_SIZE(mg_regs); i++) { - val = I915_READ(mg_regs[i]); + for (ln = 0; ln < 2; ln++) { + val = I915_READ(MG_DP_MODE(ln, port)); val |= MG_DP_MODE_CFG_TR2PWR_GATING | MG_DP_MODE_CFG_TRPWR_GATING | MG_DP_MODE_CFG_CLNPWR_GATING | MG_DP_MODE_CFG_DIGPWR_GATING | MG_DP_MODE_CFG_GAONPWR_GATING; - I915_WRITE(mg_regs[i], val); + I915_WRITE(MG_DP_MODE(ln, port), val); } val = I915_READ(MG_MISC_SUS0(tc_port)); @@ -2960,21 +2937,20 @@ static void icl_disable_phy_clock_gating(struct intel_digital_port *dig_port) struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev); enum port port = dig_port->base.port; enum tc_port tc_port = intel_port_to_tc(dev_priv, port); - i915_reg_t mg_regs[2] = { MG_DP_MODE(port, 0), MG_DP_MODE(port, 1) }; u32 val; - int i; + int ln; if (tc_port == PORT_TC_NONE) return; - for (i = 0; i < ARRAY_SIZE(mg_regs); i++) { - val = I915_READ(mg_regs[i]); + for (ln = 0; ln < 2; ln++) { + val = I915_READ(MG_DP_MODE(ln, port)); val &= ~(MG_DP_MODE_CFG_TR2PWR_GATING | MG_DP_MODE_CFG_TRPWR_GATING | MG_DP_MODE_CFG_CLNPWR_GATING | MG_DP_MODE_CFG_DIGPWR_GATING | MG_DP_MODE_CFG_GAONPWR_GATING); - I915_WRITE(mg_regs[i], val); + I915_WRITE(MG_DP_MODE(ln, port), val); } val = I915_READ(MG_MISC_SUS0(tc_port)); @@ -2998,8 +2974,8 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port) if (tc_port == PORT_TC_NONE || intel_dig_port->tc_type == TC_PORT_TBT) return; - ln0 = I915_READ(MG_DP_MODE(port, 0)); - ln1 = I915_READ(MG_DP_MODE(port, 1)); + ln0 = I915_READ(MG_DP_MODE(0, port)); + ln1 = I915_READ(MG_DP_MODE(1, port)); switch (intel_dig_port->tc_type) { case TC_PORT_TYPEC: @@ -3049,8 +3025,8 @@ static void icl_program_mg_dp_mode(struct intel_digital_port *intel_dig_port) return; } - I915_WRITE(MG_DP_MODE(port, 0), ln0); - I915_WRITE(MG_DP_MODE(port, 1), ln1); + I915_WRITE(MG_DP_MODE(0, port), ln0); + I915_WRITE(MG_DP_MODE(1, port), ln1); } static void intel_dp_sink_set_fec_ready(struct intel_dp *intel_dp, @@ -3077,7 +3053,7 @@ static void intel_ddi_enable_fec(struct intel_encoder *encoder, val |= DP_TP_CTL_FEC_ENABLE; I915_WRITE(DP_TP_CTL(port), val); - if (intel_wait_for_register(dev_priv, DP_TP_STATUS(port), + if (intel_wait_for_register(&dev_priv->uncore, DP_TP_STATUS(port), DP_TP_STATUS_FEC_ENABLE_LIVE, DP_TP_STATUS_FEC_ENABLE_LIVE, 1)) @@ -3125,7 +3101,7 @@ static void intel_ddi_pre_enable_dp(struct intel_encoder *encoder, icl_program_mg_dp_mode(dig_port); icl_disable_phy_clock_gating(dig_port); - if (IS_ICELAKE(dev_priv)) + if (INTEL_GEN(dev_priv) >= 11) icl_ddi_vswing_sequence(encoder, crtc_state->port_clock, level, encoder->type); else if (IS_CANNONLAKE(dev_priv)) @@ -3174,7 +3150,7 @@ static void intel_ddi_pre_enable_hdmi(struct intel_encoder *encoder, icl_program_mg_dp_mode(dig_port); icl_disable_phy_clock_gating(dig_port); - if (IS_ICELAKE(dev_priv)) + if (INTEL_GEN(dev_priv) >= 11) icl_ddi_vswing_sequence(encoder, crtc_state->port_clock, level, INTEL_OUTPUT_HDMI); else if (IS_CANNONLAKE(dev_priv)) @@ -3555,7 +3531,9 @@ static void intel_ddi_update_pipe_dp(struct intel_encoder *encoder, { struct intel_dp *intel_dp = enc_to_intel_dp(&encoder->base); - intel_psr_enable(intel_dp, crtc_state); + intel_ddi_set_pipe_settings(crtc_state); + + intel_psr_update(intel_dp, crtc_state); intel_edp_drrs_enable(intel_dp, crtc_state); intel_panel_update_backlight(encoder, crtc_state, conn_state); @@ -3710,7 +3688,7 @@ static bool intel_ddi_is_audio_enabled(struct drm_i915_private *dev_priv, void intel_ddi_compute_min_voltage_level(struct drm_i915_private *dev_priv, struct intel_crtc_state *crtc_state) { - if (IS_ICELAKE(dev_priv) && crtc_state->port_clock > 594000) + if (INTEL_GEN(dev_priv) >= 11 && crtc_state->port_clock > 594000) crtc_state->min_voltage_level = 1; else if (IS_CANNONLAKE(dev_priv) && crtc_state->port_clock > 594000) crtc_state->min_voltage_level = 2; @@ -3763,7 +3741,10 @@ void intel_ddi_get_config(struct intel_encoder *encoder, pipe_config->has_hdmi_sink = true; intel_dig_port = enc_to_dig_port(&encoder->base); - if (intel_dig_port->infoframe_enabled(encoder, pipe_config)) + pipe_config->infoframes.enable |= + intel_hdmi_infoframes_enabled(encoder, pipe_config); + + if (pipe_config->infoframes.enable) pipe_config->has_infoframe = true; if (temp & TRANS_DDI_HDMI_SCRAMBLING) @@ -3827,6 +3808,18 @@ void intel_ddi_get_config(struct intel_encoder *encoder, bxt_ddi_phy_get_lane_lat_optim_mask(encoder); intel_ddi_compute_min_voltage_level(dev_priv, pipe_config); + + intel_hdmi_read_gcp_infoframe(encoder, pipe_config); + + intel_read_infoframe(encoder, pipe_config, + HDMI_INFOFRAME_TYPE_AVI, + &pipe_config->infoframes.avi); + intel_read_infoframe(encoder, pipe_config, + HDMI_INFOFRAME_TYPE_SPD, + &pipe_config->infoframes.spd); + intel_read_infoframe(encoder, pipe_config, + HDMI_INFOFRAME_TYPE_VENDOR, + &pipe_config->infoframes.hdmi); } static enum intel_output_type @@ -3855,7 +3848,7 @@ static int intel_ddi_compute_config(struct intel_encoder *encoder, enum port port = encoder->port; int ret; - if (port == PORT_A) + if (HAS_TRANSCODER_EDP(dev_priv) && port == PORT_A) pipe_config->cpu_transcoder = TRANSCODER_EDP; if (intel_crtc_has_type(pipe_config, INTEL_OUTPUT_HDMI)) @@ -3959,15 +3952,7 @@ static int modeset_pipe(struct drm_crtc *crtc, goto out; } - crtc_state->mode_changed = true; - - ret = drm_atomic_add_affected_connectors(state, crtc); - if (ret) - goto out; - - ret = drm_atomic_add_affected_planes(state, crtc); - if (ret) - goto out; + crtc_state->connectors_changed = true; ret = drm_atomic_commit(state); out: |