diff options
Diffstat (limited to 'drivers/gpu/drm/i915/intel_display.c')
-rw-r--r-- | drivers/gpu/drm/i915/intel_display.c | 80 |
1 files changed, 43 insertions, 37 deletions
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 673d91a3e1f2..7335ec2733de 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c | |||
@@ -4337,14 +4337,15 @@ static void i9xx_update_pll_dividers(struct drm_crtc *crtc, | |||
4337 | } | 4337 | } |
4338 | 4338 | ||
4339 | static void vlv_update_pll(struct drm_crtc *crtc, | 4339 | static void vlv_update_pll(struct drm_crtc *crtc, |
4340 | struct drm_display_mode *mode, | ||
4341 | struct drm_display_mode *adjusted_mode, | ||
4342 | intel_clock_t *clock, intel_clock_t *reduced_clock, | 4340 | intel_clock_t *clock, intel_clock_t *reduced_clock, |
4343 | int num_connectors) | 4341 | int num_connectors) |
4344 | { | 4342 | { |
4345 | struct drm_device *dev = crtc->dev; | 4343 | struct drm_device *dev = crtc->dev; |
4346 | struct drm_i915_private *dev_priv = dev->dev_private; | 4344 | struct drm_i915_private *dev_priv = dev->dev_private; |
4347 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); | 4345 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); |
4346 | struct drm_display_mode *adjusted_mode = | ||
4347 | &intel_crtc->config.adjusted_mode; | ||
4348 | struct drm_display_mode *mode = &intel_crtc->config.requested_mode; | ||
4348 | int pipe = intel_crtc->pipe; | 4349 | int pipe = intel_crtc->pipe; |
4349 | u32 dpll, mdiv, pdiv; | 4350 | u32 dpll, mdiv, pdiv; |
4350 | u32 bestn, bestm1, bestm2, bestp1, bestp2; | 4351 | u32 bestn, bestm1, bestm2, bestp1, bestp2; |
@@ -4411,11 +4412,11 @@ static void vlv_update_pll(struct drm_crtc *crtc, | |||
4411 | 4412 | ||
4412 | temp = 0; | 4413 | temp = 0; |
4413 | if (is_sdvo) { | 4414 | if (is_sdvo) { |
4414 | temp = intel_mode_get_pixel_multiplier(adjusted_mode); | 4415 | temp = 0; |
4415 | if (temp > 1) | 4416 | if (intel_crtc->config.pixel_multiplier > 1) { |
4416 | temp = (temp - 1) << DPLL_MD_UDI_MULTIPLIER_SHIFT; | 4417 | temp = (intel_crtc->config.pixel_multiplier - 1) |
4417 | else | 4418 | << DPLL_MD_UDI_MULTIPLIER_SHIFT; |
4418 | temp = 0; | 4419 | } |
4419 | } | 4420 | } |
4420 | I915_WRITE(DPLL_MD(pipe), temp); | 4421 | I915_WRITE(DPLL_MD(pipe), temp); |
4421 | POSTING_READ(DPLL_MD(pipe)); | 4422 | POSTING_READ(DPLL_MD(pipe)); |
@@ -4441,14 +4442,15 @@ static void vlv_update_pll(struct drm_crtc *crtc, | |||
4441 | } | 4442 | } |
4442 | 4443 | ||
4443 | static void i9xx_update_pll(struct drm_crtc *crtc, | 4444 | static void i9xx_update_pll(struct drm_crtc *crtc, |
4444 | struct drm_display_mode *mode, | ||
4445 | struct drm_display_mode *adjusted_mode, | ||
4446 | intel_clock_t *clock, intel_clock_t *reduced_clock, | 4445 | intel_clock_t *clock, intel_clock_t *reduced_clock, |
4447 | int num_connectors) | 4446 | int num_connectors) |
4448 | { | 4447 | { |
4449 | struct drm_device *dev = crtc->dev; | 4448 | struct drm_device *dev = crtc->dev; |
4450 | struct drm_i915_private *dev_priv = dev->dev_private; | 4449 | struct drm_i915_private *dev_priv = dev->dev_private; |
4451 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); | 4450 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); |
4451 | struct drm_display_mode *adjusted_mode = | ||
4452 | &intel_crtc->config.adjusted_mode; | ||
4453 | struct drm_display_mode *mode = &intel_crtc->config.requested_mode; | ||
4452 | struct intel_encoder *encoder; | 4454 | struct intel_encoder *encoder; |
4453 | int pipe = intel_crtc->pipe; | 4455 | int pipe = intel_crtc->pipe; |
4454 | u32 dpll; | 4456 | u32 dpll; |
@@ -4465,11 +4467,12 @@ static void i9xx_update_pll(struct drm_crtc *crtc, | |||
4465 | dpll |= DPLLB_MODE_LVDS; | 4467 | dpll |= DPLLB_MODE_LVDS; |
4466 | else | 4468 | else |
4467 | dpll |= DPLLB_MODE_DAC_SERIAL; | 4469 | dpll |= DPLLB_MODE_DAC_SERIAL; |
4470 | |||
4468 | if (is_sdvo) { | 4471 | if (is_sdvo) { |
4469 | int pixel_multiplier = intel_mode_get_pixel_multiplier(adjusted_mode); | 4472 | if ((intel_crtc->config.pixel_multiplier > 1) && |
4470 | if (pixel_multiplier > 1) { | 4473 | (IS_I945G(dev) || IS_I945GM(dev) || IS_G33(dev))) { |
4471 | if (IS_I945G(dev) || IS_I945GM(dev) || IS_G33(dev)) | 4474 | dpll |= (intel_crtc->config.pixel_multiplier - 1) |
4472 | dpll |= (pixel_multiplier - 1) << SDVO_MULTIPLIER_SHIFT_HIRES; | 4475 | << SDVO_MULTIPLIER_SHIFT_HIRES; |
4473 | } | 4476 | } |
4474 | dpll |= DPLL_DVO_HIGH_SPEED; | 4477 | dpll |= DPLL_DVO_HIGH_SPEED; |
4475 | } | 4478 | } |
@@ -4534,11 +4537,11 @@ static void i9xx_update_pll(struct drm_crtc *crtc, | |||
4534 | if (INTEL_INFO(dev)->gen >= 4) { | 4537 | if (INTEL_INFO(dev)->gen >= 4) { |
4535 | u32 temp = 0; | 4538 | u32 temp = 0; |
4536 | if (is_sdvo) { | 4539 | if (is_sdvo) { |
4537 | temp = intel_mode_get_pixel_multiplier(adjusted_mode); | 4540 | temp = 0; |
4538 | if (temp > 1) | 4541 | if (intel_crtc->config.pixel_multiplier > 1) { |
4539 | temp = (temp - 1) << DPLL_MD_UDI_MULTIPLIER_SHIFT; | 4542 | temp = (intel_crtc->config.pixel_multiplier - 1) |
4540 | else | 4543 | << DPLL_MD_UDI_MULTIPLIER_SHIFT; |
4541 | temp = 0; | 4544 | } |
4542 | } | 4545 | } |
4543 | I915_WRITE(DPLL_MD(pipe), temp); | 4546 | I915_WRITE(DPLL_MD(pipe), temp); |
4544 | } else { | 4547 | } else { |
@@ -4748,11 +4751,11 @@ static int i9xx_crtc_mode_set(struct drm_crtc *crtc, | |||
4748 | has_reduced_clock ? &reduced_clock : NULL, | 4751 | has_reduced_clock ? &reduced_clock : NULL, |
4749 | num_connectors); | 4752 | num_connectors); |
4750 | else if (IS_VALLEYVIEW(dev)) | 4753 | else if (IS_VALLEYVIEW(dev)) |
4751 | vlv_update_pll(crtc, mode, adjusted_mode, &clock, | 4754 | vlv_update_pll(crtc, &clock, |
4752 | has_reduced_clock ? &reduced_clock : NULL, | 4755 | has_reduced_clock ? &reduced_clock : NULL, |
4753 | num_connectors); | 4756 | num_connectors); |
4754 | else | 4757 | else |
4755 | i9xx_update_pll(crtc, mode, adjusted_mode, &clock, | 4758 | i9xx_update_pll(crtc, &clock, |
4756 | has_reduced_clock ? &reduced_clock : NULL, | 4759 | has_reduced_clock ? &reduced_clock : NULL, |
4757 | num_connectors); | 4760 | num_connectors); |
4758 | 4761 | ||
@@ -5466,17 +5469,18 @@ int ironlake_get_lanes_required(int target_clock, int link_bw, int bpp) | |||
5466 | return bps / (link_bw * 8) + 1; | 5469 | return bps / (link_bw * 8) + 1; |
5467 | } | 5470 | } |
5468 | 5471 | ||
5469 | static void ironlake_set_m_n(struct drm_crtc *crtc, | 5472 | static void ironlake_set_m_n(struct drm_crtc *crtc) |
5470 | struct drm_display_mode *mode, | ||
5471 | struct drm_display_mode *adjusted_mode) | ||
5472 | { | 5473 | { |
5473 | struct drm_device *dev = crtc->dev; | 5474 | struct drm_device *dev = crtc->dev; |
5474 | struct drm_i915_private *dev_priv = dev->dev_private; | 5475 | struct drm_i915_private *dev_priv = dev->dev_private; |
5475 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); | 5476 | struct intel_crtc *intel_crtc = to_intel_crtc(crtc); |
5477 | struct drm_display_mode *adjusted_mode = | ||
5478 | &intel_crtc->config.adjusted_mode; | ||
5479 | struct drm_display_mode *mode = &intel_crtc->config.requested_mode; | ||
5476 | enum transcoder cpu_transcoder = intel_crtc->cpu_transcoder; | 5480 | enum transcoder cpu_transcoder = intel_crtc->cpu_transcoder; |
5477 | struct intel_encoder *intel_encoder, *edp_encoder = NULL; | 5481 | struct intel_encoder *intel_encoder, *edp_encoder = NULL; |
5478 | struct intel_link_m_n m_n = {0}; | 5482 | struct intel_link_m_n m_n = {0}; |
5479 | int target_clock, pixel_multiplier, lane, link_bw; | 5483 | int target_clock, lane, link_bw; |
5480 | bool is_dp = false, is_cpu_edp = false; | 5484 | bool is_dp = false, is_cpu_edp = false; |
5481 | 5485 | ||
5482 | for_each_encoder_on_crtc(dev, crtc, intel_encoder) { | 5486 | for_each_encoder_on_crtc(dev, crtc, intel_encoder) { |
@@ -5494,7 +5498,6 @@ static void ironlake_set_m_n(struct drm_crtc *crtc, | |||
5494 | } | 5498 | } |
5495 | 5499 | ||
5496 | /* FDI link */ | 5500 | /* FDI link */ |
5497 | pixel_multiplier = intel_mode_get_pixel_multiplier(adjusted_mode); | ||
5498 | lane = 0; | 5501 | lane = 0; |
5499 | /* CPU eDP doesn't require FDI link, so just set DP M/N | 5502 | /* CPU eDP doesn't require FDI link, so just set DP M/N |
5500 | according to current link config */ | 5503 | according to current link config */ |
@@ -5525,8 +5528,8 @@ static void ironlake_set_m_n(struct drm_crtc *crtc, | |||
5525 | 5528 | ||
5526 | intel_crtc->fdi_lanes = lane; | 5529 | intel_crtc->fdi_lanes = lane; |
5527 | 5530 | ||
5528 | if (pixel_multiplier > 1) | 5531 | if (intel_crtc->config.pixel_multiplier > 1) |
5529 | link_bw *= pixel_multiplier; | 5532 | link_bw *= intel_crtc->config.pixel_multiplier; |
5530 | intel_link_compute_m_n(intel_crtc->bpp, lane, target_clock, link_bw, &m_n); | 5533 | intel_link_compute_m_n(intel_crtc->bpp, lane, target_clock, link_bw, &m_n); |
5531 | 5534 | ||
5532 | I915_WRITE(PIPE_DATA_M1(cpu_transcoder), TU_SIZE(m_n.tu) | m_n.gmch_m); | 5535 | I915_WRITE(PIPE_DATA_M1(cpu_transcoder), TU_SIZE(m_n.tu) | m_n.gmch_m); |
@@ -5536,7 +5539,6 @@ static void ironlake_set_m_n(struct drm_crtc *crtc, | |||
5536 | } | 5539 | } |
5537 | 5540 | ||
5538 | static uint32_t ironlake_compute_dpll(struct intel_crtc *intel_crtc, | 5541 | static uint32_t ironlake_compute_dpll(struct intel_crtc *intel_crtc, |
5539 | struct drm_display_mode *adjusted_mode, | ||
5540 | intel_clock_t *clock, u32 fp) | 5542 | intel_clock_t *clock, u32 fp) |
5541 | { | 5543 | { |
5542 | struct drm_crtc *crtc = &intel_crtc->base; | 5544 | struct drm_crtc *crtc = &intel_crtc->base; |
@@ -5544,7 +5546,7 @@ static uint32_t ironlake_compute_dpll(struct intel_crtc *intel_crtc, | |||
5544 | struct drm_i915_private *dev_priv = dev->dev_private; | 5546 | struct drm_i915_private *dev_priv = dev->dev_private; |
5545 | struct intel_encoder *intel_encoder; | 5547 | struct intel_encoder *intel_encoder; |
5546 | uint32_t dpll; | 5548 | uint32_t dpll; |
5547 | int factor, pixel_multiplier, num_connectors = 0; | 5549 | int factor, num_connectors = 0; |
5548 | bool is_lvds = false, is_sdvo = false, is_tv = false; | 5550 | bool is_lvds = false, is_sdvo = false, is_tv = false; |
5549 | bool is_dp = false, is_cpu_edp = false; | 5551 | bool is_dp = false, is_cpu_edp = false; |
5550 | 5552 | ||
@@ -5595,9 +5597,9 @@ static uint32_t ironlake_compute_dpll(struct intel_crtc *intel_crtc, | |||
5595 | else | 5597 | else |
5596 | dpll |= DPLLB_MODE_DAC_SERIAL; | 5598 | dpll |= DPLLB_MODE_DAC_SERIAL; |
5597 | if (is_sdvo) { | 5599 | if (is_sdvo) { |
5598 | pixel_multiplier = intel_mode_get_pixel_multiplier(adjusted_mode); | 5600 | if (intel_crtc->config.pixel_multiplier > 1) { |
5599 | if (pixel_multiplier > 1) { | 5601 | dpll |= (intel_crtc->config.pixel_multiplier - 1) |
5600 | dpll |= (pixel_multiplier - 1) << PLL_REF_SDVO_HDMI_MULTIPLIER_SHIFT; | 5602 | << PLL_REF_SDVO_HDMI_MULTIPLIER_SHIFT; |
5601 | } | 5603 | } |
5602 | dpll |= DPLL_DVO_HIGH_SPEED; | 5604 | dpll |= DPLL_DVO_HIGH_SPEED; |
5603 | } | 5605 | } |
@@ -5701,7 +5703,7 @@ static int ironlake_crtc_mode_set(struct drm_crtc *crtc, | |||
5701 | fp2 = reduced_clock.n << 16 | reduced_clock.m1 << 8 | | 5703 | fp2 = reduced_clock.n << 16 | reduced_clock.m1 << 8 | |
5702 | reduced_clock.m2; | 5704 | reduced_clock.m2; |
5703 | 5705 | ||
5704 | dpll = ironlake_compute_dpll(intel_crtc, adjusted_mode, &clock, fp); | 5706 | dpll = ironlake_compute_dpll(intel_crtc, &clock, fp); |
5705 | 5707 | ||
5706 | DRM_DEBUG_KMS("Mode for pipe %d:\n", pipe); | 5708 | DRM_DEBUG_KMS("Mode for pipe %d:\n", pipe); |
5707 | drm_mode_debug_printmodeline(mode); | 5709 | drm_mode_debug_printmodeline(mode); |
@@ -5755,7 +5757,7 @@ static int ironlake_crtc_mode_set(struct drm_crtc *crtc, | |||
5755 | 5757 | ||
5756 | /* Note, this also computes intel_crtc->fdi_lanes which is used below in | 5758 | /* Note, this also computes intel_crtc->fdi_lanes which is used below in |
5757 | * ironlake_check_fdi_lanes. */ | 5759 | * ironlake_check_fdi_lanes. */ |
5758 | ironlake_set_m_n(crtc, mode, adjusted_mode); | 5760 | ironlake_set_m_n(crtc); |
5759 | 5761 | ||
5760 | fdi_config_ok = ironlake_check_fdi_lanes(intel_crtc); | 5762 | fdi_config_ok = ironlake_check_fdi_lanes(intel_crtc); |
5761 | 5763 | ||
@@ -5871,7 +5873,7 @@ static int haswell_crtc_mode_set(struct drm_crtc *crtc, | |||
5871 | intel_set_pipe_timings(intel_crtc, mode, adjusted_mode); | 5873 | intel_set_pipe_timings(intel_crtc, mode, adjusted_mode); |
5872 | 5874 | ||
5873 | if (!is_dp || is_cpu_edp) | 5875 | if (!is_dp || is_cpu_edp) |
5874 | ironlake_set_m_n(crtc, mode, adjusted_mode); | 5876 | ironlake_set_m_n(crtc); |
5875 | 5877 | ||
5876 | haswell_set_pipeconf(crtc, adjusted_mode, dither); | 5878 | haswell_set_pipeconf(crtc, adjusted_mode, dither); |
5877 | 5879 | ||
@@ -5924,8 +5926,12 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, | |||
5924 | encoder->base.base.id, | 5926 | encoder->base.base.id, |
5925 | drm_get_encoder_name(&encoder->base), | 5927 | drm_get_encoder_name(&encoder->base), |
5926 | mode->base.id, mode->name); | 5928 | mode->base.id, mode->name); |
5927 | encoder_funcs = encoder->base.helper_private; | 5929 | if (encoder->mode_set) { |
5928 | encoder_funcs->mode_set(&encoder->base, mode, adjusted_mode); | 5930 | encoder->mode_set(encoder); |
5931 | } else { | ||
5932 | encoder_funcs = encoder->base.helper_private; | ||
5933 | encoder_funcs->mode_set(&encoder->base, mode, adjusted_mode); | ||
5934 | } | ||
5929 | } | 5935 | } |
5930 | 5936 | ||
5931 | return 0; | 5937 | return 0; |