diff options
Diffstat (limited to 'drivers/gpu/drm/radeon/radeon_legacy_encoders.c')
| -rw-r--r-- | drivers/gpu/drm/radeon/radeon_legacy_encoders.c | 125 |
1 files changed, 66 insertions, 59 deletions
diff --git a/drivers/gpu/drm/radeon/radeon_legacy_encoders.c b/drivers/gpu/drm/radeon/radeon_legacy_encoders.c index 00382122869b..df00515e81fa 100644 --- a/drivers/gpu/drm/radeon/radeon_legacy_encoders.c +++ b/drivers/gpu/drm/radeon/radeon_legacy_encoders.c | |||
| @@ -136,7 +136,14 @@ static void radeon_legacy_lvds_mode_set(struct drm_encoder *encoder, | |||
| 136 | lvds_pll_cntl &= ~RADEON_LVDS_PLL_EN; | 136 | lvds_pll_cntl &= ~RADEON_LVDS_PLL_EN; |
| 137 | 137 | ||
| 138 | lvds_ss_gen_cntl = RREG32(RADEON_LVDS_SS_GEN_CNTL); | 138 | lvds_ss_gen_cntl = RREG32(RADEON_LVDS_SS_GEN_CNTL); |
| 139 | if ((!rdev->is_atom_bios)) { | 139 | if (rdev->is_atom_bios) { |
| 140 | /* LVDS_GEN_CNTL parameters are computed in LVDSEncoderControl | ||
| 141 | * need to call that on resume to set up the reg properly. | ||
| 142 | */ | ||
| 143 | radeon_encoder->pixel_clock = adjusted_mode->clock; | ||
| 144 | atombios_digital_setup(encoder, PANEL_ENCODER_ACTION_ENABLE); | ||
| 145 | lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL); | ||
| 146 | } else { | ||
| 140 | struct radeon_encoder_lvds *lvds = (struct radeon_encoder_lvds *)radeon_encoder->enc_priv; | 147 | struct radeon_encoder_lvds *lvds = (struct radeon_encoder_lvds *)radeon_encoder->enc_priv; |
| 141 | if (lvds) { | 148 | if (lvds) { |
| 142 | DRM_DEBUG("bios LVDS_GEN_CNTL: 0x%x\n", lvds->lvds_gen_cntl); | 149 | DRM_DEBUG("bios LVDS_GEN_CNTL: 0x%x\n", lvds->lvds_gen_cntl); |
| @@ -147,8 +154,7 @@ static void radeon_legacy_lvds_mode_set(struct drm_encoder *encoder, | |||
| 147 | (lvds->panel_blon_delay << RADEON_LVDS_PWRSEQ_DELAY2_SHIFT)); | 154 | (lvds->panel_blon_delay << RADEON_LVDS_PWRSEQ_DELAY2_SHIFT)); |
| 148 | } else | 155 | } else |
| 149 | lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL); | 156 | lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL); |
| 150 | } else | 157 | } |
| 151 | lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL); | ||
| 152 | lvds_gen_cntl |= RADEON_LVDS_DISPLAY_DIS; | 158 | lvds_gen_cntl |= RADEON_LVDS_DISPLAY_DIS; |
| 153 | lvds_gen_cntl &= ~(RADEON_LVDS_ON | | 159 | lvds_gen_cntl &= ~(RADEON_LVDS_ON | |
| 154 | RADEON_LVDS_BLON | | 160 | RADEON_LVDS_BLON | |
| @@ -184,9 +190,9 @@ static void radeon_legacy_lvds_mode_set(struct drm_encoder *encoder, | |||
| 184 | radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id); | 190 | radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id); |
| 185 | } | 191 | } |
| 186 | 192 | ||
| 187 | static bool radeon_legacy_lvds_mode_fixup(struct drm_encoder *encoder, | 193 | static bool radeon_legacy_mode_fixup(struct drm_encoder *encoder, |
| 188 | struct drm_display_mode *mode, | 194 | struct drm_display_mode *mode, |
| 189 | struct drm_display_mode *adjusted_mode) | 195 | struct drm_display_mode *adjusted_mode) |
| 190 | { | 196 | { |
| 191 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | 197 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
| 192 | 198 | ||
| @@ -194,15 +200,22 @@ static bool radeon_legacy_lvds_mode_fixup(struct drm_encoder *encoder, | |||
| 194 | radeon_encoder_set_active_device(encoder); | 200 | radeon_encoder_set_active_device(encoder); |
| 195 | drm_mode_set_crtcinfo(adjusted_mode, 0); | 201 | drm_mode_set_crtcinfo(adjusted_mode, 0); |
| 196 | 202 | ||
| 197 | if (radeon_encoder->rmx_type != RMX_OFF) | 203 | /* get the native mode for LVDS */ |
| 198 | radeon_rmx_mode_fixup(encoder, mode, adjusted_mode); | 204 | if (radeon_encoder->active_device & (ATOM_DEVICE_LCD_SUPPORT)) { |
| 205 | struct drm_display_mode *native_mode = &radeon_encoder->native_mode; | ||
| 206 | int mode_id = adjusted_mode->base.id; | ||
| 207 | *adjusted_mode = *native_mode; | ||
| 208 | adjusted_mode->hdisplay = mode->hdisplay; | ||
| 209 | adjusted_mode->vdisplay = mode->vdisplay; | ||
| 210 | adjusted_mode->base.id = mode_id; | ||
| 211 | } | ||
| 199 | 212 | ||
| 200 | return true; | 213 | return true; |
| 201 | } | 214 | } |
| 202 | 215 | ||
| 203 | static const struct drm_encoder_helper_funcs radeon_legacy_lvds_helper_funcs = { | 216 | static const struct drm_encoder_helper_funcs radeon_legacy_lvds_helper_funcs = { |
| 204 | .dpms = radeon_legacy_lvds_dpms, | 217 | .dpms = radeon_legacy_lvds_dpms, |
| 205 | .mode_fixup = radeon_legacy_lvds_mode_fixup, | 218 | .mode_fixup = radeon_legacy_mode_fixup, |
| 206 | .prepare = radeon_legacy_lvds_prepare, | 219 | .prepare = radeon_legacy_lvds_prepare, |
| 207 | .mode_set = radeon_legacy_lvds_mode_set, | 220 | .mode_set = radeon_legacy_lvds_mode_set, |
| 208 | .commit = radeon_legacy_lvds_commit, | 221 | .commit = radeon_legacy_lvds_commit, |
| @@ -214,17 +227,6 @@ static const struct drm_encoder_funcs radeon_legacy_lvds_enc_funcs = { | |||
| 214 | .destroy = radeon_enc_destroy, | 227 | .destroy = radeon_enc_destroy, |
| 215 | }; | 228 | }; |
| 216 | 229 | ||
| 217 | static bool radeon_legacy_primary_dac_mode_fixup(struct drm_encoder *encoder, | ||
| 218 | struct drm_display_mode *mode, | ||
| 219 | struct drm_display_mode *adjusted_mode) | ||
| 220 | { | ||
| 221 | /* set the active encoder to connector routing */ | ||
| 222 | radeon_encoder_set_active_device(encoder); | ||
| 223 | drm_mode_set_crtcinfo(adjusted_mode, 0); | ||
| 224 | |||
| 225 | return true; | ||
| 226 | } | ||
| 227 | |||
| 228 | static void radeon_legacy_primary_dac_dpms(struct drm_encoder *encoder, int mode) | 230 | static void radeon_legacy_primary_dac_dpms(struct drm_encoder *encoder, int mode) |
| 229 | { | 231 | { |
| 230 | struct drm_device *dev = encoder->dev; | 232 | struct drm_device *dev = encoder->dev; |
| @@ -410,7 +412,7 @@ static enum drm_connector_status radeon_legacy_primary_dac_detect(struct drm_enc | |||
| 410 | 412 | ||
| 411 | static const struct drm_encoder_helper_funcs radeon_legacy_primary_dac_helper_funcs = { | 413 | static const struct drm_encoder_helper_funcs radeon_legacy_primary_dac_helper_funcs = { |
| 412 | .dpms = radeon_legacy_primary_dac_dpms, | 414 | .dpms = radeon_legacy_primary_dac_dpms, |
| 413 | .mode_fixup = radeon_legacy_primary_dac_mode_fixup, | 415 | .mode_fixup = radeon_legacy_mode_fixup, |
| 414 | .prepare = radeon_legacy_primary_dac_prepare, | 416 | .prepare = radeon_legacy_primary_dac_prepare, |
| 415 | .mode_set = radeon_legacy_primary_dac_mode_set, | 417 | .mode_set = radeon_legacy_primary_dac_mode_set, |
| 416 | .commit = radeon_legacy_primary_dac_commit, | 418 | .commit = radeon_legacy_primary_dac_commit, |
| @@ -423,16 +425,6 @@ static const struct drm_encoder_funcs radeon_legacy_primary_dac_enc_funcs = { | |||
| 423 | .destroy = radeon_enc_destroy, | 425 | .destroy = radeon_enc_destroy, |
| 424 | }; | 426 | }; |
| 425 | 427 | ||
| 426 | static bool radeon_legacy_tmds_int_mode_fixup(struct drm_encoder *encoder, | ||
| 427 | struct drm_display_mode *mode, | ||
| 428 | struct drm_display_mode *adjusted_mode) | ||
| 429 | { | ||
| 430 | |||
| 431 | drm_mode_set_crtcinfo(adjusted_mode, 0); | ||
| 432 | |||
| 433 | return true; | ||
| 434 | } | ||
| 435 | |||
| 436 | static void radeon_legacy_tmds_int_dpms(struct drm_encoder *encoder, int mode) | 428 | static void radeon_legacy_tmds_int_dpms(struct drm_encoder *encoder, int mode) |
| 437 | { | 429 | { |
| 438 | struct drm_device *dev = encoder->dev; | 430 | struct drm_device *dev = encoder->dev; |
| @@ -584,7 +576,7 @@ static void radeon_legacy_tmds_int_mode_set(struct drm_encoder *encoder, | |||
| 584 | 576 | ||
| 585 | static const struct drm_encoder_helper_funcs radeon_legacy_tmds_int_helper_funcs = { | 577 | static const struct drm_encoder_helper_funcs radeon_legacy_tmds_int_helper_funcs = { |
| 586 | .dpms = radeon_legacy_tmds_int_dpms, | 578 | .dpms = radeon_legacy_tmds_int_dpms, |
| 587 | .mode_fixup = radeon_legacy_tmds_int_mode_fixup, | 579 | .mode_fixup = radeon_legacy_mode_fixup, |
| 588 | .prepare = radeon_legacy_tmds_int_prepare, | 580 | .prepare = radeon_legacy_tmds_int_prepare, |
| 589 | .mode_set = radeon_legacy_tmds_int_mode_set, | 581 | .mode_set = radeon_legacy_tmds_int_mode_set, |
| 590 | .commit = radeon_legacy_tmds_int_commit, | 582 | .commit = radeon_legacy_tmds_int_commit, |
| @@ -596,17 +588,6 @@ static const struct drm_encoder_funcs radeon_legacy_tmds_int_enc_funcs = { | |||
| 596 | .destroy = radeon_enc_destroy, | 588 | .destroy = radeon_enc_destroy, |
| 597 | }; | 589 | }; |
| 598 | 590 | ||
| 599 | static bool radeon_legacy_tmds_ext_mode_fixup(struct drm_encoder *encoder, | ||
| 600 | struct drm_display_mode *mode, | ||
| 601 | struct drm_display_mode *adjusted_mode) | ||
| 602 | { | ||
| 603 | /* set the active encoder to connector routing */ | ||
| 604 | radeon_encoder_set_active_device(encoder); | ||
| 605 | drm_mode_set_crtcinfo(adjusted_mode, 0); | ||
| 606 | |||
| 607 | return true; | ||
| 608 | } | ||
| 609 | |||
| 610 | static void radeon_legacy_tmds_ext_dpms(struct drm_encoder *encoder, int mode) | 591 | static void radeon_legacy_tmds_ext_dpms(struct drm_encoder *encoder, int mode) |
| 611 | { | 592 | { |
| 612 | struct drm_device *dev = encoder->dev; | 593 | struct drm_device *dev = encoder->dev; |
| @@ -697,6 +678,8 @@ static void radeon_legacy_tmds_ext_mode_set(struct drm_encoder *encoder, | |||
| 697 | /*if (mode->clock > 165000) | 678 | /*if (mode->clock > 165000) |
| 698 | fp2_gen_cntl |= R300_FP2_DVO_DUAL_CHANNEL_EN;*/ | 679 | fp2_gen_cntl |= R300_FP2_DVO_DUAL_CHANNEL_EN;*/ |
| 699 | } | 680 | } |
| 681 | if (!radeon_combios_external_tmds_setup(encoder)) | ||
| 682 | radeon_external_tmds_setup(encoder); | ||
| 700 | } | 683 | } |
| 701 | 684 | ||
| 702 | if (radeon_crtc->crtc_id == 0) { | 685 | if (radeon_crtc->crtc_id == 0) { |
| @@ -724,9 +707,22 @@ static void radeon_legacy_tmds_ext_mode_set(struct drm_encoder *encoder, | |||
| 724 | radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id); | 707 | radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id); |
| 725 | } | 708 | } |
| 726 | 709 | ||
| 710 | static void radeon_ext_tmds_enc_destroy(struct drm_encoder *encoder) | ||
| 711 | { | ||
| 712 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | ||
| 713 | struct radeon_encoder_ext_tmds *tmds = radeon_encoder->enc_priv; | ||
| 714 | if (tmds) { | ||
| 715 | if (tmds->i2c_bus) | ||
| 716 | radeon_i2c_destroy(tmds->i2c_bus); | ||
| 717 | } | ||
| 718 | kfree(radeon_encoder->enc_priv); | ||
| 719 | drm_encoder_cleanup(encoder); | ||
| 720 | kfree(radeon_encoder); | ||
| 721 | } | ||
| 722 | |||
| 727 | static const struct drm_encoder_helper_funcs radeon_legacy_tmds_ext_helper_funcs = { | 723 | static const struct drm_encoder_helper_funcs radeon_legacy_tmds_ext_helper_funcs = { |
| 728 | .dpms = radeon_legacy_tmds_ext_dpms, | 724 | .dpms = radeon_legacy_tmds_ext_dpms, |
| 729 | .mode_fixup = radeon_legacy_tmds_ext_mode_fixup, | 725 | .mode_fixup = radeon_legacy_mode_fixup, |
| 730 | .prepare = radeon_legacy_tmds_ext_prepare, | 726 | .prepare = radeon_legacy_tmds_ext_prepare, |
| 731 | .mode_set = radeon_legacy_tmds_ext_mode_set, | 727 | .mode_set = radeon_legacy_tmds_ext_mode_set, |
| 732 | .commit = radeon_legacy_tmds_ext_commit, | 728 | .commit = radeon_legacy_tmds_ext_commit, |
| @@ -735,20 +731,9 @@ static const struct drm_encoder_helper_funcs radeon_legacy_tmds_ext_helper_funcs | |||
| 735 | 731 | ||
| 736 | 732 | ||
| 737 | static const struct drm_encoder_funcs radeon_legacy_tmds_ext_enc_funcs = { | 733 | static const struct drm_encoder_funcs radeon_legacy_tmds_ext_enc_funcs = { |
| 738 | .destroy = radeon_enc_destroy, | 734 | .destroy = radeon_ext_tmds_enc_destroy, |
| 739 | }; | 735 | }; |
| 740 | 736 | ||
| 741 | static bool radeon_legacy_tv_dac_mode_fixup(struct drm_encoder *encoder, | ||
| 742 | struct drm_display_mode *mode, | ||
| 743 | struct drm_display_mode *adjusted_mode) | ||
| 744 | { | ||
| 745 | /* set the active encoder to connector routing */ | ||
| 746 | radeon_encoder_set_active_device(encoder); | ||
| 747 | drm_mode_set_crtcinfo(adjusted_mode, 0); | ||
| 748 | |||
| 749 | return true; | ||
| 750 | } | ||
| 751 | |||
| 752 | static void radeon_legacy_tv_dac_dpms(struct drm_encoder *encoder, int mode) | 737 | static void radeon_legacy_tv_dac_dpms(struct drm_encoder *encoder, int mode) |
| 753 | { | 738 | { |
| 754 | struct drm_device *dev = encoder->dev; | 739 | struct drm_device *dev = encoder->dev; |
| @@ -1265,7 +1250,7 @@ static enum drm_connector_status radeon_legacy_tv_dac_detect(struct drm_encoder | |||
| 1265 | 1250 | ||
| 1266 | static const struct drm_encoder_helper_funcs radeon_legacy_tv_dac_helper_funcs = { | 1251 | static const struct drm_encoder_helper_funcs radeon_legacy_tv_dac_helper_funcs = { |
| 1267 | .dpms = radeon_legacy_tv_dac_dpms, | 1252 | .dpms = radeon_legacy_tv_dac_dpms, |
| 1268 | .mode_fixup = radeon_legacy_tv_dac_mode_fixup, | 1253 | .mode_fixup = radeon_legacy_mode_fixup, |
| 1269 | .prepare = radeon_legacy_tv_dac_prepare, | 1254 | .prepare = radeon_legacy_tv_dac_prepare, |
| 1270 | .mode_set = radeon_legacy_tv_dac_mode_set, | 1255 | .mode_set = radeon_legacy_tv_dac_mode_set, |
| 1271 | .commit = radeon_legacy_tv_dac_commit, | 1256 | .commit = radeon_legacy_tv_dac_commit, |
| @@ -1302,6 +1287,29 @@ static struct radeon_encoder_int_tmds *radeon_legacy_get_tmds_info(struct radeon | |||
| 1302 | return tmds; | 1287 | return tmds; |
| 1303 | } | 1288 | } |
| 1304 | 1289 | ||
| 1290 | static struct radeon_encoder_ext_tmds *radeon_legacy_get_ext_tmds_info(struct radeon_encoder *encoder) | ||
| 1291 | { | ||
| 1292 | struct drm_device *dev = encoder->base.dev; | ||
| 1293 | struct radeon_device *rdev = dev->dev_private; | ||
| 1294 | struct radeon_encoder_ext_tmds *tmds = NULL; | ||
| 1295 | bool ret; | ||
| 1296 | |||
| 1297 | if (rdev->is_atom_bios) | ||
| 1298 | return NULL; | ||
| 1299 | |||
| 1300 | tmds = kzalloc(sizeof(struct radeon_encoder_ext_tmds), GFP_KERNEL); | ||
| 1301 | |||
| 1302 | if (!tmds) | ||
| 1303 | return NULL; | ||
| 1304 | |||
| 1305 | ret = radeon_legacy_get_ext_tmds_info_from_combios(encoder, tmds); | ||
| 1306 | |||
| 1307 | if (ret == false) | ||
| 1308 | radeon_legacy_get_ext_tmds_info_from_table(encoder, tmds); | ||
| 1309 | |||
| 1310 | return tmds; | ||
| 1311 | } | ||
| 1312 | |||
| 1305 | void | 1313 | void |
| 1306 | radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t supported_device) | 1314 | radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t supported_device) |
| 1307 | { | 1315 | { |
| @@ -1329,7 +1337,6 @@ radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t | |||
| 1329 | encoder->possible_crtcs = 0x1; | 1337 | encoder->possible_crtcs = 0x1; |
| 1330 | else | 1338 | else |
| 1331 | encoder->possible_crtcs = 0x3; | 1339 | encoder->possible_crtcs = 0x3; |
| 1332 | encoder->possible_clones = 0; | ||
| 1333 | 1340 | ||
| 1334 | radeon_encoder->enc_priv = NULL; | 1341 | radeon_encoder->enc_priv = NULL; |
| 1335 | 1342 | ||
| @@ -1373,7 +1380,7 @@ radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t | |||
| 1373 | drm_encoder_init(dev, encoder, &radeon_legacy_tmds_ext_enc_funcs, DRM_MODE_ENCODER_TMDS); | 1380 | drm_encoder_init(dev, encoder, &radeon_legacy_tmds_ext_enc_funcs, DRM_MODE_ENCODER_TMDS); |
| 1374 | drm_encoder_helper_add(encoder, &radeon_legacy_tmds_ext_helper_funcs); | 1381 | drm_encoder_helper_add(encoder, &radeon_legacy_tmds_ext_helper_funcs); |
| 1375 | if (!rdev->is_atom_bios) | 1382 | if (!rdev->is_atom_bios) |
| 1376 | radeon_combios_get_ext_tmds_info(radeon_encoder); | 1383 | radeon_encoder->enc_priv = radeon_legacy_get_ext_tmds_info(radeon_encoder); |
| 1377 | break; | 1384 | break; |
| 1378 | } | 1385 | } |
| 1379 | } | 1386 | } |
