diff options
author | Chunming Zhou <david1.zhou@amd.com> | 2015-08-25 05:23:45 -0400 |
---|---|---|
committer | Alex Deucher <alexander.deucher@amd.com> | 2015-08-26 17:50:42 -0400 |
commit | c7ae72c01be10f539f385f624713f8ba0aa11a8f (patch) | |
tree | c523633396afdeede8a47c386436bf0dd4e541ac /drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | |
parent | 113cd9dacbad4906e1c8db09233b9fdcb002f80d (diff) |
drm/amdgpu: use IB for copy buffer of eviction
This aids handling buffers moves with the scheduler.
Signed-off-by: Chunming Zhou <david1.zhou@amd.com>
Reviewed-by: Christian K?nig <christian.koenig@amd.com>
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c')
-rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | 77 |
1 files changed, 40 insertions, 37 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index 4cb81320b045..399143541d8a 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | |||
@@ -228,7 +228,7 @@ static int amdgpu_move_blit(struct ttm_buffer_object *bo, | |||
228 | struct amdgpu_device *adev; | 228 | struct amdgpu_device *adev; |
229 | struct amdgpu_ring *ring; | 229 | struct amdgpu_ring *ring; |
230 | uint64_t old_start, new_start; | 230 | uint64_t old_start, new_start; |
231 | struct amdgpu_fence *fence; | 231 | struct fence *fence; |
232 | int r; | 232 | int r; |
233 | 233 | ||
234 | adev = amdgpu_get_adev(bo->bdev); | 234 | adev = amdgpu_get_adev(bo->bdev); |
@@ -269,9 +269,9 @@ static int amdgpu_move_blit(struct ttm_buffer_object *bo, | |||
269 | new_mem->num_pages * PAGE_SIZE, /* bytes */ | 269 | new_mem->num_pages * PAGE_SIZE, /* bytes */ |
270 | bo->resv, &fence); | 270 | bo->resv, &fence); |
271 | /* FIXME: handle copy error */ | 271 | /* FIXME: handle copy error */ |
272 | r = ttm_bo_move_accel_cleanup(bo, &fence->base, | 272 | r = ttm_bo_move_accel_cleanup(bo, fence, |
273 | evict, no_wait_gpu, new_mem); | 273 | evict, no_wait_gpu, new_mem); |
274 | amdgpu_fence_unref(&fence); | 274 | fence_put(fence); |
275 | return r; | 275 | return r; |
276 | } | 276 | } |
277 | 277 | ||
@@ -987,52 +987,48 @@ int amdgpu_copy_buffer(struct amdgpu_ring *ring, | |||
987 | uint64_t dst_offset, | 987 | uint64_t dst_offset, |
988 | uint32_t byte_count, | 988 | uint32_t byte_count, |
989 | struct reservation_object *resv, | 989 | struct reservation_object *resv, |
990 | struct amdgpu_fence **fence) | 990 | struct fence **fence) |
991 | { | 991 | { |
992 | struct amdgpu_device *adev = ring->adev; | 992 | struct amdgpu_device *adev = ring->adev; |
993 | struct amdgpu_sync sync; | ||
994 | uint32_t max_bytes; | 993 | uint32_t max_bytes; |
995 | unsigned num_loops, num_dw; | 994 | unsigned num_loops, num_dw; |
995 | struct amdgpu_ib *ib; | ||
996 | unsigned i; | 996 | unsigned i; |
997 | int r; | 997 | int r; |
998 | 998 | ||
999 | /* sync other rings */ | ||
1000 | amdgpu_sync_create(&sync); | ||
1001 | if (resv) { | ||
1002 | r = amdgpu_sync_resv(adev, &sync, resv, false); | ||
1003 | if (r) { | ||
1004 | DRM_ERROR("sync failed (%d).\n", r); | ||
1005 | amdgpu_sync_free(adev, &sync, NULL); | ||
1006 | return r; | ||
1007 | } | ||
1008 | } | ||
1009 | |||
1010 | max_bytes = adev->mman.buffer_funcs->copy_max_bytes; | 999 | max_bytes = adev->mman.buffer_funcs->copy_max_bytes; |
1011 | num_loops = DIV_ROUND_UP(byte_count, max_bytes); | 1000 | num_loops = DIV_ROUND_UP(byte_count, max_bytes); |
1012 | num_dw = num_loops * adev->mman.buffer_funcs->copy_num_dw; | 1001 | num_dw = num_loops * adev->mman.buffer_funcs->copy_num_dw; |
1013 | 1002 | ||
1014 | /* for fence and sync */ | 1003 | /* for IB padding */ |
1015 | num_dw += 64 + AMDGPU_NUM_SYNCS * 8; | 1004 | while (num_dw & 0x7) |
1005 | num_dw++; | ||
1006 | |||
1007 | ib = kzalloc(sizeof(struct amdgpu_ib), GFP_KERNEL); | ||
1008 | if (!ib) | ||
1009 | return -ENOMEM; | ||
1016 | 1010 | ||
1017 | r = amdgpu_sync_wait(&sync); | 1011 | r = amdgpu_ib_get(ring, NULL, num_dw * 4, ib); |
1018 | if (r) { | 1012 | if (r) { |
1019 | DRM_ERROR("sync wait failed (%d).\n", r); | 1013 | kfree(ib); |
1020 | amdgpu_sync_free(adev, &sync, NULL); | ||
1021 | return r; | 1014 | return r; |
1022 | } | 1015 | } |
1023 | 1016 | ||
1024 | r = amdgpu_ring_lock(ring, num_dw); | 1017 | ib->length_dw = 0; |
1025 | if (r) { | 1018 | |
1026 | DRM_ERROR("ring lock failed (%d).\n", r); | 1019 | if (resv) { |
1027 | amdgpu_sync_free(adev, &sync, NULL); | 1020 | r = amdgpu_sync_resv(adev, &ib->sync, resv, |
1028 | return r; | 1021 | AMDGPU_FENCE_OWNER_UNDEFINED); |
1022 | if (r) { | ||
1023 | DRM_ERROR("sync failed (%d).\n", r); | ||
1024 | goto error_free; | ||
1025 | } | ||
1029 | } | 1026 | } |
1030 | amdgpu_sync_rings(&sync, ring); | ||
1031 | 1027 | ||
1032 | for (i = 0; i < num_loops; i++) { | 1028 | for (i = 0; i < num_loops; i++) { |
1033 | uint32_t cur_size_in_bytes = min(byte_count, max_bytes); | 1029 | uint32_t cur_size_in_bytes = min(byte_count, max_bytes); |
1034 | 1030 | ||
1035 | amdgpu_emit_copy_buffer(adev, ring, src_offset, dst_offset, | 1031 | amdgpu_emit_copy_buffer(adev, ib, src_offset, dst_offset, |
1036 | cur_size_in_bytes); | 1032 | cur_size_in_bytes); |
1037 | 1033 | ||
1038 | src_offset += cur_size_in_bytes; | 1034 | src_offset += cur_size_in_bytes; |
@@ -1040,17 +1036,24 @@ int amdgpu_copy_buffer(struct amdgpu_ring *ring, | |||
1040 | byte_count -= cur_size_in_bytes; | 1036 | byte_count -= cur_size_in_bytes; |
1041 | } | 1037 | } |
1042 | 1038 | ||
1043 | r = amdgpu_fence_emit(ring, AMDGPU_FENCE_OWNER_MOVE, fence); | 1039 | amdgpu_vm_pad_ib(adev, ib); |
1044 | if (r) { | 1040 | WARN_ON(ib->length_dw > num_dw); |
1045 | amdgpu_ring_unlock_undo(ring); | 1041 | r = amdgpu_sched_ib_submit_kernel_helper(adev, ring, ib, 1, |
1046 | amdgpu_sync_free(adev, &sync, NULL); | 1042 | &amdgpu_vm_free_job, |
1047 | return r; | 1043 | AMDGPU_FENCE_OWNER_MOVE, |
1048 | } | 1044 | fence); |
1049 | 1045 | if (r) | |
1050 | amdgpu_ring_unlock_commit(ring); | 1046 | goto error_free; |
1051 | amdgpu_sync_free(adev, &sync, &(*fence)->base); | ||
1052 | 1047 | ||
1048 | if (!amdgpu_enable_scheduler) { | ||
1049 | amdgpu_ib_free(adev, ib); | ||
1050 | kfree(ib); | ||
1051 | } | ||
1053 | return 0; | 1052 | return 0; |
1053 | error_free: | ||
1054 | amdgpu_ib_free(adev, ib); | ||
1055 | kfree(ib); | ||
1056 | return r; | ||
1054 | } | 1057 | } |
1055 | 1058 | ||
1056 | #if defined(CONFIG_DEBUG_FS) | 1059 | #if defined(CONFIG_DEBUG_FS) |