Commit d5445a17 authored by Alex Deucher's avatar Alex Deucher

drm/radeon: update r600 set/get pcie lane config

Updated to the preferred programming sequence.
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 492d2b61
...@@ -4523,7 +4523,7 @@ void r600_ioctl_wait_idle(struct radeon_device *rdev, struct radeon_bo *bo) ...@@ -4523,7 +4523,7 @@ void r600_ioctl_wait_idle(struct radeon_device *rdev, struct radeon_bo *bo)
void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes) void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes)
{ {
u32 link_width_cntl, mask, target_reg; u32 link_width_cntl, mask;
if (rdev->flags & RADEON_IS_IGP) if (rdev->flags & RADEON_IS_IGP)
return; return;
...@@ -4535,7 +4535,7 @@ void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes) ...@@ -4535,7 +4535,7 @@ void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes)
if (ASIC_IS_X2(rdev)) if (ASIC_IS_X2(rdev))
return; return;
/* FIXME wait for idle */ radeon_gui_idle(rdev);
switch (lanes) { switch (lanes) {
case 0: case 0:
...@@ -4554,53 +4554,24 @@ void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes) ...@@ -4554,53 +4554,24 @@ void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes)
mask = RADEON_PCIE_LC_LINK_WIDTH_X8; mask = RADEON_PCIE_LC_LINK_WIDTH_X8;
break; break;
case 12: case 12:
/* not actually supported */
mask = RADEON_PCIE_LC_LINK_WIDTH_X12; mask = RADEON_PCIE_LC_LINK_WIDTH_X12;
break; break;
case 16: case 16:
default:
mask = RADEON_PCIE_LC_LINK_WIDTH_X16; mask = RADEON_PCIE_LC_LINK_WIDTH_X16;
break; break;
default:
DRM_ERROR("invalid pcie lane request: %d\n", lanes);
return;
} }
link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL); link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL);
link_width_cntl &= ~RADEON_PCIE_LC_LINK_WIDTH_MASK;
if ((link_width_cntl & RADEON_PCIE_LC_LINK_WIDTH_RD_MASK) == link_width_cntl |= mask << RADEON_PCIE_LC_LINK_WIDTH_SHIFT;
(mask << RADEON_PCIE_LC_LINK_WIDTH_RD_SHIFT)) link_width_cntl |= (RADEON_PCIE_LC_RECONFIG_NOW |
return; R600_PCIE_LC_RECONFIG_ARC_MISSING_ESCAPE);
if (link_width_cntl & R600_PCIE_LC_UPCONFIGURE_DIS)
return;
link_width_cntl &= ~(RADEON_PCIE_LC_LINK_WIDTH_MASK |
RADEON_PCIE_LC_RECONFIG_NOW |
R600_PCIE_LC_RENEGOTIATE_EN |
R600_PCIE_LC_RECONFIG_ARC_MISSING_ESCAPE);
link_width_cntl |= mask;
WREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); WREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl);
/* some northbridges can renegotiate the link rather than requiring
* a complete re-config.
* e.g., AMD 780/790 northbridges (pci ids: 0x5956, 0x5957, 0x5958, etc.)
*/
if (link_width_cntl & R600_PCIE_LC_RENEGOTIATION_SUPPORT)
link_width_cntl |= R600_PCIE_LC_RENEGOTIATE_EN | R600_PCIE_LC_UPCONFIGURE_SUPPORT;
else
link_width_cntl |= R600_PCIE_LC_RECONFIG_ARC_MISSING_ESCAPE;
WREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL, (link_width_cntl |
RADEON_PCIE_LC_RECONFIG_NOW));
if (rdev->family >= CHIP_RV770)
target_reg = R700_TARGET_AND_CURRENT_PROFILE_INDEX;
else
target_reg = R600_TARGET_AND_CURRENT_PROFILE_INDEX;
/* wait for lane set to complete */
link_width_cntl = RREG32(target_reg);
while (link_width_cntl == 0xffffffff)
link_width_cntl = RREG32(target_reg);
} }
int r600_get_pcie_lanes(struct radeon_device *rdev) int r600_get_pcie_lanes(struct radeon_device *rdev)
...@@ -4617,13 +4588,11 @@ int r600_get_pcie_lanes(struct radeon_device *rdev) ...@@ -4617,13 +4588,11 @@ int r600_get_pcie_lanes(struct radeon_device *rdev)
if (ASIC_IS_X2(rdev)) if (ASIC_IS_X2(rdev))
return 0; return 0;
/* FIXME wait for idle */ radeon_gui_idle(rdev);
link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL); link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL);
switch ((link_width_cntl & RADEON_PCIE_LC_LINK_WIDTH_RD_MASK) >> RADEON_PCIE_LC_LINK_WIDTH_RD_SHIFT) { switch ((link_width_cntl & RADEON_PCIE_LC_LINK_WIDTH_RD_MASK) >> RADEON_PCIE_LC_LINK_WIDTH_RD_SHIFT) {
case RADEON_PCIE_LC_LINK_WIDTH_X0:
return 0;
case RADEON_PCIE_LC_LINK_WIDTH_X1: case RADEON_PCIE_LC_LINK_WIDTH_X1:
return 1; return 1;
case RADEON_PCIE_LC_LINK_WIDTH_X2: case RADEON_PCIE_LC_LINK_WIDTH_X2:
...@@ -4632,6 +4601,10 @@ int r600_get_pcie_lanes(struct radeon_device *rdev) ...@@ -4632,6 +4601,10 @@ int r600_get_pcie_lanes(struct radeon_device *rdev)
return 4; return 4;
case RADEON_PCIE_LC_LINK_WIDTH_X8: case RADEON_PCIE_LC_LINK_WIDTH_X8:
return 8; return 8;
case RADEON_PCIE_LC_LINK_WIDTH_X12:
/* not actually supported */
return 12;
case RADEON_PCIE_LC_LINK_WIDTH_X0:
case RADEON_PCIE_LC_LINK_WIDTH_X16: case RADEON_PCIE_LC_LINK_WIDTH_X16:
default: default:
return 16; return 16;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment