diff options
author | Christian König <christian.koenig@amd.com> | 2014-08-26 08:45:54 -0400 |
---|---|---|
committer | Alex Deucher <alexander.deucher@amd.com> | 2014-08-26 12:20:38 -0400 |
commit | 054e01d681b457ab50bdf1f22c0f0d1ad03afd70 (patch) | |
tree | bc43a50fe294caff637d3aef90dc4872904cb0dd | |
parent | a284e9d14e35b776807c3a40dd1ff1e05429d4a4 (diff) |
drm/radeon: save/restore the PD addr on suspend/resume
This fixes a problem with GPU resets and TLB flushes on SI/CIK.
Signed-off-by: Christian König <christian.koenig@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
-rw-r--r-- | drivers/gpu/drm/radeon/cik.c | 20 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/ni.c | 9 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon.h | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/si.c | 15 |
4 files changed, 37 insertions, 9 deletions
diff --git a/drivers/gpu/drm/radeon/cik.c b/drivers/gpu/drm/radeon/cik.c index 79a5a5519bd6..e57698847be5 100644 --- a/drivers/gpu/drm/radeon/cik.c +++ b/drivers/gpu/drm/radeon/cik.c | |||
@@ -5749,20 +5749,17 @@ static int cik_pcie_gart_enable(struct radeon_device *rdev) | |||
5749 | WREG32(0x15D8, 0); | 5749 | WREG32(0x15D8, 0); |
5750 | WREG32(0x15DC, 0); | 5750 | WREG32(0x15DC, 0); |
5751 | 5751 | ||
5752 | /* empty context1-15 */ | 5752 | /* restore context1-15 */ |
5753 | /* FIXME start with 4G, once using 2 level pt switch to full | ||
5754 | * vm size space | ||
5755 | */ | ||
5756 | /* set vm size, must be a multiple of 4 */ | 5753 | /* set vm size, must be a multiple of 4 */ |
5757 | WREG32(VM_CONTEXT1_PAGE_TABLE_START_ADDR, 0); | 5754 | WREG32(VM_CONTEXT1_PAGE_TABLE_START_ADDR, 0); |
5758 | WREG32(VM_CONTEXT1_PAGE_TABLE_END_ADDR, rdev->vm_manager.max_pfn); | 5755 | WREG32(VM_CONTEXT1_PAGE_TABLE_END_ADDR, rdev->vm_manager.max_pfn); |
5759 | for (i = 1; i < 16; i++) { | 5756 | for (i = 1; i < 16; i++) { |
5760 | if (i < 8) | 5757 | if (i < 8) |
5761 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), | 5758 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), |
5762 | rdev->gart.table_addr >> 12); | 5759 | rdev->vm_manager.saved_table_addr[i]); |
5763 | else | 5760 | else |
5764 | WREG32(VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2), | 5761 | WREG32(VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2), |
5765 | rdev->gart.table_addr >> 12); | 5762 | rdev->vm_manager.saved_table_addr[i]); |
5766 | } | 5763 | } |
5767 | 5764 | ||
5768 | /* enable context1-15 */ | 5765 | /* enable context1-15 */ |
@@ -5827,6 +5824,17 @@ static int cik_pcie_gart_enable(struct radeon_device *rdev) | |||
5827 | */ | 5824 | */ |
5828 | static void cik_pcie_gart_disable(struct radeon_device *rdev) | 5825 | static void cik_pcie_gart_disable(struct radeon_device *rdev) |
5829 | { | 5826 | { |
5827 | unsigned i; | ||
5828 | |||
5829 | for (i = 1; i < 16; ++i) { | ||
5830 | uint32_t reg; | ||
5831 | if (i < 8) | ||
5832 | reg = VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2); | ||
5833 | else | ||
5834 | reg = VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2); | ||
5835 | rdev->vm_manager.saved_table_addr[i] = RREG32(reg); | ||
5836 | } | ||
5837 | |||
5830 | /* Disable all tables */ | 5838 | /* Disable all tables */ |
5831 | WREG32(VM_CONTEXT0_CNTL, 0); | 5839 | WREG32(VM_CONTEXT0_CNTL, 0); |
5832 | WREG32(VM_CONTEXT1_CNTL, 0); | 5840 | WREG32(VM_CONTEXT1_CNTL, 0); |
diff --git a/drivers/gpu/drm/radeon/ni.c b/drivers/gpu/drm/radeon/ni.c index ba89375f197f..3faee58946dd 100644 --- a/drivers/gpu/drm/radeon/ni.c +++ b/drivers/gpu/drm/radeon/ni.c | |||
@@ -1271,7 +1271,7 @@ static int cayman_pcie_gart_enable(struct radeon_device *rdev) | |||
1271 | WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR + (i << 2), 0); | 1271 | WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR + (i << 2), 0); |
1272 | WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR + (i << 2), rdev->vm_manager.max_pfn); | 1272 | WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR + (i << 2), rdev->vm_manager.max_pfn); |
1273 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), | 1273 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), |
1274 | rdev->gart.table_addr >> 12); | 1274 | rdev->vm_manager.saved_table_addr[i]); |
1275 | } | 1275 | } |
1276 | 1276 | ||
1277 | /* enable context1-7 */ | 1277 | /* enable context1-7 */ |
@@ -1303,6 +1303,13 @@ static int cayman_pcie_gart_enable(struct radeon_device *rdev) | |||
1303 | 1303 | ||
1304 | static void cayman_pcie_gart_disable(struct radeon_device *rdev) | 1304 | static void cayman_pcie_gart_disable(struct radeon_device *rdev) |
1305 | { | 1305 | { |
1306 | unsigned i; | ||
1307 | |||
1308 | for (i = 1; i < 8; ++i) { | ||
1309 | rdev->vm_manager.saved_table_addr[i] = RREG32( | ||
1310 | VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2)); | ||
1311 | } | ||
1312 | |||
1306 | /* Disable all tables */ | 1313 | /* Disable all tables */ |
1307 | WREG32(VM_CONTEXT0_CNTL, 0); | 1314 | WREG32(VM_CONTEXT0_CNTL, 0); |
1308 | WREG32(VM_CONTEXT1_CNTL, 0); | 1315 | WREG32(VM_CONTEXT1_CNTL, 0); |
diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h index b281886f6f51..5f05b4c84338 100644 --- a/drivers/gpu/drm/radeon/radeon.h +++ b/drivers/gpu/drm/radeon/radeon.h | |||
@@ -915,6 +915,8 @@ struct radeon_vm_manager { | |||
915 | u64 vram_base_offset; | 915 | u64 vram_base_offset; |
916 | /* is vm enabled? */ | 916 | /* is vm enabled? */ |
917 | bool enabled; | 917 | bool enabled; |
918 | /* for hw to save the PD addr on suspend/resume */ | ||
919 | uint32_t saved_table_addr[RADEON_NUM_VM]; | ||
918 | }; | 920 | }; |
919 | 921 | ||
920 | /* | 922 | /* |
diff --git a/drivers/gpu/drm/radeon/si.c b/drivers/gpu/drm/radeon/si.c index a1274a31405c..739e0a5349f8 100644 --- a/drivers/gpu/drm/radeon/si.c +++ b/drivers/gpu/drm/radeon/si.c | |||
@@ -4290,10 +4290,10 @@ static int si_pcie_gart_enable(struct radeon_device *rdev) | |||
4290 | for (i = 1; i < 16; i++) { | 4290 | for (i = 1; i < 16; i++) { |
4291 | if (i < 8) | 4291 | if (i < 8) |
4292 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), | 4292 | WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2), |
4293 | rdev->gart.table_addr >> 12); | 4293 | rdev->vm_manager.saved_table_addr[i]); |
4294 | else | 4294 | else |
4295 | WREG32(VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2), | 4295 | WREG32(VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2), |
4296 | rdev->gart.table_addr >> 12); | 4296 | rdev->vm_manager.saved_table_addr[i]); |
4297 | } | 4297 | } |
4298 | 4298 | ||
4299 | /* enable context1-15 */ | 4299 | /* enable context1-15 */ |
@@ -4325,6 +4325,17 @@ static int si_pcie_gart_enable(struct radeon_device *rdev) | |||
4325 | 4325 | ||
4326 | static void si_pcie_gart_disable(struct radeon_device *rdev) | 4326 | static void si_pcie_gart_disable(struct radeon_device *rdev) |
4327 | { | 4327 | { |
4328 | unsigned i; | ||
4329 | |||
4330 | for (i = 1; i < 16; ++i) { | ||
4331 | uint32_t reg; | ||
4332 | if (i < 8) | ||
4333 | reg = VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2); | ||
4334 | else | ||
4335 | reg = VM_CONTEXT8_PAGE_TABLE_BASE_ADDR + ((i - 8) << 2); | ||
4336 | rdev->vm_manager.saved_table_addr[i] = RREG32(reg); | ||
4337 | } | ||
4338 | |||
4328 | /* Disable all tables */ | 4339 | /* Disable all tables */ |
4329 | WREG32(VM_CONTEXT0_CNTL, 0); | 4340 | WREG32(VM_CONTEXT0_CNTL, 0); |
4330 | WREG32(VM_CONTEXT1_CNTL, 0); | 4341 | WREG32(VM_CONTEXT1_CNTL, 0); |