aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/gpu/drm/radeon/atombios_crtc.c66
-rw-r--r--drivers/gpu/drm/radeon/radeon_mode.h1
2 files changed, 39 insertions, 28 deletions
diff --git a/drivers/gpu/drm/radeon/atombios_crtc.c b/drivers/gpu/drm/radeon/atombios_crtc.c
index 721f80e9568d..8e32c5891be1 100644
--- a/drivers/gpu/drm/radeon/atombios_crtc.c
+++ b/drivers/gpu/drm/radeon/atombios_crtc.c
@@ -1492,16 +1492,16 @@ static u32 radeon_get_pll_use_mask(struct drm_crtc *crtc)
1492{ 1492{
1493 struct drm_device *dev = crtc->dev; 1493 struct drm_device *dev = crtc->dev;
1494 struct drm_crtc *test_crtc; 1494 struct drm_crtc *test_crtc;
1495 struct radeon_crtc *radeon_test_crtc; 1495 struct radeon_crtc *test_radeon_crtc;
1496 u32 pll_in_use = 0; 1496 u32 pll_in_use = 0;
1497 1497
1498 list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) { 1498 list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) {
1499 if (crtc == test_crtc) 1499 if (crtc == test_crtc)
1500 continue; 1500 continue;
1501 1501
1502 radeon_test_crtc = to_radeon_crtc(test_crtc); 1502 test_radeon_crtc = to_radeon_crtc(test_crtc);
1503 if (radeon_test_crtc->pll_id != ATOM_PPLL_INVALID) 1503 if (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID)
1504 pll_in_use |= (1 << radeon_test_crtc->pll_id); 1504 pll_in_use |= (1 << test_radeon_crtc->pll_id);
1505 } 1505 }
1506 return pll_in_use; 1506 return pll_in_use;
1507} 1507}
@@ -1518,17 +1518,18 @@ static u32 radeon_get_pll_use_mask(struct drm_crtc *crtc)
1518static int radeon_get_shared_dp_ppll(struct drm_crtc *crtc) 1518static int radeon_get_shared_dp_ppll(struct drm_crtc *crtc)
1519{ 1519{
1520 struct drm_device *dev = crtc->dev; 1520 struct drm_device *dev = crtc->dev;
1521 struct drm_encoder *test_encoder; 1521 struct drm_crtc *test_crtc;
1522 struct radeon_crtc *test_radeon_crtc; 1522 struct radeon_crtc *test_radeon_crtc;
1523 1523
1524 list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { 1524 list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) {
1525 if (test_encoder->crtc && (test_encoder->crtc != crtc)) { 1525 if (crtc == test_crtc)
1526 if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { 1526 continue;
1527 /* for DP use the same PLL for all */ 1527 test_radeon_crtc = to_radeon_crtc(test_crtc);
1528 test_radeon_crtc = to_radeon_crtc(test_encoder->crtc); 1528 if (test_radeon_crtc->encoder &&
1529 if (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID) 1529 ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_radeon_crtc->encoder))) {
1530 return test_radeon_crtc->pll_id; 1530 /* for DP use the same PLL for all */
1531 } 1531 if (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID)
1532 return test_radeon_crtc->pll_id;
1532 } 1533 }
1533 } 1534 }
1534 return ATOM_PPLL_INVALID; 1535 return ATOM_PPLL_INVALID;
@@ -1547,10 +1548,8 @@ static int radeon_get_shared_nondp_ppll(struct drm_crtc *crtc)
1547{ 1548{
1548 struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); 1549 struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc);
1549 struct drm_device *dev = crtc->dev; 1550 struct drm_device *dev = crtc->dev;
1550 struct drm_encoder *test_encoder;
1551 struct drm_crtc *test_crtc; 1551 struct drm_crtc *test_crtc;
1552 struct radeon_crtc *test_radeon_crtc; 1552 struct radeon_crtc *test_radeon_crtc;
1553 struct radeon_encoder *test_radeon_encoder;
1554 u32 adjusted_clock, test_adjusted_clock; 1553 u32 adjusted_clock, test_adjusted_clock;
1555 1554
1556 adjusted_clock = radeon_crtc->adjusted_clock; 1555 adjusted_clock = radeon_crtc->adjusted_clock;
@@ -1558,20 +1557,25 @@ static int radeon_get_shared_nondp_ppll(struct drm_crtc *crtc)
1558 if (adjusted_clock == 0) 1557 if (adjusted_clock == 0)
1559 return ATOM_PPLL_INVALID; 1558 return ATOM_PPLL_INVALID;
1560 1559
1561 list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { 1560 list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) {
1562 if (test_encoder->crtc && (test_encoder->crtc != crtc)) { 1561 if (crtc == test_crtc)
1563 if (!ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { 1562 continue;
1564 test_radeon_encoder = to_radeon_encoder(test_encoder); 1563 test_radeon_crtc = to_radeon_crtc(test_crtc);
1565 test_crtc = test_encoder->crtc; 1564 if (test_radeon_crtc->encoder &&
1566 test_radeon_crtc = to_radeon_crtc(test_crtc); 1565 !ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_radeon_crtc->encoder))) {
1567 /* for non-DP check the clock */ 1566 /* check if we are already driving this connector with another crtc */
1568 test_adjusted_clock = test_radeon_crtc->adjusted_clock; 1567 if (test_radeon_crtc->connector == radeon_crtc->connector) {
1569 if ((crtc->mode.clock == test_crtc->mode.clock) && 1568 /* if we are, return that pll */
1570 (adjusted_clock == test_adjusted_clock) && 1569 if (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID)
1571 (radeon_crtc->ss_enabled == test_radeon_crtc->ss_enabled) &&
1572 (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID))
1573 return test_radeon_crtc->pll_id; 1570 return test_radeon_crtc->pll_id;
1574 } 1571 }
1572 /* for non-DP check the clock */
1573 test_adjusted_clock = test_radeon_crtc->adjusted_clock;
1574 if ((crtc->mode.clock == test_crtc->mode.clock) &&
1575 (adjusted_clock == test_adjusted_clock) &&
1576 (radeon_crtc->ss_enabled == test_radeon_crtc->ss_enabled) &&
1577 (test_radeon_crtc->pll_id != ATOM_PPLL_INVALID))
1578 return test_radeon_crtc->pll_id;
1575 } 1579 }
1576 } 1580 }
1577 return ATOM_PPLL_INVALID; 1581 return ATOM_PPLL_INVALID;
@@ -1793,11 +1797,15 @@ static bool atombios_crtc_mode_fixup(struct drm_crtc *crtc,
1793 list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { 1797 list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
1794 if (encoder->crtc == crtc) { 1798 if (encoder->crtc == crtc) {
1795 radeon_crtc->encoder = encoder; 1799 radeon_crtc->encoder = encoder;
1800 radeon_crtc->connector = radeon_get_connector_for_encoder(encoder);
1796 break; 1801 break;
1797 } 1802 }
1798 } 1803 }
1799 if (radeon_crtc->encoder == NULL) 1804 if ((radeon_crtc->encoder == NULL) || (radeon_crtc->connector == NULL)) {
1805 radeon_crtc->encoder = NULL;
1806 radeon_crtc->connector = NULL;
1800 return false; 1807 return false;
1808 }
1801 if (!radeon_crtc_scaling_mode_fixup(crtc, mode, adjusted_mode)) 1809 if (!radeon_crtc_scaling_mode_fixup(crtc, mode, adjusted_mode))
1802 return false; 1810 return false;
1803 if (!atombios_crtc_prepare_pll(crtc, adjusted_mode)) 1811 if (!atombios_crtc_prepare_pll(crtc, adjusted_mode))
@@ -1874,6 +1882,7 @@ done:
1874 radeon_crtc->pll_id = ATOM_PPLL_INVALID; 1882 radeon_crtc->pll_id = ATOM_PPLL_INVALID;
1875 radeon_crtc->adjusted_clock = 0; 1883 radeon_crtc->adjusted_clock = 0;
1876 radeon_crtc->encoder = NULL; 1884 radeon_crtc->encoder = NULL;
1885 radeon_crtc->connector = NULL;
1877} 1886}
1878 1887
1879static const struct drm_crtc_helper_funcs atombios_helper_funcs = { 1888static const struct drm_crtc_helper_funcs atombios_helper_funcs = {
@@ -1925,5 +1934,6 @@ void radeon_atombios_init_crtc(struct drm_device *dev,
1925 radeon_crtc->pll_id = ATOM_PPLL_INVALID; 1934 radeon_crtc->pll_id = ATOM_PPLL_INVALID;
1926 radeon_crtc->adjusted_clock = 0; 1935 radeon_crtc->adjusted_clock = 0;
1927 radeon_crtc->encoder = NULL; 1936 radeon_crtc->encoder = NULL;
1937 radeon_crtc->connector = NULL;
1928 drm_crtc_helper_add(&radeon_crtc->base, &atombios_helper_funcs); 1938 drm_crtc_helper_add(&radeon_crtc->base, &atombios_helper_funcs);
1929} 1939}
diff --git a/drivers/gpu/drm/radeon/radeon_mode.h b/drivers/gpu/drm/radeon/radeon_mode.h
index 2d78645576d7..917d02750cf7 100644
--- a/drivers/gpu/drm/radeon/radeon_mode.h
+++ b/drivers/gpu/drm/radeon/radeon_mode.h
@@ -327,6 +327,7 @@ struct radeon_crtc {
327 u32 pll_post_div; 327 u32 pll_post_div;
328 u32 pll_flags; 328 u32 pll_flags;
329 struct drm_encoder *encoder; 329 struct drm_encoder *encoder;
330 struct drm_connector *connector;
330}; 331};
331 332
332struct radeon_encoder_primary_dac { 333struct radeon_encoder_primary_dac {