diff options
Diffstat (limited to 'drivers/gpu/drm/radeon')
-rw-r--r-- | drivers/gpu/drm/radeon/atombios_crtc.c | 199 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/atombios_dp.c | 29 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/atombios_encoders.c | 140 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/r600_cs.c | 30 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/r600d.h | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_device.c | 5 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_drv.c | 3 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_fence.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/reg_srcs/r600 | 1 |
9 files changed, 275 insertions, 148 deletions
diff --git a/drivers/gpu/drm/radeon/atombios_crtc.c b/drivers/gpu/drm/radeon/atombios_crtc.c index f4d4505fe831..e721e3087b99 100644 --- a/drivers/gpu/drm/radeon/atombios_crtc.c +++ b/drivers/gpu/drm/radeon/atombios_crtc.c | |||
@@ -258,7 +258,6 @@ void atombios_crtc_dpms(struct drm_crtc *crtc, int mode) | |||
258 | radeon_crtc->enabled = true; | 258 | radeon_crtc->enabled = true; |
259 | /* adjust pm to dpms changes BEFORE enabling crtcs */ | 259 | /* adjust pm to dpms changes BEFORE enabling crtcs */ |
260 | radeon_pm_compute_clocks(rdev); | 260 | radeon_pm_compute_clocks(rdev); |
261 | /* disable crtc pair power gating before programming */ | ||
262 | if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) | 261 | if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) |
263 | atombios_powergate_crtc(crtc, ATOM_DISABLE); | 262 | atombios_powergate_crtc(crtc, ATOM_DISABLE); |
264 | atombios_enable_crtc(crtc, ATOM_ENABLE); | 263 | atombios_enable_crtc(crtc, ATOM_ENABLE); |
@@ -278,25 +277,8 @@ void atombios_crtc_dpms(struct drm_crtc *crtc, int mode) | |||
278 | atombios_enable_crtc_memreq(crtc, ATOM_DISABLE); | 277 | atombios_enable_crtc_memreq(crtc, ATOM_DISABLE); |
279 | atombios_enable_crtc(crtc, ATOM_DISABLE); | 278 | atombios_enable_crtc(crtc, ATOM_DISABLE); |
280 | radeon_crtc->enabled = false; | 279 | radeon_crtc->enabled = false; |
281 | /* power gating is per-pair */ | 280 | if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) |
282 | if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) { | 281 | atombios_powergate_crtc(crtc, ATOM_ENABLE); |
283 | struct drm_crtc *other_crtc; | ||
284 | struct radeon_crtc *other_radeon_crtc; | ||
285 | list_for_each_entry(other_crtc, &rdev->ddev->mode_config.crtc_list, head) { | ||
286 | other_radeon_crtc = to_radeon_crtc(other_crtc); | ||
287 | if (((radeon_crtc->crtc_id == 0) && (other_radeon_crtc->crtc_id == 1)) || | ||
288 | ((radeon_crtc->crtc_id == 1) && (other_radeon_crtc->crtc_id == 0)) || | ||
289 | ((radeon_crtc->crtc_id == 2) && (other_radeon_crtc->crtc_id == 3)) || | ||
290 | ((radeon_crtc->crtc_id == 3) && (other_radeon_crtc->crtc_id == 2)) || | ||
291 | ((radeon_crtc->crtc_id == 4) && (other_radeon_crtc->crtc_id == 5)) || | ||
292 | ((radeon_crtc->crtc_id == 5) && (other_radeon_crtc->crtc_id == 4))) { | ||
293 | /* if both crtcs in the pair are off, enable power gating */ | ||
294 | if (other_radeon_crtc->enabled == false) | ||
295 | atombios_powergate_crtc(crtc, ATOM_ENABLE); | ||
296 | break; | ||
297 | } | ||
298 | } | ||
299 | } | ||
300 | /* adjust pm to dpms changes AFTER disabling crtcs */ | 282 | /* adjust pm to dpms changes AFTER disabling crtcs */ |
301 | radeon_pm_compute_clocks(rdev); | 283 | radeon_pm_compute_clocks(rdev); |
302 | break; | 284 | break; |
@@ -1497,14 +1479,98 @@ static void radeon_legacy_atom_fixup(struct drm_crtc *crtc) | |||
1497 | } | 1479 | } |
1498 | } | 1480 | } |
1499 | 1481 | ||
1482 | /** | ||
1483 | * radeon_get_pll_use_mask - look up a mask of which pplls are in use | ||
1484 | * | ||
1485 | * @crtc: drm crtc | ||
1486 | * | ||
1487 | * Returns the mask of which PPLLs (Pixel PLLs) are in use. | ||
1488 | */ | ||
1489 | static u32 radeon_get_pll_use_mask(struct drm_crtc *crtc) | ||
1490 | { | ||
1491 | struct drm_device *dev = crtc->dev; | ||
1492 | struct drm_crtc *test_crtc; | ||
1493 | struct radeon_crtc *radeon_test_crtc; | ||
1494 | u32 pll_in_use = 0; | ||
1495 | |||
1496 | list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) { | ||
1497 | if (crtc == test_crtc) | ||
1498 | continue; | ||
1499 | |||
1500 | radeon_test_crtc = to_radeon_crtc(test_crtc); | ||
1501 | if (radeon_test_crtc->pll_id != ATOM_PPLL_INVALID) | ||
1502 | pll_in_use |= (1 << radeon_test_crtc->pll_id); | ||
1503 | } | ||
1504 | return pll_in_use; | ||
1505 | } | ||
1506 | |||
1507 | /** | ||
1508 | * radeon_get_shared_dp_ppll - return the PPLL used by another crtc for DP | ||
1509 | * | ||
1510 | * @crtc: drm crtc | ||
1511 | * | ||
1512 | * Returns the PPLL (Pixel PLL) used by another crtc/encoder which is | ||
1513 | * also in DP mode. For DP, a single PPLL can be used for all DP | ||
1514 | * crtcs/encoders. | ||
1515 | */ | ||
1516 | static int radeon_get_shared_dp_ppll(struct drm_crtc *crtc) | ||
1517 | { | ||
1518 | struct drm_device *dev = crtc->dev; | ||
1519 | struct drm_encoder *test_encoder; | ||
1520 | struct radeon_crtc *radeon_test_crtc; | ||
1521 | |||
1522 | list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { | ||
1523 | if (test_encoder->crtc && (test_encoder->crtc != crtc)) { | ||
1524 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { | ||
1525 | /* for DP use the same PLL for all */ | ||
1526 | radeon_test_crtc = to_radeon_crtc(test_encoder->crtc); | ||
1527 | if (radeon_test_crtc->pll_id != ATOM_PPLL_INVALID) | ||
1528 | return radeon_test_crtc->pll_id; | ||
1529 | } | ||
1530 | } | ||
1531 | } | ||
1532 | return ATOM_PPLL_INVALID; | ||
1533 | } | ||
1534 | |||
1535 | /** | ||
1536 | * radeon_atom_pick_pll - Allocate a PPLL for use by the crtc. | ||
1537 | * | ||
1538 | * @crtc: drm crtc | ||
1539 | * | ||
1540 | * Returns the PPLL (Pixel PLL) to be used by the crtc. For DP monitors | ||
1541 | * a single PPLL can be used for all DP crtcs/encoders. For non-DP | ||
1542 | * monitors a dedicated PPLL must be used. If a particular board has | ||
1543 | * an external DP PLL, return ATOM_PPLL_INVALID to skip PLL programming | ||
1544 | * as there is no need to program the PLL itself. If we are not able to | ||
1545 | * allocate a PLL, return ATOM_PPLL_INVALID to skip PLL programming to | ||
1546 | * avoid messing up an existing monitor. | ||
1547 | * | ||
1548 | * Asic specific PLL information | ||
1549 | * | ||
1550 | * DCE 6.1 | ||
1551 | * - PPLL2 is only available to UNIPHYA (both DP and non-DP) | ||
1552 | * - PPLL0, PPLL1 are available for UNIPHYB/C/D/E/F (both DP and non-DP) | ||
1553 | * | ||
1554 | * DCE 6.0 | ||
1555 | * - PPLL0 is available to all UNIPHY (DP only) | ||
1556 | * - PPLL1, PPLL2 are available for all UNIPHY (both DP and non-DP) and DAC | ||
1557 | * | ||
1558 | * DCE 5.0 | ||
1559 | * - DCPLL is available to all UNIPHY (DP only) | ||
1560 | * - PPLL1, PPLL2 are available for all UNIPHY (both DP and non-DP) and DAC | ||
1561 | * | ||
1562 | * DCE 3.0/4.0/4.1 | ||
1563 | * - PPLL1, PPLL2 are available for all UNIPHY (both DP and non-DP) and DAC | ||
1564 | * | ||
1565 | */ | ||
1500 | static int radeon_atom_pick_pll(struct drm_crtc *crtc) | 1566 | static int radeon_atom_pick_pll(struct drm_crtc *crtc) |
1501 | { | 1567 | { |
1502 | struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); | 1568 | struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); |
1503 | struct drm_device *dev = crtc->dev; | 1569 | struct drm_device *dev = crtc->dev; |
1504 | struct radeon_device *rdev = dev->dev_private; | 1570 | struct radeon_device *rdev = dev->dev_private; |
1505 | struct drm_encoder *test_encoder; | 1571 | struct drm_encoder *test_encoder; |
1506 | struct drm_crtc *test_crtc; | 1572 | u32 pll_in_use; |
1507 | uint32_t pll_in_use = 0; | 1573 | int pll; |
1508 | 1574 | ||
1509 | if (ASIC_IS_DCE61(rdev)) { | 1575 | if (ASIC_IS_DCE61(rdev)) { |
1510 | list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { | 1576 | list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { |
@@ -1516,32 +1582,40 @@ static int radeon_atom_pick_pll(struct drm_crtc *crtc) | |||
1516 | 1582 | ||
1517 | if ((test_radeon_encoder->encoder_id == | 1583 | if ((test_radeon_encoder->encoder_id == |
1518 | ENCODER_OBJECT_ID_INTERNAL_UNIPHY) && | 1584 | ENCODER_OBJECT_ID_INTERNAL_UNIPHY) && |
1519 | (dig->linkb == false)) /* UNIPHY A uses PPLL2 */ | 1585 | (dig->linkb == false)) |
1586 | /* UNIPHY A uses PPLL2 */ | ||
1520 | return ATOM_PPLL2; | 1587 | return ATOM_PPLL2; |
1588 | else if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { | ||
1589 | /* UNIPHY B/C/D/E/F */ | ||
1590 | if (rdev->clock.dp_extclk) | ||
1591 | /* skip PPLL programming if using ext clock */ | ||
1592 | return ATOM_PPLL_INVALID; | ||
1593 | else { | ||
1594 | /* use the same PPLL for all DP monitors */ | ||
1595 | pll = radeon_get_shared_dp_ppll(crtc); | ||
1596 | if (pll != ATOM_PPLL_INVALID) | ||
1597 | return pll; | ||
1598 | } | ||
1599 | } | ||
1600 | break; | ||
1521 | } | 1601 | } |
1522 | } | 1602 | } |
1523 | /* UNIPHY B/C/D/E/F */ | 1603 | /* UNIPHY B/C/D/E/F */ |
1524 | list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) { | 1604 | pll_in_use = radeon_get_pll_use_mask(crtc); |
1525 | struct radeon_crtc *radeon_test_crtc; | 1605 | if (!(pll_in_use & (1 << ATOM_PPLL0))) |
1526 | |||
1527 | if (crtc == test_crtc) | ||
1528 | continue; | ||
1529 | |||
1530 | radeon_test_crtc = to_radeon_crtc(test_crtc); | ||
1531 | if ((radeon_test_crtc->pll_id == ATOM_PPLL0) || | ||
1532 | (radeon_test_crtc->pll_id == ATOM_PPLL1)) | ||
1533 | pll_in_use |= (1 << radeon_test_crtc->pll_id); | ||
1534 | } | ||
1535 | if (!(pll_in_use & 4)) | ||
1536 | return ATOM_PPLL0; | 1606 | return ATOM_PPLL0; |
1537 | return ATOM_PPLL1; | 1607 | if (!(pll_in_use & (1 << ATOM_PPLL1))) |
1608 | return ATOM_PPLL1; | ||
1609 | DRM_ERROR("unable to allocate a PPLL\n"); | ||
1610 | return ATOM_PPLL_INVALID; | ||
1538 | } else if (ASIC_IS_DCE4(rdev)) { | 1611 | } else if (ASIC_IS_DCE4(rdev)) { |
1539 | list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { | 1612 | list_for_each_entry(test_encoder, &dev->mode_config.encoder_list, head) { |
1540 | if (test_encoder->crtc && (test_encoder->crtc == crtc)) { | 1613 | if (test_encoder->crtc && (test_encoder->crtc == crtc)) { |
1541 | /* in DP mode, the DP ref clock can come from PPLL, DCPLL, or ext clock, | 1614 | /* in DP mode, the DP ref clock can come from PPLL, DCPLL, or ext clock, |
1542 | * depending on the asic: | 1615 | * depending on the asic: |
1543 | * DCE4: PPLL or ext clock | 1616 | * DCE4: PPLL or ext clock |
1544 | * DCE5: DCPLL or ext clock | 1617 | * DCE5: PPLL, DCPLL, or ext clock |
1618 | * DCE6: PPLL, PPLL0, or ext clock | ||
1545 | * | 1619 | * |
1546 | * Setting ATOM_PPLL_INVALID will cause SetPixelClock to skip | 1620 | * Setting ATOM_PPLL_INVALID will cause SetPixelClock to skip |
1547 | * PPLL/DCPLL programming and only program the DP DTO for the | 1621 | * PPLL/DCPLL programming and only program the DP DTO for the |
@@ -1549,31 +1623,34 @@ static int radeon_atom_pick_pll(struct drm_crtc *crtc) | |||
1549 | */ | 1623 | */ |
1550 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { | 1624 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(test_encoder))) { |
1551 | if (rdev->clock.dp_extclk) | 1625 | if (rdev->clock.dp_extclk) |
1626 | /* skip PPLL programming if using ext clock */ | ||
1552 | return ATOM_PPLL_INVALID; | 1627 | return ATOM_PPLL_INVALID; |
1553 | else if (ASIC_IS_DCE6(rdev)) | 1628 | else if (ASIC_IS_DCE6(rdev)) |
1629 | /* use PPLL0 for all DP */ | ||
1554 | return ATOM_PPLL0; | 1630 | return ATOM_PPLL0; |
1555 | else if (ASIC_IS_DCE5(rdev)) | 1631 | else if (ASIC_IS_DCE5(rdev)) |
1632 | /* use DCPLL for all DP */ | ||
1556 | return ATOM_DCPLL; | 1633 | return ATOM_DCPLL; |
1634 | else { | ||
1635 | /* use the same PPLL for all DP monitors */ | ||
1636 | pll = radeon_get_shared_dp_ppll(crtc); | ||
1637 | if (pll != ATOM_PPLL_INVALID) | ||
1638 | return pll; | ||
1639 | } | ||
1557 | } | 1640 | } |
1641 | break; | ||
1558 | } | 1642 | } |
1559 | } | 1643 | } |
1560 | 1644 | /* all other cases */ | |
1561 | /* otherwise, pick one of the plls */ | 1645 | pll_in_use = radeon_get_pll_use_mask(crtc); |
1562 | list_for_each_entry(test_crtc, &dev->mode_config.crtc_list, head) { | 1646 | if (!(pll_in_use & (1 << ATOM_PPLL2))) |
1563 | struct radeon_crtc *radeon_test_crtc; | 1647 | return ATOM_PPLL2; |
1564 | 1648 | if (!(pll_in_use & (1 << ATOM_PPLL1))) | |
1565 | if (crtc == test_crtc) | ||
1566 | continue; | ||
1567 | |||
1568 | radeon_test_crtc = to_radeon_crtc(test_crtc); | ||
1569 | if ((radeon_test_crtc->pll_id >= ATOM_PPLL1) && | ||
1570 | (radeon_test_crtc->pll_id <= ATOM_PPLL2)) | ||
1571 | pll_in_use |= (1 << radeon_test_crtc->pll_id); | ||
1572 | } | ||
1573 | if (!(pll_in_use & 1)) | ||
1574 | return ATOM_PPLL1; | 1649 | return ATOM_PPLL1; |
1575 | return ATOM_PPLL2; | 1650 | DRM_ERROR("unable to allocate a PPLL\n"); |
1651 | return ATOM_PPLL_INVALID; | ||
1576 | } else | 1652 | } else |
1653 | /* use PPLL1 or PPLL2 */ | ||
1577 | return radeon_crtc->crtc_id; | 1654 | return radeon_crtc->crtc_id; |
1578 | 1655 | ||
1579 | } | 1656 | } |
@@ -1682,9 +1759,22 @@ static void atombios_crtc_disable(struct drm_crtc *crtc) | |||
1682 | struct drm_device *dev = crtc->dev; | 1759 | struct drm_device *dev = crtc->dev; |
1683 | struct radeon_device *rdev = dev->dev_private; | 1760 | struct radeon_device *rdev = dev->dev_private; |
1684 | struct radeon_atom_ss ss; | 1761 | struct radeon_atom_ss ss; |
1762 | int i; | ||
1685 | 1763 | ||
1686 | atombios_crtc_dpms(crtc, DRM_MODE_DPMS_OFF); | 1764 | atombios_crtc_dpms(crtc, DRM_MODE_DPMS_OFF); |
1687 | 1765 | ||
1766 | for (i = 0; i < rdev->num_crtc; i++) { | ||
1767 | if (rdev->mode_info.crtcs[i] && | ||
1768 | rdev->mode_info.crtcs[i]->enabled && | ||
1769 | i != radeon_crtc->crtc_id && | ||
1770 | radeon_crtc->pll_id == rdev->mode_info.crtcs[i]->pll_id) { | ||
1771 | /* one other crtc is using this pll don't turn | ||
1772 | * off the pll | ||
1773 | */ | ||
1774 | goto done; | ||
1775 | } | ||
1776 | } | ||
1777 | |||
1688 | switch (radeon_crtc->pll_id) { | 1778 | switch (radeon_crtc->pll_id) { |
1689 | case ATOM_PPLL1: | 1779 | case ATOM_PPLL1: |
1690 | case ATOM_PPLL2: | 1780 | case ATOM_PPLL2: |
@@ -1701,7 +1791,8 @@ static void atombios_crtc_disable(struct drm_crtc *crtc) | |||
1701 | default: | 1791 | default: |
1702 | break; | 1792 | break; |
1703 | } | 1793 | } |
1704 | radeon_crtc->pll_id = -1; | 1794 | done: |
1795 | radeon_crtc->pll_id = ATOM_PPLL_INVALID; | ||
1705 | } | 1796 | } |
1706 | 1797 | ||
1707 | static const struct drm_crtc_helper_funcs atombios_helper_funcs = { | 1798 | static const struct drm_crtc_helper_funcs atombios_helper_funcs = { |
@@ -1750,6 +1841,6 @@ void radeon_atombios_init_crtc(struct drm_device *dev, | |||
1750 | else | 1841 | else |
1751 | radeon_crtc->crtc_offset = 0; | 1842 | radeon_crtc->crtc_offset = 0; |
1752 | } | 1843 | } |
1753 | radeon_crtc->pll_id = -1; | 1844 | radeon_crtc->pll_id = ATOM_PPLL_INVALID; |
1754 | drm_crtc_helper_add(&radeon_crtc->base, &atombios_helper_funcs); | 1845 | drm_crtc_helper_add(&radeon_crtc->base, &atombios_helper_funcs); |
1755 | } | 1846 | } |
diff --git a/drivers/gpu/drm/radeon/atombios_dp.c b/drivers/gpu/drm/radeon/atombios_dp.c index 7712cf5ab33b..3623b98ed3fe 100644 --- a/drivers/gpu/drm/radeon/atombios_dp.c +++ b/drivers/gpu/drm/radeon/atombios_dp.c | |||
@@ -577,30 +577,25 @@ int radeon_dp_get_panel_mode(struct drm_encoder *encoder, | |||
577 | struct radeon_device *rdev = dev->dev_private; | 577 | struct radeon_device *rdev = dev->dev_private; |
578 | struct radeon_connector *radeon_connector = to_radeon_connector(connector); | 578 | struct radeon_connector *radeon_connector = to_radeon_connector(connector); |
579 | int panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; | 579 | int panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; |
580 | u16 dp_bridge = radeon_connector_encoder_get_dp_bridge_encoder_id(connector); | ||
581 | u8 tmp; | ||
580 | 582 | ||
581 | if (!ASIC_IS_DCE4(rdev)) | 583 | if (!ASIC_IS_DCE4(rdev)) |
582 | return panel_mode; | 584 | return panel_mode; |
583 | 585 | ||
584 | if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) == | 586 | if (dp_bridge != ENCODER_OBJECT_ID_NONE) { |
585 | ENCODER_OBJECT_ID_NUTMEG) | 587 | /* DP bridge chips */ |
586 | panel_mode = DP_PANEL_MODE_INTERNAL_DP1_MODE; | 588 | tmp = radeon_read_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_CAP); |
587 | else if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) == | 589 | if (tmp & 1) |
588 | ENCODER_OBJECT_ID_TRAVIS) { | 590 | panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE; |
589 | u8 id[6]; | 591 | else if ((dp_bridge == ENCODER_OBJECT_ID_NUTMEG) || |
590 | int i; | 592 | (dp_bridge == ENCODER_OBJECT_ID_TRAVIS)) |
591 | for (i = 0; i < 6; i++) | ||
592 | id[i] = radeon_read_dpcd_reg(radeon_connector, 0x503 + i); | ||
593 | if (id[0] == 0x73 && | ||
594 | id[1] == 0x69 && | ||
595 | id[2] == 0x76 && | ||
596 | id[3] == 0x61 && | ||
597 | id[4] == 0x72 && | ||
598 | id[5] == 0x54) | ||
599 | panel_mode = DP_PANEL_MODE_INTERNAL_DP1_MODE; | 593 | panel_mode = DP_PANEL_MODE_INTERNAL_DP1_MODE; |
600 | else | 594 | else |
601 | panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE; | 595 | panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; |
602 | } else if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) { | 596 | } else if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) { |
603 | u8 tmp = radeon_read_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_CAP); | 597 | /* eDP */ |
598 | tmp = radeon_read_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_CAP); | ||
604 | if (tmp & 1) | 599 | if (tmp & 1) |
605 | panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE; | 600 | panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE; |
606 | } | 601 | } |
diff --git a/drivers/gpu/drm/radeon/atombios_encoders.c b/drivers/gpu/drm/radeon/atombios_encoders.c index f9bc27fe269a..6e8803a1170c 100644 --- a/drivers/gpu/drm/radeon/atombios_encoders.c +++ b/drivers/gpu/drm/radeon/atombios_encoders.c | |||
@@ -1379,6 +1379,8 @@ radeon_atom_encoder_dpms_dig(struct drm_encoder *encoder, int mode) | |||
1379 | struct drm_device *dev = encoder->dev; | 1379 | struct drm_device *dev = encoder->dev; |
1380 | struct radeon_device *rdev = dev->dev_private; | 1380 | struct radeon_device *rdev = dev->dev_private; |
1381 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | 1381 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
1382 | struct drm_encoder *ext_encoder = radeon_get_external_encoder(encoder); | ||
1383 | struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; | ||
1382 | struct drm_connector *connector = radeon_get_connector_for_encoder(encoder); | 1384 | struct drm_connector *connector = radeon_get_connector_for_encoder(encoder); |
1383 | struct radeon_connector *radeon_connector = NULL; | 1385 | struct radeon_connector *radeon_connector = NULL; |
1384 | struct radeon_connector_atom_dig *radeon_dig_connector = NULL; | 1386 | struct radeon_connector_atom_dig *radeon_dig_connector = NULL; |
@@ -1390,19 +1392,37 @@ radeon_atom_encoder_dpms_dig(struct drm_encoder *encoder, int mode) | |||
1390 | 1392 | ||
1391 | switch (mode) { | 1393 | switch (mode) { |
1392 | case DRM_MODE_DPMS_ON: | 1394 | case DRM_MODE_DPMS_ON: |
1393 | /* some early dce3.2 boards have a bug in their transmitter control table */ | 1395 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE5(rdev)) { |
1394 | if ((rdev->family == CHIP_RV710) || (rdev->family == CHIP_RV730) || | 1396 | if (!connector) |
1395 | ASIC_IS_DCE41(rdev) || ASIC_IS_DCE5(rdev)) { | 1397 | dig->panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; |
1396 | if (ASIC_IS_DCE6(rdev)) { | 1398 | else |
1397 | /* It seems we need to call ATOM_ENCODER_CMD_SETUP again | 1399 | dig->panel_mode = radeon_dp_get_panel_mode(encoder, connector); |
1398 | * before reenabling encoder on DPMS ON, otherwise we never | 1400 | |
1399 | * get picture | 1401 | /* setup and enable the encoder */ |
1400 | */ | 1402 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_SETUP, 0); |
1401 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_SETUP, 0); | 1403 | atombios_dig_encoder_setup(encoder, |
1404 | ATOM_ENCODER_CMD_SETUP_PANEL_MODE, | ||
1405 | dig->panel_mode); | ||
1406 | if (ext_encoder) { | ||
1407 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE61(rdev)) | ||
1408 | atombios_external_encoder_setup(encoder, ext_encoder, | ||
1409 | EXTERNAL_ENCODER_ACTION_V3_ENCODER_SETUP); | ||
1402 | } | 1410 | } |
1403 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); | 1411 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); |
1404 | } else { | 1412 | } else if (ASIC_IS_DCE4(rdev)) { |
1413 | /* setup and enable the encoder */ | ||
1414 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_SETUP, 0); | ||
1415 | /* enable the transmitter */ | ||
1416 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); | ||
1405 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE_OUTPUT, 0, 0); | 1417 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE_OUTPUT, 0, 0); |
1418 | } else { | ||
1419 | /* setup and enable the encoder and transmitter */ | ||
1420 | atombios_dig_encoder_setup(encoder, ATOM_ENABLE, 0); | ||
1421 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_SETUP, 0, 0); | ||
1422 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); | ||
1423 | /* some early dce3.2 boards have a bug in their transmitter control table */ | ||
1424 | if ((rdev->family != CHIP_RV710) || (rdev->family != CHIP_RV730)) | ||
1425 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE_OUTPUT, 0, 0); | ||
1406 | } | 1426 | } |
1407 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(encoder)) && connector) { | 1427 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(encoder)) && connector) { |
1408 | if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) { | 1428 | if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) { |
@@ -1420,10 +1440,19 @@ radeon_atom_encoder_dpms_dig(struct drm_encoder *encoder, int mode) | |||
1420 | case DRM_MODE_DPMS_STANDBY: | 1440 | case DRM_MODE_DPMS_STANDBY: |
1421 | case DRM_MODE_DPMS_SUSPEND: | 1441 | case DRM_MODE_DPMS_SUSPEND: |
1422 | case DRM_MODE_DPMS_OFF: | 1442 | case DRM_MODE_DPMS_OFF: |
1423 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE5(rdev)) | 1443 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE5(rdev)) { |
1444 | /* disable the transmitter */ | ||
1424 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | 1445 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); |
1425 | else | 1446 | } else if (ASIC_IS_DCE4(rdev)) { |
1447 | /* disable the transmitter */ | ||
1448 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE_OUTPUT, 0, 0); | ||
1449 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
1450 | } else { | ||
1451 | /* disable the encoder and transmitter */ | ||
1426 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE_OUTPUT, 0, 0); | 1452 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE_OUTPUT, 0, 0); |
1453 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
1454 | atombios_dig_encoder_setup(encoder, ATOM_DISABLE, 0); | ||
1455 | } | ||
1427 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(encoder)) && connector) { | 1456 | if (ENCODER_MODE_IS_DP(atombios_get_encoder_mode(encoder)) && connector) { |
1428 | if (ASIC_IS_DCE4(rdev)) | 1457 | if (ASIC_IS_DCE4(rdev)) |
1429 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_DP_VIDEO_OFF, 0); | 1458 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_DP_VIDEO_OFF, 0); |
@@ -1740,13 +1769,34 @@ static int radeon_atom_pick_dig_encoder(struct drm_encoder *encoder) | |||
1740 | struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc); | 1769 | struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc); |
1741 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | 1770 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
1742 | struct drm_encoder *test_encoder; | 1771 | struct drm_encoder *test_encoder; |
1743 | struct radeon_encoder_atom_dig *dig; | 1772 | struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
1744 | uint32_t dig_enc_in_use = 0; | 1773 | uint32_t dig_enc_in_use = 0; |
1745 | 1774 | ||
1746 | /* DCE4/5 */ | 1775 | if (ASIC_IS_DCE6(rdev)) { |
1747 | if (ASIC_IS_DCE4(rdev)) { | 1776 | /* DCE6 */ |
1748 | dig = radeon_encoder->enc_priv; | 1777 | switch (radeon_encoder->encoder_id) { |
1749 | if (ASIC_IS_DCE41(rdev)) { | 1778 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY: |
1779 | if (dig->linkb) | ||
1780 | return 1; | ||
1781 | else | ||
1782 | return 0; | ||
1783 | break; | ||
1784 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: | ||
1785 | if (dig->linkb) | ||
1786 | return 3; | ||
1787 | else | ||
1788 | return 2; | ||
1789 | break; | ||
1790 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: | ||
1791 | if (dig->linkb) | ||
1792 | return 5; | ||
1793 | else | ||
1794 | return 4; | ||
1795 | break; | ||
1796 | } | ||
1797 | } else if (ASIC_IS_DCE4(rdev)) { | ||
1798 | /* DCE4/5 */ | ||
1799 | if (ASIC_IS_DCE41(rdev) && !ASIC_IS_DCE61(rdev)) { | ||
1750 | /* ontario follows DCE4 */ | 1800 | /* ontario follows DCE4 */ |
1751 | if (rdev->family == CHIP_PALM) { | 1801 | if (rdev->family == CHIP_PALM) { |
1752 | if (dig->linkb) | 1802 | if (dig->linkb) |
@@ -1848,10 +1898,12 @@ radeon_atom_encoder_mode_set(struct drm_encoder *encoder, | |||
1848 | struct drm_device *dev = encoder->dev; | 1898 | struct drm_device *dev = encoder->dev; |
1849 | struct radeon_device *rdev = dev->dev_private; | 1899 | struct radeon_device *rdev = dev->dev_private; |
1850 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | 1900 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
1851 | struct drm_encoder *ext_encoder = radeon_get_external_encoder(encoder); | ||
1852 | 1901 | ||
1853 | radeon_encoder->pixel_clock = adjusted_mode->clock; | 1902 | radeon_encoder->pixel_clock = adjusted_mode->clock; |
1854 | 1903 | ||
1904 | /* need to call this here rather than in prepare() since we need some crtc info */ | ||
1905 | radeon_atom_encoder_dpms(encoder, DRM_MODE_DPMS_OFF); | ||
1906 | |||
1855 | if (ASIC_IS_AVIVO(rdev) && !ASIC_IS_DCE4(rdev)) { | 1907 | if (ASIC_IS_AVIVO(rdev) && !ASIC_IS_DCE4(rdev)) { |
1856 | if (radeon_encoder->active_device & (ATOM_DEVICE_CV_SUPPORT | ATOM_DEVICE_TV_SUPPORT)) | 1908 | if (radeon_encoder->active_device & (ATOM_DEVICE_CV_SUPPORT | ATOM_DEVICE_TV_SUPPORT)) |
1857 | atombios_yuv_setup(encoder, true); | 1909 | atombios_yuv_setup(encoder, true); |
@@ -1870,38 +1922,7 @@ radeon_atom_encoder_mode_set(struct drm_encoder *encoder, | |||
1870 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: | 1922 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: |
1871 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: | 1923 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: |
1872 | case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA: | 1924 | case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA: |
1873 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE5(rdev)) { | 1925 | /* handled in dpms */ |
1874 | struct drm_connector *connector = radeon_get_connector_for_encoder(encoder); | ||
1875 | struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; | ||
1876 | |||
1877 | if (!connector) | ||
1878 | dig->panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; | ||
1879 | else | ||
1880 | dig->panel_mode = radeon_dp_get_panel_mode(encoder, connector); | ||
1881 | |||
1882 | /* setup and enable the encoder */ | ||
1883 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_SETUP, 0); | ||
1884 | atombios_dig_encoder_setup(encoder, | ||
1885 | ATOM_ENCODER_CMD_SETUP_PANEL_MODE, | ||
1886 | dig->panel_mode); | ||
1887 | } else if (ASIC_IS_DCE4(rdev)) { | ||
1888 | /* disable the transmitter */ | ||
1889 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
1890 | /* setup and enable the encoder */ | ||
1891 | atombios_dig_encoder_setup(encoder, ATOM_ENCODER_CMD_SETUP, 0); | ||
1892 | |||
1893 | /* enable the transmitter */ | ||
1894 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); | ||
1895 | } else { | ||
1896 | /* disable the encoder and transmitter */ | ||
1897 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
1898 | atombios_dig_encoder_setup(encoder, ATOM_DISABLE, 0); | ||
1899 | |||
1900 | /* setup and enable the encoder and transmitter */ | ||
1901 | atombios_dig_encoder_setup(encoder, ATOM_ENABLE, 0); | ||
1902 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_SETUP, 0, 0); | ||
1903 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE, 0, 0); | ||
1904 | } | ||
1905 | break; | 1926 | break; |
1906 | case ENCODER_OBJECT_ID_INTERNAL_DDI: | 1927 | case ENCODER_OBJECT_ID_INTERNAL_DDI: |
1907 | case ENCODER_OBJECT_ID_INTERNAL_DVO1: | 1928 | case ENCODER_OBJECT_ID_INTERNAL_DVO1: |
@@ -1922,14 +1943,6 @@ radeon_atom_encoder_mode_set(struct drm_encoder *encoder, | |||
1922 | break; | 1943 | break; |
1923 | } | 1944 | } |
1924 | 1945 | ||
1925 | if (ext_encoder) { | ||
1926 | if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE61(rdev)) | ||
1927 | atombios_external_encoder_setup(encoder, ext_encoder, | ||
1928 | EXTERNAL_ENCODER_ACTION_V3_ENCODER_SETUP); | ||
1929 | else | ||
1930 | atombios_external_encoder_setup(encoder, ext_encoder, ATOM_ENABLE); | ||
1931 | } | ||
1932 | |||
1933 | atombios_apply_encoder_quirks(encoder, adjusted_mode); | 1946 | atombios_apply_encoder_quirks(encoder, adjusted_mode); |
1934 | 1947 | ||
1935 | if (atombios_get_encoder_mode(encoder) == ATOM_ENCODER_MODE_HDMI) { | 1948 | if (atombios_get_encoder_mode(encoder) == ATOM_ENCODER_MODE_HDMI) { |
@@ -2116,7 +2129,6 @@ static void radeon_atom_encoder_prepare(struct drm_encoder *encoder) | |||
2116 | } | 2129 | } |
2117 | 2130 | ||
2118 | radeon_atom_output_lock(encoder, true); | 2131 | radeon_atom_output_lock(encoder, true); |
2119 | radeon_atom_encoder_dpms(encoder, DRM_MODE_DPMS_OFF); | ||
2120 | 2132 | ||
2121 | if (connector) { | 2133 | if (connector) { |
2122 | struct radeon_connector *radeon_connector = to_radeon_connector(connector); | 2134 | struct radeon_connector *radeon_connector = to_radeon_connector(connector); |
@@ -2137,6 +2149,7 @@ static void radeon_atom_encoder_prepare(struct drm_encoder *encoder) | |||
2137 | 2149 | ||
2138 | static void radeon_atom_encoder_commit(struct drm_encoder *encoder) | 2150 | static void radeon_atom_encoder_commit(struct drm_encoder *encoder) |
2139 | { | 2151 | { |
2152 | /* need to call this here as we need the crtc set up */ | ||
2140 | radeon_atom_encoder_dpms(encoder, DRM_MODE_DPMS_ON); | 2153 | radeon_atom_encoder_dpms(encoder, DRM_MODE_DPMS_ON); |
2141 | radeon_atom_output_lock(encoder, false); | 2154 | radeon_atom_output_lock(encoder, false); |
2142 | } | 2155 | } |
@@ -2177,14 +2190,7 @@ static void radeon_atom_encoder_disable(struct drm_encoder *encoder) | |||
2177 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: | 2190 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: |
2178 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: | 2191 | case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: |
2179 | case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA: | 2192 | case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA: |
2180 | if (ASIC_IS_DCE4(rdev)) | 2193 | /* handled in dpms */ |
2181 | /* disable the transmitter */ | ||
2182 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
2183 | else { | ||
2184 | /* disable the encoder and transmitter */ | ||
2185 | atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_DISABLE, 0, 0); | ||
2186 | atombios_dig_encoder_setup(encoder, ATOM_DISABLE, 0); | ||
2187 | } | ||
2188 | break; | 2194 | break; |
2189 | case ENCODER_OBJECT_ID_INTERNAL_DDI: | 2195 | case ENCODER_OBJECT_ID_INTERNAL_DDI: |
2190 | case ENCODER_OBJECT_ID_INTERNAL_DVO1: | 2196 | case ENCODER_OBJECT_ID_INTERNAL_DVO1: |
diff --git a/drivers/gpu/drm/radeon/r600_cs.c b/drivers/gpu/drm/radeon/r600_cs.c index ab74e6b149e7..f37676d7f217 100644 --- a/drivers/gpu/drm/radeon/r600_cs.c +++ b/drivers/gpu/drm/radeon/r600_cs.c | |||
@@ -63,6 +63,7 @@ struct r600_cs_track { | |||
63 | u32 cb_color_size_idx[8]; /* unused */ | 63 | u32 cb_color_size_idx[8]; /* unused */ |
64 | u32 cb_target_mask; | 64 | u32 cb_target_mask; |
65 | u32 cb_shader_mask; /* unused */ | 65 | u32 cb_shader_mask; /* unused */ |
66 | bool is_resolve; | ||
66 | u32 cb_color_size[8]; | 67 | u32 cb_color_size[8]; |
67 | u32 vgt_strmout_en; | 68 | u32 vgt_strmout_en; |
68 | u32 vgt_strmout_buffer_en; | 69 | u32 vgt_strmout_buffer_en; |
@@ -315,7 +316,15 @@ static void r600_cs_track_init(struct r600_cs_track *track) | |||
315 | track->cb_color_bo[i] = NULL; | 316 | track->cb_color_bo[i] = NULL; |
316 | track->cb_color_bo_offset[i] = 0xFFFFFFFF; | 317 | track->cb_color_bo_offset[i] = 0xFFFFFFFF; |
317 | track->cb_color_bo_mc[i] = 0xFFFFFFFF; | 318 | track->cb_color_bo_mc[i] = 0xFFFFFFFF; |
318 | } | 319 | track->cb_color_frag_bo[i] = NULL; |
320 | track->cb_color_frag_offset[i] = 0xFFFFFFFF; | ||
321 | track->cb_color_tile_bo[i] = NULL; | ||
322 | track->cb_color_tile_offset[i] = 0xFFFFFFFF; | ||
323 | track->cb_color_mask[i] = 0xFFFFFFFF; | ||
324 | } | ||
325 | track->is_resolve = false; | ||
326 | track->nsamples = 16; | ||
327 | track->log_nsamples = 4; | ||
319 | track->cb_target_mask = 0xFFFFFFFF; | 328 | track->cb_target_mask = 0xFFFFFFFF; |
320 | track->cb_shader_mask = 0xFFFFFFFF; | 329 | track->cb_shader_mask = 0xFFFFFFFF; |
321 | track->cb_dirty = true; | 330 | track->cb_dirty = true; |
@@ -352,6 +361,8 @@ static int r600_cs_track_validate_cb(struct radeon_cs_parser *p, int i) | |||
352 | volatile u32 *ib = p->ib.ptr; | 361 | volatile u32 *ib = p->ib.ptr; |
353 | unsigned array_mode; | 362 | unsigned array_mode; |
354 | u32 format; | 363 | u32 format; |
364 | /* When resolve is used, the second colorbuffer has always 1 sample. */ | ||
365 | unsigned nsamples = track->is_resolve && i == 1 ? 1 : track->nsamples; | ||
355 | 366 | ||
356 | size = radeon_bo_size(track->cb_color_bo[i]) - track->cb_color_bo_offset[i]; | 367 | size = radeon_bo_size(track->cb_color_bo[i]) - track->cb_color_bo_offset[i]; |
357 | format = G_0280A0_FORMAT(track->cb_color_info[i]); | 368 | format = G_0280A0_FORMAT(track->cb_color_info[i]); |
@@ -375,7 +386,7 @@ static int r600_cs_track_validate_cb(struct radeon_cs_parser *p, int i) | |||
375 | array_check.group_size = track->group_size; | 386 | array_check.group_size = track->group_size; |
376 | array_check.nbanks = track->nbanks; | 387 | array_check.nbanks = track->nbanks; |
377 | array_check.npipes = track->npipes; | 388 | array_check.npipes = track->npipes; |
378 | array_check.nsamples = track->nsamples; | 389 | array_check.nsamples = nsamples; |
379 | array_check.blocksize = r600_fmt_get_blocksize(format); | 390 | array_check.blocksize = r600_fmt_get_blocksize(format); |
380 | if (r600_get_array_mode_alignment(&array_check, | 391 | if (r600_get_array_mode_alignment(&array_check, |
381 | &pitch_align, &height_align, &depth_align, &base_align)) { | 392 | &pitch_align, &height_align, &depth_align, &base_align)) { |
@@ -421,7 +432,7 @@ static int r600_cs_track_validate_cb(struct radeon_cs_parser *p, int i) | |||
421 | 432 | ||
422 | /* check offset */ | 433 | /* check offset */ |
423 | tmp = r600_fmt_get_nblocksy(format, height) * r600_fmt_get_nblocksx(format, pitch) * | 434 | tmp = r600_fmt_get_nblocksy(format, height) * r600_fmt_get_nblocksx(format, pitch) * |
424 | r600_fmt_get_blocksize(format) * track->nsamples; | 435 | r600_fmt_get_blocksize(format) * nsamples; |
425 | switch (array_mode) { | 436 | switch (array_mode) { |
426 | default: | 437 | default: |
427 | case V_0280A0_ARRAY_LINEAR_GENERAL: | 438 | case V_0280A0_ARRAY_LINEAR_GENERAL: |
@@ -792,6 +803,12 @@ static int r600_cs_track_check(struct radeon_cs_parser *p) | |||
792 | */ | 803 | */ |
793 | if (track->cb_dirty) { | 804 | if (track->cb_dirty) { |
794 | tmp = track->cb_target_mask; | 805 | tmp = track->cb_target_mask; |
806 | |||
807 | /* We must check both colorbuffers for RESOLVE. */ | ||
808 | if (track->is_resolve) { | ||
809 | tmp |= 0xff; | ||
810 | } | ||
811 | |||
795 | for (i = 0; i < 8; i++) { | 812 | for (i = 0; i < 8; i++) { |
796 | if ((tmp >> (i * 4)) & 0xF) { | 813 | if ((tmp >> (i * 4)) & 0xF) { |
797 | /* at least one component is enabled */ | 814 | /* at least one component is enabled */ |
@@ -1281,6 +1298,11 @@ static int r600_cs_check_reg(struct radeon_cs_parser *p, u32 reg, u32 idx) | |||
1281 | track->nsamples = 1 << tmp; | 1298 | track->nsamples = 1 << tmp; |
1282 | track->cb_dirty = true; | 1299 | track->cb_dirty = true; |
1283 | break; | 1300 | break; |
1301 | case R_028808_CB_COLOR_CONTROL: | ||
1302 | tmp = G_028808_SPECIAL_OP(radeon_get_ib_value(p, idx)); | ||
1303 | track->is_resolve = tmp == V_028808_SPECIAL_RESOLVE_BOX; | ||
1304 | track->cb_dirty = true; | ||
1305 | break; | ||
1284 | case R_0280A0_CB_COLOR0_INFO: | 1306 | case R_0280A0_CB_COLOR0_INFO: |
1285 | case R_0280A4_CB_COLOR1_INFO: | 1307 | case R_0280A4_CB_COLOR1_INFO: |
1286 | case R_0280A8_CB_COLOR2_INFO: | 1308 | case R_0280A8_CB_COLOR2_INFO: |
@@ -1416,7 +1438,7 @@ static int r600_cs_check_reg(struct radeon_cs_parser *p, u32 reg, u32 idx) | |||
1416 | case R_028118_CB_COLOR6_MASK: | 1438 | case R_028118_CB_COLOR6_MASK: |
1417 | case R_02811C_CB_COLOR7_MASK: | 1439 | case R_02811C_CB_COLOR7_MASK: |
1418 | tmp = (reg - R_028100_CB_COLOR0_MASK) / 4; | 1440 | tmp = (reg - R_028100_CB_COLOR0_MASK) / 4; |
1419 | track->cb_color_mask[tmp] = ib[idx]; | 1441 | track->cb_color_mask[tmp] = radeon_get_ib_value(p, idx); |
1420 | if (G_0280A0_TILE_MODE(track->cb_color_info[tmp])) { | 1442 | if (G_0280A0_TILE_MODE(track->cb_color_info[tmp])) { |
1421 | track->cb_dirty = true; | 1443 | track->cb_dirty = true; |
1422 | } | 1444 | } |
diff --git a/drivers/gpu/drm/radeon/r600d.h b/drivers/gpu/drm/radeon/r600d.h index bdb69a63062f..fa6f37099ba9 100644 --- a/drivers/gpu/drm/radeon/r600d.h +++ b/drivers/gpu/drm/radeon/r600d.h | |||
@@ -66,6 +66,14 @@ | |||
66 | #define CC_RB_BACKEND_DISABLE 0x98F4 | 66 | #define CC_RB_BACKEND_DISABLE 0x98F4 |
67 | #define BACKEND_DISABLE(x) ((x) << 16) | 67 | #define BACKEND_DISABLE(x) ((x) << 16) |
68 | 68 | ||
69 | #define R_028808_CB_COLOR_CONTROL 0x28808 | ||
70 | #define S_028808_SPECIAL_OP(x) (((x) & 0x7) << 4) | ||
71 | #define G_028808_SPECIAL_OP(x) (((x) >> 4) & 0x7) | ||
72 | #define C_028808_SPECIAL_OP 0xFFFFFF8F | ||
73 | #define V_028808_SPECIAL_NORMAL 0x00 | ||
74 | #define V_028808_SPECIAL_DISABLE 0x01 | ||
75 | #define V_028808_SPECIAL_RESOLVE_BOX 0x07 | ||
76 | |||
69 | #define CB_COLOR0_BASE 0x28040 | 77 | #define CB_COLOR0_BASE 0x28040 |
70 | #define CB_COLOR1_BASE 0x28044 | 78 | #define CB_COLOR1_BASE 0x28044 |
71 | #define CB_COLOR2_BASE 0x28048 | 79 | #define CB_COLOR2_BASE 0x28048 |
diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c index d2e243867ac6..7a3daebd732d 100644 --- a/drivers/gpu/drm/radeon/radeon_device.c +++ b/drivers/gpu/drm/radeon/radeon_device.c | |||
@@ -1051,7 +1051,7 @@ int radeon_device_init(struct radeon_device *rdev, | |||
1051 | if (rdev->flags & RADEON_IS_AGP) | 1051 | if (rdev->flags & RADEON_IS_AGP) |
1052 | rdev->need_dma32 = true; | 1052 | rdev->need_dma32 = true; |
1053 | if ((rdev->flags & RADEON_IS_PCI) && | 1053 | if ((rdev->flags & RADEON_IS_PCI) && |
1054 | (rdev->family < CHIP_RS400)) | 1054 | (rdev->family <= CHIP_RS740)) |
1055 | rdev->need_dma32 = true; | 1055 | rdev->need_dma32 = true; |
1056 | 1056 | ||
1057 | dma_bits = rdev->need_dma32 ? 32 : 40; | 1057 | dma_bits = rdev->need_dma32 ? 32 : 40; |
@@ -1346,12 +1346,15 @@ retry: | |||
1346 | for (i = 0; i < RADEON_NUM_RINGS; ++i) { | 1346 | for (i = 0; i < RADEON_NUM_RINGS; ++i) { |
1347 | radeon_ring_restore(rdev, &rdev->ring[i], | 1347 | radeon_ring_restore(rdev, &rdev->ring[i], |
1348 | ring_sizes[i], ring_data[i]); | 1348 | ring_sizes[i], ring_data[i]); |
1349 | ring_sizes[i] = 0; | ||
1350 | ring_data[i] = NULL; | ||
1349 | } | 1351 | } |
1350 | 1352 | ||
1351 | r = radeon_ib_ring_tests(rdev); | 1353 | r = radeon_ib_ring_tests(rdev); |
1352 | if (r) { | 1354 | if (r) { |
1353 | dev_err(rdev->dev, "ib ring test failed (%d).\n", r); | 1355 | dev_err(rdev->dev, "ib ring test failed (%d).\n", r); |
1354 | if (saved) { | 1356 | if (saved) { |
1357 | saved = false; | ||
1355 | radeon_suspend(rdev); | 1358 | radeon_suspend(rdev); |
1356 | goto retry; | 1359 | goto retry; |
1357 | } | 1360 | } |
diff --git a/drivers/gpu/drm/radeon/radeon_drv.c b/drivers/gpu/drm/radeon/radeon_drv.c index 27d22d709c90..8c593ea82c41 100644 --- a/drivers/gpu/drm/radeon/radeon_drv.c +++ b/drivers/gpu/drm/radeon/radeon_drv.c | |||
@@ -63,9 +63,10 @@ | |||
63 | * 2.19.0 - r600-eg: MSAA textures | 63 | * 2.19.0 - r600-eg: MSAA textures |
64 | * 2.20.0 - r600-si: RADEON_INFO_TIMESTAMP query | 64 | * 2.20.0 - r600-si: RADEON_INFO_TIMESTAMP query |
65 | * 2.21.0 - r600-r700: FMASK and CMASK | 65 | * 2.21.0 - r600-r700: FMASK and CMASK |
66 | * 2.22.0 - r600 only: RESOLVE_BOX allowed | ||
66 | */ | 67 | */ |
67 | #define KMS_DRIVER_MAJOR 2 | 68 | #define KMS_DRIVER_MAJOR 2 |
68 | #define KMS_DRIVER_MINOR 21 | 69 | #define KMS_DRIVER_MINOR 22 |
69 | #define KMS_DRIVER_PATCHLEVEL 0 | 70 | #define KMS_DRIVER_PATCHLEVEL 0 |
70 | int radeon_driver_load_kms(struct drm_device *dev, unsigned long flags); | 71 | int radeon_driver_load_kms(struct drm_device *dev, unsigned long flags); |
71 | int radeon_driver_unload_kms(struct drm_device *dev); | 72 | int radeon_driver_unload_kms(struct drm_device *dev); |
diff --git a/drivers/gpu/drm/radeon/radeon_fence.c b/drivers/gpu/drm/radeon/radeon_fence.c index 7b737b9339ad..2a59375dbe52 100644 --- a/drivers/gpu/drm/radeon/radeon_fence.c +++ b/drivers/gpu/drm/radeon/radeon_fence.c | |||
@@ -131,7 +131,7 @@ int radeon_fence_emit(struct radeon_device *rdev, | |||
131 | */ | 131 | */ |
132 | void radeon_fence_process(struct radeon_device *rdev, int ring) | 132 | void radeon_fence_process(struct radeon_device *rdev, int ring) |
133 | { | 133 | { |
134 | uint64_t seq, last_seq; | 134 | uint64_t seq, last_seq, last_emitted; |
135 | unsigned count_loop = 0; | 135 | unsigned count_loop = 0; |
136 | bool wake = false; | 136 | bool wake = false; |
137 | 137 | ||
@@ -158,13 +158,15 @@ void radeon_fence_process(struct radeon_device *rdev, int ring) | |||
158 | */ | 158 | */ |
159 | last_seq = atomic64_read(&rdev->fence_drv[ring].last_seq); | 159 | last_seq = atomic64_read(&rdev->fence_drv[ring].last_seq); |
160 | do { | 160 | do { |
161 | last_emitted = rdev->fence_drv[ring].sync_seq[ring]; | ||
161 | seq = radeon_fence_read(rdev, ring); | 162 | seq = radeon_fence_read(rdev, ring); |
162 | seq |= last_seq & 0xffffffff00000000LL; | 163 | seq |= last_seq & 0xffffffff00000000LL; |
163 | if (seq < last_seq) { | 164 | if (seq < last_seq) { |
164 | seq += 0x100000000LL; | 165 | seq &= 0xffffffff; |
166 | seq |= last_emitted & 0xffffffff00000000LL; | ||
165 | } | 167 | } |
166 | 168 | ||
167 | if (seq == last_seq) { | 169 | if (seq <= last_seq || seq > last_emitted) { |
168 | break; | 170 | break; |
169 | } | 171 | } |
170 | /* If we loop over we don't want to return without | 172 | /* If we loop over we don't want to return without |
diff --git a/drivers/gpu/drm/radeon/reg_srcs/r600 b/drivers/gpu/drm/radeon/reg_srcs/r600 index f93e45d869f4..20bfbda7b3f1 100644 --- a/drivers/gpu/drm/radeon/reg_srcs/r600 +++ b/drivers/gpu/drm/radeon/reg_srcs/r600 | |||
@@ -744,7 +744,6 @@ r600 0x9400 | |||
744 | 0x00028C38 CB_CLRCMP_DST | 744 | 0x00028C38 CB_CLRCMP_DST |
745 | 0x00028C3C CB_CLRCMP_MSK | 745 | 0x00028C3C CB_CLRCMP_MSK |
746 | 0x00028C34 CB_CLRCMP_SRC | 746 | 0x00028C34 CB_CLRCMP_SRC |
747 | 0x00028808 CB_COLOR_CONTROL | ||
748 | 0x0002842C CB_FOG_BLUE | 747 | 0x0002842C CB_FOG_BLUE |
749 | 0x00028428 CB_FOG_GREEN | 748 | 0x00028428 CB_FOG_GREEN |
750 | 0x00028424 CB_FOG_RED | 749 | 0x00028424 CB_FOG_RED |