0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025 #include "radeon.h"
0026 #include "radeon_asic.h"
0027 #include "evergreen.h"
0028 #include "evergreend.h"
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040 void evergreen_dma_fence_ring_emit(struct radeon_device *rdev,
0041 struct radeon_fence *fence)
0042 {
0043 struct radeon_ring *ring = &rdev->ring[fence->ring];
0044 u64 addr = rdev->fence_drv[fence->ring].gpu_addr;
0045
0046 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_FENCE, 0, 0));
0047 radeon_ring_write(ring, addr & 0xfffffffc);
0048 radeon_ring_write(ring, (upper_32_bits(addr) & 0xff));
0049 radeon_ring_write(ring, fence->seq);
0050
0051 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_TRAP, 0, 0));
0052
0053 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0));
0054 radeon_ring_write(ring, (0xf << 16) | (HDP_MEM_COHERENCY_FLUSH_CNTL >> 2));
0055 radeon_ring_write(ring, 1);
0056 }
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066 void evergreen_dma_ring_ib_execute(struct radeon_device *rdev,
0067 struct radeon_ib *ib)
0068 {
0069 struct radeon_ring *ring = &rdev->ring[ib->ring];
0070
0071 if (rdev->wb.enabled) {
0072 u32 next_rptr = ring->wptr + 4;
0073 while ((next_rptr & 7) != 5)
0074 next_rptr++;
0075 next_rptr += 3;
0076 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 1));
0077 radeon_ring_write(ring, ring->next_rptr_gpu_addr & 0xfffffffc);
0078 radeon_ring_write(ring, upper_32_bits(ring->next_rptr_gpu_addr) & 0xff);
0079 radeon_ring_write(ring, next_rptr);
0080 }
0081
0082
0083
0084
0085 while ((ring->wptr & 7) != 5)
0086 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_NOP, 0, 0));
0087 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_INDIRECT_BUFFER, 0, 0));
0088 radeon_ring_write(ring, (ib->gpu_addr & 0xFFFFFFE0));
0089 radeon_ring_write(ring, (ib->length_dw << 12) | (upper_32_bits(ib->gpu_addr) & 0xFF));
0090
0091 }
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105
0106 struct radeon_fence *evergreen_copy_dma(struct radeon_device *rdev,
0107 uint64_t src_offset,
0108 uint64_t dst_offset,
0109 unsigned num_gpu_pages,
0110 struct dma_resv *resv)
0111 {
0112 struct radeon_fence *fence;
0113 struct radeon_sync sync;
0114 int ring_index = rdev->asic->copy.dma_ring_index;
0115 struct radeon_ring *ring = &rdev->ring[ring_index];
0116 u32 size_in_dw, cur_size_in_dw;
0117 int i, num_loops;
0118 int r = 0;
0119
0120 radeon_sync_create(&sync);
0121
0122 size_in_dw = (num_gpu_pages << RADEON_GPU_PAGE_SHIFT) / 4;
0123 num_loops = DIV_ROUND_UP(size_in_dw, 0xfffff);
0124 r = radeon_ring_lock(rdev, ring, num_loops * 5 + 11);
0125 if (r) {
0126 DRM_ERROR("radeon: moving bo (%d).\n", r);
0127 radeon_sync_free(rdev, &sync, NULL);
0128 return ERR_PTR(r);
0129 }
0130
0131 radeon_sync_resv(rdev, &sync, resv, false);
0132 radeon_sync_rings(rdev, &sync, ring->idx);
0133
0134 for (i = 0; i < num_loops; i++) {
0135 cur_size_in_dw = size_in_dw;
0136 if (cur_size_in_dw > 0xFFFFF)
0137 cur_size_in_dw = 0xFFFFF;
0138 size_in_dw -= cur_size_in_dw;
0139 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_COPY, 0, cur_size_in_dw));
0140 radeon_ring_write(ring, dst_offset & 0xfffffffc);
0141 radeon_ring_write(ring, src_offset & 0xfffffffc);
0142 radeon_ring_write(ring, upper_32_bits(dst_offset) & 0xff);
0143 radeon_ring_write(ring, upper_32_bits(src_offset) & 0xff);
0144 src_offset += cur_size_in_dw * 4;
0145 dst_offset += cur_size_in_dw * 4;
0146 }
0147
0148 r = radeon_fence_emit(rdev, &fence, ring->idx);
0149 if (r) {
0150 radeon_ring_unlock_undo(rdev, ring);
0151 radeon_sync_free(rdev, &sync, NULL);
0152 return ERR_PTR(r);
0153 }
0154
0155 radeon_ring_unlock_commit(rdev, ring, false);
0156 radeon_sync_free(rdev, &sync, fence);
0157
0158 return fence;
0159 }
0160
0161
0162
0163
0164
0165
0166
0167
0168
0169
0170 bool evergreen_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring)
0171 {
0172 u32 reset_mask = evergreen_gpu_check_soft_reset(rdev);
0173
0174 if (!(reset_mask & RADEON_RESET_DMA)) {
0175 radeon_ring_lockup_update(rdev, ring);
0176 return false;
0177 }
0178 return radeon_ring_test_lockup(rdev, ring);
0179 }
0180
0181