diff options
Diffstat (limited to 'drivers/gpu/drm/i915/intel_dp.c')
-rw-r--r-- | drivers/gpu/drm/i915/intel_dp.c | 58 |
1 files changed, 48 insertions, 10 deletions
diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 2d5d9b010073..52fda950fd2a 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c | |||
@@ -123,7 +123,8 @@ intel_dp_max_link_bw(struct intel_dp *intel_dp) | |||
123 | case DP_LINK_BW_2_7: | 123 | case DP_LINK_BW_2_7: |
124 | break; | 124 | break; |
125 | case DP_LINK_BW_5_4: /* 1.2 capable displays may advertise higher bw */ | 125 | case DP_LINK_BW_5_4: /* 1.2 capable displays may advertise higher bw */ |
126 | if ((IS_HASWELL(dev) || INTEL_INFO(dev)->gen >= 8) && | 126 | if (((IS_HASWELL(dev) && !IS_HSW_ULX(dev)) || |
127 | INTEL_INFO(dev)->gen >= 8) && | ||
127 | intel_dp->dpcd[DP_DPCD_REV] >= 0x12) | 128 | intel_dp->dpcd[DP_DPCD_REV] >= 0x12) |
128 | max_link_bw = DP_LINK_BW_5_4; | 129 | max_link_bw = DP_LINK_BW_5_4; |
129 | else | 130 | else |
@@ -138,6 +139,22 @@ intel_dp_max_link_bw(struct intel_dp *intel_dp) | |||
138 | return max_link_bw; | 139 | return max_link_bw; |
139 | } | 140 | } |
140 | 141 | ||
142 | static u8 intel_dp_max_lane_count(struct intel_dp *intel_dp) | ||
143 | { | ||
144 | struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp); | ||
145 | struct drm_device *dev = intel_dig_port->base.base.dev; | ||
146 | u8 source_max, sink_max; | ||
147 | |||
148 | source_max = 4; | ||
149 | if (HAS_DDI(dev) && intel_dig_port->port == PORT_A && | ||
150 | (intel_dig_port->saved_port_bits & DDI_A_4_LANES) == 0) | ||
151 | source_max = 2; | ||
152 | |||
153 | sink_max = drm_dp_max_lane_count(intel_dp->dpcd); | ||
154 | |||
155 | return min(source_max, sink_max); | ||
156 | } | ||
157 | |||
141 | /* | 158 | /* |
142 | * The units on the numbers in the next two are... bizarre. Examples will | 159 | * The units on the numbers in the next two are... bizarre. Examples will |
143 | * make it clearer; this one parallels an example in the eDP spec. | 160 | * make it clearer; this one parallels an example in the eDP spec. |
@@ -188,7 +205,7 @@ intel_dp_mode_valid(struct drm_connector *connector, | |||
188 | } | 205 | } |
189 | 206 | ||
190 | max_link_clock = drm_dp_bw_code_to_link_rate(intel_dp_max_link_bw(intel_dp)); | 207 | max_link_clock = drm_dp_bw_code_to_link_rate(intel_dp_max_link_bw(intel_dp)); |
191 | max_lanes = drm_dp_max_lane_count(intel_dp->dpcd); | 208 | max_lanes = intel_dp_max_lane_count(intel_dp); |
192 | 209 | ||
193 | max_rate = intel_dp_max_data_rate(max_link_clock, max_lanes); | 210 | max_rate = intel_dp_max_data_rate(max_link_clock, max_lanes); |
194 | mode_rate = intel_dp_link_required(target_clock, 18); | 211 | mode_rate = intel_dp_link_required(target_clock, 18); |
@@ -789,8 +806,10 @@ intel_dp_compute_config(struct intel_encoder *encoder, | |||
789 | struct intel_crtc *intel_crtc = encoder->new_crtc; | 806 | struct intel_crtc *intel_crtc = encoder->new_crtc; |
790 | struct intel_connector *intel_connector = intel_dp->attached_connector; | 807 | struct intel_connector *intel_connector = intel_dp->attached_connector; |
791 | int lane_count, clock; | 808 | int lane_count, clock; |
792 | int max_lane_count = drm_dp_max_lane_count(intel_dp->dpcd); | 809 | int min_lane_count = 1; |
810 | int max_lane_count = intel_dp_max_lane_count(intel_dp); | ||
793 | /* Conveniently, the link BW constants become indices with a shift...*/ | 811 | /* Conveniently, the link BW constants become indices with a shift...*/ |
812 | int min_clock = 0; | ||
794 | int max_clock = intel_dp_max_link_bw(intel_dp) >> 3; | 813 | int max_clock = intel_dp_max_link_bw(intel_dp) >> 3; |
795 | int bpp, mode_rate; | 814 | int bpp, mode_rate; |
796 | static int bws[] = { DP_LINK_BW_1_62, DP_LINK_BW_2_7, DP_LINK_BW_5_4 }; | 815 | static int bws[] = { DP_LINK_BW_1_62, DP_LINK_BW_2_7, DP_LINK_BW_5_4 }; |
@@ -824,19 +843,38 @@ intel_dp_compute_config(struct intel_encoder *encoder, | |||
824 | /* Walk through all bpp values. Luckily they're all nicely spaced with 2 | 843 | /* Walk through all bpp values. Luckily they're all nicely spaced with 2 |
825 | * bpc in between. */ | 844 | * bpc in between. */ |
826 | bpp = pipe_config->pipe_bpp; | 845 | bpp = pipe_config->pipe_bpp; |
827 | if (is_edp(intel_dp) && dev_priv->vbt.edp_bpp && | 846 | if (is_edp(intel_dp)) { |
828 | dev_priv->vbt.edp_bpp < bpp) { | 847 | if (dev_priv->vbt.edp_bpp && dev_priv->vbt.edp_bpp < bpp) { |
829 | DRM_DEBUG_KMS("clamping bpp for eDP panel to BIOS-provided %i\n", | 848 | DRM_DEBUG_KMS("clamping bpp for eDP panel to BIOS-provided %i\n", |
830 | dev_priv->vbt.edp_bpp); | 849 | dev_priv->vbt.edp_bpp); |
831 | bpp = dev_priv->vbt.edp_bpp; | 850 | bpp = dev_priv->vbt.edp_bpp; |
851 | } | ||
852 | |||
853 | if (IS_BROADWELL(dev)) { | ||
854 | /* Yes, it's an ugly hack. */ | ||
855 | min_lane_count = max_lane_count; | ||
856 | DRM_DEBUG_KMS("forcing lane count to max (%u) on BDW\n", | ||
857 | min_lane_count); | ||
858 | } else if (dev_priv->vbt.edp_lanes) { | ||
859 | min_lane_count = min(dev_priv->vbt.edp_lanes, | ||
860 | max_lane_count); | ||
861 | DRM_DEBUG_KMS("using min %u lanes per VBT\n", | ||
862 | min_lane_count); | ||
863 | } | ||
864 | |||
865 | if (dev_priv->vbt.edp_rate) { | ||
866 | min_clock = min(dev_priv->vbt.edp_rate >> 3, max_clock); | ||
867 | DRM_DEBUG_KMS("using min %02x link bw per VBT\n", | ||
868 | bws[min_clock]); | ||
869 | } | ||
832 | } | 870 | } |
833 | 871 | ||
834 | for (; bpp >= 6*3; bpp -= 2*3) { | 872 | for (; bpp >= 6*3; bpp -= 2*3) { |
835 | mode_rate = intel_dp_link_required(adjusted_mode->crtc_clock, | 873 | mode_rate = intel_dp_link_required(adjusted_mode->crtc_clock, |
836 | bpp); | 874 | bpp); |
837 | 875 | ||
838 | for (lane_count = 1; lane_count <= max_lane_count; lane_count <<= 1) { | 876 | for (lane_count = min_lane_count; lane_count <= max_lane_count; lane_count <<= 1) { |
839 | for (clock = 0; clock <= max_clock; clock++) { | 877 | for (clock = min_clock; clock <= max_clock; clock++) { |
840 | link_clock = drm_dp_bw_code_to_link_rate(bws[clock]); | 878 | link_clock = drm_dp_bw_code_to_link_rate(bws[clock]); |
841 | link_avail = intel_dp_max_data_rate(link_clock, | 879 | link_avail = intel_dp_max_data_rate(link_clock, |
842 | lane_count); | 880 | lane_count); |