aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/i915/intel_ddi.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/i915/intel_ddi.c')
-rw-r--r--drivers/gpu/drm/i915/intel_ddi.c251
1 files changed, 203 insertions, 48 deletions
diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c
index b53fff84a7d5..1591576a6101 100644
--- a/drivers/gpu/drm/i915/intel_ddi.c
+++ b/drivers/gpu/drm/i915/intel_ddi.c
@@ -42,7 +42,6 @@ static const u32 hsw_ddi_translations_dp[] = {
42 0x80C30FFF, 0x000B0000, 42 0x80C30FFF, 0x000B0000,
43 0x00FFFFFF, 0x00040006, 43 0x00FFFFFF, 0x00040006,
44 0x80D75FFF, 0x000B0000, 44 0x80D75FFF, 0x000B0000,
45 0x00FFFFFF, 0x00040006 /* HDMI parameters */
46}; 45};
47 46
48static const u32 hsw_ddi_translations_fdi[] = { 47static const u32 hsw_ddi_translations_fdi[] = {
@@ -55,10 +54,64 @@ static const u32 hsw_ddi_translations_fdi[] = {
55 0x00C30FFF, 0x001E0000, 54 0x00C30FFF, 0x001E0000,
56 0x00FFFFFF, 0x00060006, 55 0x00FFFFFF, 0x00060006,
57 0x00D75FFF, 0x001E0000, 56 0x00D75FFF, 0x001E0000,
58 0x00FFFFFF, 0x00040006 /* HDMI parameters */
59}; 57};
60 58
61static enum port intel_ddi_get_encoder_port(struct intel_encoder *intel_encoder) 59static const u32 hsw_ddi_translations_hdmi[] = {
60 /* Idx NT mV diff T mV diff db */
61 0x00FFFFFF, 0x0006000E, /* 0: 400 400 0 */
62 0x00E79FFF, 0x000E000C, /* 1: 400 500 2 */
63 0x00D75FFF, 0x0005000A, /* 2: 400 600 3.5 */
64 0x00FFFFFF, 0x0005000A, /* 3: 600 600 0 */
65 0x00E79FFF, 0x001D0007, /* 4: 600 750 2 */
66 0x00D75FFF, 0x000C0004, /* 5: 600 900 3.5 */
67 0x00FFFFFF, 0x00040006, /* 6: 800 800 0 */
68 0x80E79FFF, 0x00030002, /* 7: 800 1000 2 */
69 0x00FFFFFF, 0x00140005, /* 8: 850 850 0 */
70 0x00FFFFFF, 0x000C0004, /* 9: 900 900 0 */
71 0x00FFFFFF, 0x001C0003, /* 10: 950 950 0 */
72 0x80FFFFFF, 0x00030002, /* 11: 1000 1000 0 */
73};
74
75static const u32 bdw_ddi_translations_edp[] = {
76 0x00FFFFFF, 0x00000012, /* DP parameters */
77 0x00EBAFFF, 0x00020011,
78 0x00C71FFF, 0x0006000F,
79 0x00FFFFFF, 0x00020011,
80 0x00DB6FFF, 0x0005000F,
81 0x00BEEFFF, 0x000A000C,
82 0x00FFFFFF, 0x0005000F,
83 0x00DB6FFF, 0x000A000C,
84 0x00FFFFFF, 0x000A000C,
85 0x00FFFFFF, 0x00140006 /* HDMI parameters 800mV 0dB*/
86};
87
88static const u32 bdw_ddi_translations_dp[] = {
89 0x00FFFFFF, 0x0007000E, /* DP parameters */
90 0x00D75FFF, 0x000E000A,
91 0x00BEFFFF, 0x00140006,
92 0x00FFFFFF, 0x000E000A,
93 0x00D75FFF, 0x00180004,
94 0x80CB2FFF, 0x001B0002,
95 0x00F7DFFF, 0x00180004,
96 0x80D75FFF, 0x001B0002,
97 0x80FFFFFF, 0x001B0002,
98 0x00FFFFFF, 0x00140006 /* HDMI parameters 800mV 0dB*/
99};
100
101static const u32 bdw_ddi_translations_fdi[] = {
102 0x00FFFFFF, 0x0001000E, /* FDI parameters */
103 0x00D75FFF, 0x0004000A,
104 0x00C30FFF, 0x00070006,
105 0x00AAAFFF, 0x000C0000,
106 0x00FFFFFF, 0x0004000A,
107 0x00D75FFF, 0x00090004,
108 0x00C30FFF, 0x000C0000,
109 0x00FFFFFF, 0x00070006,
110 0x00D75FFF, 0x000C0000,
111 0x00FFFFFF, 0x00140006 /* HDMI parameters 800mV 0dB*/
112};
113
114enum port intel_ddi_get_encoder_port(struct intel_encoder *intel_encoder)
62{ 115{
63 struct drm_encoder *encoder = &intel_encoder->base; 116 struct drm_encoder *encoder = &intel_encoder->base;
64 int type = intel_encoder->type; 117 int type = intel_encoder->type;
@@ -78,8 +131,9 @@ static enum port intel_ddi_get_encoder_port(struct intel_encoder *intel_encoder)
78 } 131 }
79} 132}
80 133
81/* On Haswell, DDI port buffers must be programmed with correct values 134/*
82 * in advance. The buffer values are different for FDI and DP modes, 135 * Starting with Haswell, DDI port buffers must be programmed with correct
136 * values in advance. The buffer values are different for FDI and DP modes,
83 * but the HDMI/DVI fields are shared among those. So we program the DDI 137 * but the HDMI/DVI fields are shared among those. So we program the DDI
84 * in either FDI or DP modes only, as HDMI connections will work with both 138 * in either FDI or DP modes only, as HDMI connections will work with both
85 * of those 139 * of those
@@ -89,15 +143,58 @@ static void intel_prepare_ddi_buffers(struct drm_device *dev, enum port port)
89 struct drm_i915_private *dev_priv = dev->dev_private; 143 struct drm_i915_private *dev_priv = dev->dev_private;
90 u32 reg; 144 u32 reg;
91 int i; 145 int i;
92 const u32 *ddi_translations = (port == PORT_E) ? 146 int hdmi_level = dev_priv->vbt.ddi_port_info[port].hdmi_level_shift;
93 hsw_ddi_translations_fdi : 147 const u32 *ddi_translations_fdi;
94 hsw_ddi_translations_dp; 148 const u32 *ddi_translations_dp;
149 const u32 *ddi_translations_edp;
150 const u32 *ddi_translations;
151
152 if (IS_BROADWELL(dev)) {
153 ddi_translations_fdi = bdw_ddi_translations_fdi;
154 ddi_translations_dp = bdw_ddi_translations_dp;
155 ddi_translations_edp = bdw_ddi_translations_edp;
156 } else if (IS_HASWELL(dev)) {
157 ddi_translations_fdi = hsw_ddi_translations_fdi;
158 ddi_translations_dp = hsw_ddi_translations_dp;
159 ddi_translations_edp = hsw_ddi_translations_dp;
160 } else {
161 WARN(1, "ddi translation table missing\n");
162 ddi_translations_edp = bdw_ddi_translations_dp;
163 ddi_translations_fdi = bdw_ddi_translations_fdi;
164 ddi_translations_dp = bdw_ddi_translations_dp;
165 }
166
167 switch (port) {
168 case PORT_A:
169 ddi_translations = ddi_translations_edp;
170 break;
171 case PORT_B:
172 case PORT_C:
173 ddi_translations = ddi_translations_dp;
174 break;
175 case PORT_D:
176 if (intel_dpd_is_edp(dev))
177 ddi_translations = ddi_translations_edp;
178 else
179 ddi_translations = ddi_translations_dp;
180 break;
181 case PORT_E:
182 ddi_translations = ddi_translations_fdi;
183 break;
184 default:
185 BUG();
186 }
95 187
96 for (i = 0, reg = DDI_BUF_TRANS(port); 188 for (i = 0, reg = DDI_BUF_TRANS(port);
97 i < ARRAY_SIZE(hsw_ddi_translations_fdi); i++) { 189 i < ARRAY_SIZE(hsw_ddi_translations_fdi); i++) {
98 I915_WRITE(reg, ddi_translations[i]); 190 I915_WRITE(reg, ddi_translations[i]);
99 reg += 4; 191 reg += 4;
100 } 192 }
193 /* Entry 9 is for HDMI: */
194 for (i = 0; i < 2; i++) {
195 I915_WRITE(reg, hsw_ddi_translations_hdmi[hdmi_level * 2 + i]);
196 reg += 4;
197 }
101} 198}
102 199
103/* Program DDI buffers translations for DP. By default, program ports A-D in DP 200/* Program DDI buffers translations for DP. By default, program ports A-D in DP
@@ -296,9 +393,6 @@ static void intel_ddi_mode_set(struct intel_encoder *encoder)
296 DRM_DEBUG_DRIVER("DP audio: write eld information\n"); 393 DRM_DEBUG_DRIVER("DP audio: write eld information\n");
297 intel_write_eld(&encoder->base, adjusted_mode); 394 intel_write_eld(&encoder->base, adjusted_mode);
298 } 395 }
299
300 intel_dp_init_link_config(intel_dp);
301
302 } else if (type == INTEL_OUTPUT_HDMI) { 396 } else if (type == INTEL_OUTPUT_HDMI) {
303 struct intel_hdmi *intel_hdmi = enc_to_intel_hdmi(&encoder->base); 397 struct intel_hdmi *intel_hdmi = enc_to_intel_hdmi(&encoder->base);
304 398
@@ -739,7 +833,8 @@ void intel_ddi_enable_transcoder_func(struct drm_crtc *crtc)
739 struct intel_crtc *intel_crtc = to_intel_crtc(crtc); 833 struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
740 struct intel_encoder *intel_encoder = intel_ddi_get_crtc_encoder(crtc); 834 struct intel_encoder *intel_encoder = intel_ddi_get_crtc_encoder(crtc);
741 struct drm_encoder *encoder = &intel_encoder->base; 835 struct drm_encoder *encoder = &intel_encoder->base;
742 struct drm_i915_private *dev_priv = crtc->dev->dev_private; 836 struct drm_device *dev = crtc->dev;
837 struct drm_i915_private *dev_priv = dev->dev_private;
743 enum pipe pipe = intel_crtc->pipe; 838 enum pipe pipe = intel_crtc->pipe;
744 enum transcoder cpu_transcoder = intel_crtc->config.cpu_transcoder; 839 enum transcoder cpu_transcoder = intel_crtc->config.cpu_transcoder;
745 enum port port = intel_ddi_get_encoder_port(intel_encoder); 840 enum port port = intel_ddi_get_encoder_port(intel_encoder);
@@ -767,18 +862,19 @@ void intel_ddi_enable_transcoder_func(struct drm_crtc *crtc)
767 BUG(); 862 BUG();
768 } 863 }
769 864
770 if (crtc->mode.flags & DRM_MODE_FLAG_PVSYNC) 865 if (intel_crtc->config.adjusted_mode.flags & DRM_MODE_FLAG_PVSYNC)
771 temp |= TRANS_DDI_PVSYNC; 866 temp |= TRANS_DDI_PVSYNC;
772 if (crtc->mode.flags & DRM_MODE_FLAG_PHSYNC) 867 if (intel_crtc->config.adjusted_mode.flags & DRM_MODE_FLAG_PHSYNC)
773 temp |= TRANS_DDI_PHSYNC; 868 temp |= TRANS_DDI_PHSYNC;
774 869
775 if (cpu_transcoder == TRANSCODER_EDP) { 870 if (cpu_transcoder == TRANSCODER_EDP) {
776 switch (pipe) { 871 switch (pipe) {
777 case PIPE_A: 872 case PIPE_A:
778 /* Can only use the always-on power well for eDP when 873 /* On Haswell, can only use the always-on power well for
779 * not using the panel fitter, and when not using motion 874 * eDP when not using the panel fitter, and when not
780 * blur mitigation (which we don't support). */ 875 * using motion blur mitigation (which we don't
781 if (intel_crtc->config.pch_pfit.enabled) 876 * support). */
877 if (IS_HASWELL(dev) && intel_crtc->config.pch_pfit.enabled)
782 temp |= TRANS_DDI_EDP_INPUT_A_ONOFF; 878 temp |= TRANS_DDI_EDP_INPUT_A_ONOFF;
783 else 879 else
784 temp |= TRANS_DDI_EDP_INPUT_A_ON; 880 temp |= TRANS_DDI_EDP_INPUT_A_ON;
@@ -1139,18 +1235,29 @@ static void intel_disable_ddi(struct intel_encoder *intel_encoder)
1139 1235
1140int intel_ddi_get_cdclk_freq(struct drm_i915_private *dev_priv) 1236int intel_ddi_get_cdclk_freq(struct drm_i915_private *dev_priv)
1141{ 1237{
1238 struct drm_device *dev = dev_priv->dev;
1142 uint32_t lcpll = I915_READ(LCPLL_CTL); 1239 uint32_t lcpll = I915_READ(LCPLL_CTL);
1240 uint32_t freq = lcpll & LCPLL_CLK_FREQ_MASK;
1143 1241
1144 if (lcpll & LCPLL_CD_SOURCE_FCLK) 1242 if (lcpll & LCPLL_CD_SOURCE_FCLK) {
1145 return 800000; 1243 return 800000;
1146 else if (I915_READ(HSW_FUSE_STRAP) & HSW_CDCLK_LIMIT) 1244 } else if (I915_READ(HSW_FUSE_STRAP) & HSW_CDCLK_LIMIT) {
1147 return 450000; 1245 return 450000;
1148 else if ((lcpll & LCPLL_CLK_FREQ_MASK) == LCPLL_CLK_FREQ_450) 1246 } else if (freq == LCPLL_CLK_FREQ_450) {
1149 return 450000; 1247 return 450000;
1150 else if (IS_ULT(dev_priv->dev)) 1248 } else if (IS_HASWELL(dev)) {
1151 return 337500; 1249 if (IS_ULT(dev))
1152 else 1250 return 337500;
1153 return 540000; 1251 else
1252 return 540000;
1253 } else {
1254 if (freq == LCPLL_CLK_FREQ_54O_BDW)
1255 return 540000;
1256 else if (freq == LCPLL_CLK_FREQ_337_5_BDW)
1257 return 337500;
1258 else
1259 return 675000;
1260 }
1154} 1261}
1155 1262
1156void intel_ddi_pll_init(struct drm_device *dev) 1263void intel_ddi_pll_init(struct drm_device *dev)
@@ -1202,7 +1309,7 @@ void intel_ddi_prepare_link_retrain(struct drm_encoder *encoder)
1202 1309
1203 val = DP_TP_CTL_ENABLE | DP_TP_CTL_MODE_SST | 1310 val = DP_TP_CTL_ENABLE | DP_TP_CTL_MODE_SST |
1204 DP_TP_CTL_LINK_TRAIN_PAT1 | DP_TP_CTL_SCRAMBLE_DISABLE; 1311 DP_TP_CTL_LINK_TRAIN_PAT1 | DP_TP_CTL_SCRAMBLE_DISABLE;
1205 if (intel_dp->link_configuration[1] & DP_LANE_COUNT_ENHANCED_FRAME_EN) 1312 if (drm_dp_enhanced_frame_cap(intel_dp->dpcd))
1206 val |= DP_TP_CTL_ENHANCED_FRAME_ENABLE; 1313 val |= DP_TP_CTL_ENHANCED_FRAME_ENABLE;
1207 I915_WRITE(DP_TP_CTL(port), val); 1314 I915_WRITE(DP_TP_CTL(port), val);
1208 POSTING_READ(DP_TP_CTL(port)); 1315 POSTING_READ(DP_TP_CTL(port));
@@ -1285,6 +1392,20 @@ void intel_ddi_get_config(struct intel_encoder *encoder,
1285 default: 1392 default:
1286 break; 1393 break;
1287 } 1394 }
1395
1396 switch (temp & TRANS_DDI_MODE_SELECT_MASK) {
1397 case TRANS_DDI_MODE_SELECT_HDMI:
1398 case TRANS_DDI_MODE_SELECT_DVI:
1399 case TRANS_DDI_MODE_SELECT_FDI:
1400 break;
1401 case TRANS_DDI_MODE_SELECT_DP_SST:
1402 case TRANS_DDI_MODE_SELECT_DP_MST:
1403 pipe_config->has_dp_encoder = true;
1404 intel_dp_get_m_n(intel_crtc, pipe_config);
1405 break;
1406 default:
1407 break;
1408 }
1288} 1409}
1289 1410
1290static void intel_ddi_destroy(struct drm_encoder *encoder) 1411static void intel_ddi_destroy(struct drm_encoder *encoder)
@@ -1314,6 +1435,41 @@ static const struct drm_encoder_funcs intel_ddi_funcs = {
1314 .destroy = intel_ddi_destroy, 1435 .destroy = intel_ddi_destroy,
1315}; 1436};
1316 1437
1438static struct intel_connector *
1439intel_ddi_init_dp_connector(struct intel_digital_port *intel_dig_port)
1440{
1441 struct intel_connector *connector;
1442 enum port port = intel_dig_port->port;
1443
1444 connector = kzalloc(sizeof(*connector), GFP_KERNEL);
1445 if (!connector)
1446 return NULL;
1447
1448 intel_dig_port->dp.output_reg = DDI_BUF_CTL(port);
1449 if (!intel_dp_init_connector(intel_dig_port, connector)) {
1450 kfree(connector);
1451 return NULL;
1452 }
1453
1454 return connector;
1455}
1456
1457static struct intel_connector *
1458intel_ddi_init_hdmi_connector(struct intel_digital_port *intel_dig_port)
1459{
1460 struct intel_connector *connector;
1461 enum port port = intel_dig_port->port;
1462
1463 connector = kzalloc(sizeof(*connector), GFP_KERNEL);
1464 if (!connector)
1465 return NULL;
1466
1467 intel_dig_port->hdmi.hdmi_reg = DDI_BUF_CTL(port);
1468 intel_hdmi_init_connector(intel_dig_port, connector);
1469
1470 return connector;
1471}
1472
1317void intel_ddi_init(struct drm_device *dev, enum port port) 1473void intel_ddi_init(struct drm_device *dev, enum port port)
1318{ 1474{
1319 struct drm_i915_private *dev_priv = dev->dev_private; 1475 struct drm_i915_private *dev_priv = dev->dev_private;
@@ -1322,17 +1478,22 @@ void intel_ddi_init(struct drm_device *dev, enum port port)
1322 struct drm_encoder *encoder; 1478 struct drm_encoder *encoder;
1323 struct intel_connector *hdmi_connector = NULL; 1479 struct intel_connector *hdmi_connector = NULL;
1324 struct intel_connector *dp_connector = NULL; 1480 struct intel_connector *dp_connector = NULL;
1481 bool init_hdmi, init_dp;
1482
1483 init_hdmi = (dev_priv->vbt.ddi_port_info[port].supports_dvi ||
1484 dev_priv->vbt.ddi_port_info[port].supports_hdmi);
1485 init_dp = dev_priv->vbt.ddi_port_info[port].supports_dp;
1486 if (!init_dp && !init_hdmi) {
1487 DRM_DEBUG_KMS("VBT says port %c is not DVI/HDMI/DP compatible\n",
1488 port_name(port));
1489 init_hdmi = true;
1490 init_dp = true;
1491 }
1325 1492
1326 intel_dig_port = kzalloc(sizeof(struct intel_digital_port), GFP_KERNEL); 1493 intel_dig_port = kzalloc(sizeof(*intel_dig_port), GFP_KERNEL);
1327 if (!intel_dig_port) 1494 if (!intel_dig_port)
1328 return; 1495 return;
1329 1496
1330 dp_connector = kzalloc(sizeof(struct intel_connector), GFP_KERNEL);
1331 if (!dp_connector) {
1332 kfree(intel_dig_port);
1333 return;
1334 }
1335
1336 intel_encoder = &intel_dig_port->base; 1497 intel_encoder = &intel_dig_port->base;
1337 encoder = &intel_encoder->base; 1498 encoder = &intel_encoder->base;
1338 1499
@@ -1352,28 +1513,22 @@ void intel_ddi_init(struct drm_device *dev, enum port port)
1352 intel_dig_port->saved_port_bits = I915_READ(DDI_BUF_CTL(port)) & 1513 intel_dig_port->saved_port_bits = I915_READ(DDI_BUF_CTL(port)) &
1353 (DDI_BUF_PORT_REVERSAL | 1514 (DDI_BUF_PORT_REVERSAL |
1354 DDI_A_4_LANES); 1515 DDI_A_4_LANES);
1355 intel_dig_port->dp.output_reg = DDI_BUF_CTL(port);
1356 1516
1357 intel_encoder->type = INTEL_OUTPUT_UNKNOWN; 1517 intel_encoder->type = INTEL_OUTPUT_UNKNOWN;
1358 intel_encoder->crtc_mask = (1 << 0) | (1 << 1) | (1 << 2); 1518 intel_encoder->crtc_mask = (1 << 0) | (1 << 1) | (1 << 2);
1359 intel_encoder->cloneable = false; 1519 intel_encoder->cloneable = false;
1360 intel_encoder->hot_plug = intel_ddi_hot_plug; 1520 intel_encoder->hot_plug = intel_ddi_hot_plug;
1361 1521
1362 if (!intel_dp_init_connector(intel_dig_port, dp_connector)) { 1522 if (init_dp)
1363 drm_encoder_cleanup(encoder); 1523 dp_connector = intel_ddi_init_dp_connector(intel_dig_port);
1364 kfree(intel_dig_port);
1365 kfree(dp_connector);
1366 return;
1367 }
1368 1524
1369 if (intel_encoder->type != INTEL_OUTPUT_EDP) { 1525 /* In theory we don't need the encoder->type check, but leave it just in
1370 hdmi_connector = kzalloc(sizeof(struct intel_connector), 1526 * case we have some really bad VBTs... */
1371 GFP_KERNEL); 1527 if (intel_encoder->type != INTEL_OUTPUT_EDP && init_hdmi)
1372 if (!hdmi_connector) { 1528 hdmi_connector = intel_ddi_init_hdmi_connector(intel_dig_port);
1373 return;
1374 }
1375 1529
1376 intel_dig_port->hdmi.hdmi_reg = DDI_BUF_CTL(port); 1530 if (!dp_connector && !hdmi_connector) {
1377 intel_hdmi_init_connector(intel_dig_port, hdmi_connector); 1531 drm_encoder_cleanup(encoder);
1532 kfree(intel_dig_port);
1378 } 1533 }
1379} 1534}