From mboxrd@z Thu Jan 1 00:00:00 1970 From: Eugeni Dodonov Subject: [PATCH 16/21] drm/i915: Modesetting for eDP on HSw Date: Thu, 28 Jun 2012 15:55:44 -0300 Message-ID: <1340909749-15249-17-git-send-email-eugeni.dodonov@intel.com> References: <1340909749-15249-1-git-send-email-eugeni.dodonov@intel.com> Mime-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Return-path: Received: from mga09.intel.com (mga09.intel.com [134.134.136.24]) by gabe.freedesktop.org (Postfix) with ESMTP id AABD8A0A3B for ; Thu, 28 Jun 2012 11:54:47 -0700 (PDT) In-Reply-To: <1340909749-15249-1-git-send-email-eugeni.dodonov@intel.com> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: intel-gfx-bounces+gcfxdi-intel-gfx=m.gmane.org@lists.freedesktop.org Errors-To: intel-gfx-bounces+gcfxdi-intel-gfx=m.gmane.org@lists.freedesktop.org To: intel-gfx@lists.freedesktop.org Cc: Eugeni Dodonov List-Id: intel-gfx@lists.freedesktop.org From: Shobhit Kumar The MSA register and PIPE EDP register are differnet than that of DP. Also link training flow though similar for DP had been corrected to follow DP path Signed-off-by: Shobhit Kumar Signed-off-by: Sateesh Kavuri Signed-off-by: Eugeni Dodonov --- drivers/gpu/drm/i915/i915_reg.h | 1 + drivers/gpu/drm/i915/intel_ddi.c | 70 ++++++++++++++++++++++++++++------------ drivers/gpu/drm/i915/intel_dp.c | 8 ++--- drivers/gpu/drm/i915/intel_drv.h | 1 + 4 files changed, 55 insertions(+), 25 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 1e70fae..1165d2e 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h @@ -4316,6 +4316,7 @@ #define PIPE_DDI_MODE_SELECT_DP_SST (2<<24) #define PIPE_DDI_MODE_SELECT_DP_MST (3<<24) #define PIPE_DDI_MODE_SELECT_FDI (4<<24) +#define PIPE_DDI_BPC_MASK (0x7<<20) #define PIPE_DDI_BPC_8 (0<<20) #define PIPE_DDI_BPC_10 (1<<20) #define PIPE_DDI_BPC_6 (2<<20) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 1c76d20..9d09f38 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -756,22 +756,16 @@ intel_ddi_mode_set_dp(struct drm_encoder *encoder, int port = intel_dp->ddi_port; int pipe = intel_crtc->pipe; int port_width = PIPE_DDI_PORT_WIDTH_X1; - int temp; + int temp, reg; DRM_DEBUG_KMS("Preparing DP DDI mode for Haswell on port %c, pipe %c\n", port_name(port), pipe_name(pipe)); - /* Turn on the eDP PLL if needed */ - /* TBD: */ - /* * There are two kinds of DP registers in HSW: * DDI CPU * LPT PCH */ - /* Preserve the BIOS-computed detected bit. This is - * supposed to be read-only. - */ intel_dp->DP = I915_READ(DDI_BUF_CTL(intel_dp->ddi_port)); intel_dp->DP |= DDI_BUF_EMP_400MV_0DB_HSW; intel_dp->TP = I915_READ(DP_TP_CTL(intel_dp->ddi_port)); @@ -794,6 +788,10 @@ intel_ddi_mode_set_dp(struct drm_encoder *encoder, BUG(); } + /* Assuming all 4 lanes available to DDI A for eDP */ + if (is_edp(intel_dp)) + intel_dp->DP |= DDI_PORT_LANE_CAP_DDIA_4; + if (intel_dp->has_audio) DRM_DEBUG_DRIVER("HSW DP Audio not yet supported\n"); @@ -830,14 +828,24 @@ intel_ddi_mode_set_dp(struct drm_encoder *encoder, /* Set the MSA bits, since from HSW onwards, * this has to be explictly set */ - temp = I915_READ(HSW_MSA_CTL); + if (is_edp(intel_dp)) + temp = I915_READ(HSW_MSA_EDP_CTL); + else + temp = I915_READ(HSW_MSA_CTL); + temp |= HSW_MSA_SYNC_CLK; temp &= ~HSW_MSA_DYNAMIC_RANGE; temp &= ~HSW_MSA_COLORIMETRY; temp &= ~HSW_MSA_BPC_MASK; - temp |= HSW_MSA_BPC_8_BITS; /* Color depth */ - I915_WRITE(HSW_MSA_CTL, temp); + if (is_edp(intel_dp)) { + temp |= HSW_MSA_BPC_6_BITS; /* Color depth */ + I915_WRITE(HSW_MSA_EDP_CTL, temp); + } + else { + temp |= HSW_MSA_BPC_8_BITS; /* Color depth */ + I915_WRITE(HSW_MSA_CTL, temp); + } if ((intel_dp->dpcd[DP_MAX_DOWNSPREAD] & 0x1) == 0x1) { /* SSC Enabled Panel */ @@ -854,8 +862,9 @@ intel_ddi_mode_set_dp(struct drm_encoder *encoder, */ I915_WRITE(PORT_CLK_SEL(port), PORT_CLK_SEL_SPLL); - I915_WRITE(PIPE_CLK_SEL(pipe), - PIPE_CLK_SEL_PORT(port)); + if (!is_edp(intel_dp)) + I915_WRITE(PIPE_CLK_SEL(pipe), + PIPE_CLK_SEL_PORT(port)); } else { /* Non SSC Panel */ /* configure LCPLL for NON-SSC */ @@ -864,30 +873,49 @@ intel_ddi_mode_set_dp(struct drm_encoder *encoder, LCPLL_PLL_REFERENCE_NON_SSC; I915_WRITE(LCPLL_CTL, temp); udelay(20); - /* Use LCPLL clock to drive the output to the dp port, * and tell the pipe to use this port for connection. */ I915_WRITE(PORT_CLK_SEL(port), PORT_CLK_SEL_LCPLL_1350); - I915_WRITE(PIPE_CLK_SEL(pipe), - PIPE_CLK_SEL_PORT(port)); + if (!is_edp(intel_dp)) + I915_WRITE(PIPE_CLK_SEL(pipe), + PIPE_CLK_SEL_PORT(port)); } /* Enable PIPE_DDI_FUNC_CTL for the pipe to work in DP mode */ - temp = I915_READ(DDI_FUNC_CTL(pipe)); + if(is_edp(intel_dp)) { + reg = PIPE_DDI_FUNC_CTL_EDP; + temp = I915_READ(reg); + temp &= ~PIPE_DDI_EDP_INPUT_SRC_MASK ; + + /* Use On/Off for now to address all cases; later we + * need to also add support for always on without panel + * fitter in case of native mode to save power + */ + temp &= ~PIPE_DDI_BPC_MASK; + temp |= PIPE_DDI_EDI_INPUT_SRC_A_ON_OFF; + temp |= ((intel_crtc->bpp > 24) ? + PIPE_DDI_BPC_12 : + PIPE_DDI_BPC_6); + } + else { + reg = DDI_FUNC_CTL(pipe); + temp = I915_READ(reg); + temp &= ~PIPE_DDI_BPC_MASK; + temp |= ((intel_crtc->bpp > 24) ? + PIPE_DDI_BPC_12 : + PIPE_DDI_BPC_8); + } + temp &= ~PIPE_DDI_PORT_MASK; - temp &= ~PIPE_DDI_BPC_12; temp &= ~PIPE_DDI_PORT_WIDTH_MASK; temp |= PIPE_DDI_SELECT_PORT(port) | PIPE_DDI_MODE_SELECT_DP_SST | port_width | - ((intel_crtc->bpp > 24) ? - PIPE_DDI_BPC_12 : - PIPE_DDI_BPC_8) | PIPE_DDI_FUNC_ENABLE; - I915_WRITE(DDI_FUNC_CTL(pipe), temp); + I915_WRITE(reg, temp); } } diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 38a1d3b..f086944 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -45,7 +45,7 @@ * If a CPU or PCH DP output is attached to an eDP panel, this function * will return true, and false otherwise. */ -static bool is_edp(struct intel_dp *intel_dp) +bool is_edp(struct intel_dp *intel_dp) { return intel_dp->base.type == INTEL_OUTPUT_EDP; } @@ -363,7 +363,7 @@ intel_dp_aux_ch(struct intel_dp *intel_dp, * clock divider. */ if (is_cpu_edp(intel_dp)) { - if (IS_GEN6(dev) || IS_GEN7(dev)) + if ((IS_GEN6(dev) || IS_GEN7(dev)) && !IS_HASWELL(dev)) aux_clock_divider = 200; /* SNB & IVB eDP input clock at 400Mhz */ else aux_clock_divider = 225; /* eDP input clock at 450Mhz */ @@ -1753,7 +1753,7 @@ intel_dp_start_link_train(struct intel_dp *intel_dp) uint32_t signal_levels; - if (IS_GEN7(dev) && is_cpu_edp(intel_dp)) { + if (IS_GEN7(dev) && is_cpu_edp(intel_dp) && !IS_HASWELL(dev)) { signal_levels = intel_gen7_edp_signal_levels(intel_dp->train_set[0]); DP = (DP & ~EDP_LINK_TRAIN_VOL_EMP_MASK_IVB) | signal_levels; } else if (IS_GEN6(dev) && is_cpu_edp(intel_dp)) { @@ -1855,7 +1855,7 @@ intel_dp_complete_link_train(struct intel_dp *intel_dp) break; } - if (IS_GEN7(dev) && is_cpu_edp(intel_dp)) { + if (IS_GEN7(dev) && is_cpu_edp(intel_dp) && !IS_HASWELL(dev)) { signal_levels = intel_gen7_edp_signal_levels(intel_dp->train_set[0]); DP = (DP & ~EDP_LINK_TRAIN_VOL_EMP_MASK_IVB) | signal_levels; } else if (IS_GEN6(dev) && is_cpu_edp(intel_dp)) { diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index 5ca133d..a741a02 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -392,6 +392,7 @@ extern void intel_mark_busy(struct drm_device *dev, extern bool intel_lvds_init(struct drm_device *dev); extern void intel_dp_init(struct drm_device *dev, int dp_reg); extern struct intel_dp *enc_to_intel_dp(struct drm_encoder *encoder); +extern bool is_edp(struct intel_dp *intel_dp); void intel_dp_set_m_n(struct drm_crtc *crtc, struct drm_display_mode *mode, -- 1.7.11.1