diff options
author | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2017-10-09 03:02:35 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2017-10-09 03:02:35 -0400 |
commit | 1236d6bb6e19fc72ffc6bbcdeb1bfefe450e54ee (patch) | |
tree | 47da3feee8e263e8c9352c85cf518e624be3c211 /drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c | |
parent | 750b1a6894ecc9b178c6e3d0a1170122971b2036 (diff) | |
parent | 8a5776a5f49812d29fe4b2d0a2d71675c3facf3f (diff) |
Merge 4.14-rc4 into staging-next
We want the staging/iio fixes in here as well to handle merge issues.
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c')
-rw-r--r-- | drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c | 22 |
1 files changed, 17 insertions, 5 deletions
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c b/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c index 681b639f5133..ed71ad40e8f7 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c | |||
@@ -183,8 +183,8 @@ static void uninitialize(struct kernel_queue *kq) | |||
183 | { | 183 | { |
184 | if (kq->queue->properties.type == KFD_QUEUE_TYPE_HIQ) | 184 | if (kq->queue->properties.type == KFD_QUEUE_TYPE_HIQ) |
185 | kq->mqd->destroy_mqd(kq->mqd, | 185 | kq->mqd->destroy_mqd(kq->mqd, |
186 | NULL, | 186 | kq->queue->mqd, |
187 | false, | 187 | KFD_PREEMPT_TYPE_WAVEFRONT_RESET, |
188 | QUEUE_PREEMPT_DEFAULT_TIMEOUT_MS, | 188 | QUEUE_PREEMPT_DEFAULT_TIMEOUT_MS, |
189 | kq->queue->pipe, | 189 | kq->queue->pipe, |
190 | kq->queue->queue); | 190 | kq->queue->queue); |
@@ -210,6 +210,11 @@ static int acquire_packet_buffer(struct kernel_queue *kq, | |||
210 | uint32_t wptr, rptr; | 210 | uint32_t wptr, rptr; |
211 | unsigned int *queue_address; | 211 | unsigned int *queue_address; |
212 | 212 | ||
213 | /* When rptr == wptr, the buffer is empty. | ||
214 | * When rptr == wptr + 1, the buffer is full. | ||
215 | * It is always rptr that advances to the position of wptr, rather than | ||
216 | * the opposite. So we can only use up to queue_size_dwords - 1 dwords. | ||
217 | */ | ||
213 | rptr = *kq->rptr_kernel; | 218 | rptr = *kq->rptr_kernel; |
214 | wptr = *kq->wptr_kernel; | 219 | wptr = *kq->wptr_kernel; |
215 | queue_address = (unsigned int *)kq->pq_kernel_addr; | 220 | queue_address = (unsigned int *)kq->pq_kernel_addr; |
@@ -219,11 +224,10 @@ static int acquire_packet_buffer(struct kernel_queue *kq, | |||
219 | pr_debug("wptr: %d\n", wptr); | 224 | pr_debug("wptr: %d\n", wptr); |
220 | pr_debug("queue_address 0x%p\n", queue_address); | 225 | pr_debug("queue_address 0x%p\n", queue_address); |
221 | 226 | ||
222 | available_size = (rptr - 1 - wptr + queue_size_dwords) % | 227 | available_size = (rptr + queue_size_dwords - 1 - wptr) % |
223 | queue_size_dwords; | 228 | queue_size_dwords; |
224 | 229 | ||
225 | if (packet_size_in_dwords >= queue_size_dwords || | 230 | if (packet_size_in_dwords > available_size) { |
226 | packet_size_in_dwords >= available_size) { | ||
227 | /* | 231 | /* |
228 | * make sure calling functions know | 232 | * make sure calling functions know |
229 | * acquire_packet_buffer() failed | 233 | * acquire_packet_buffer() failed |
@@ -233,6 +237,14 @@ static int acquire_packet_buffer(struct kernel_queue *kq, | |||
233 | } | 237 | } |
234 | 238 | ||
235 | if (wptr + packet_size_in_dwords >= queue_size_dwords) { | 239 | if (wptr + packet_size_in_dwords >= queue_size_dwords) { |
240 | /* make sure after rolling back to position 0, there is | ||
241 | * still enough space. | ||
242 | */ | ||
243 | if (packet_size_in_dwords >= rptr) { | ||
244 | *buffer_ptr = NULL; | ||
245 | return -ENOMEM; | ||
246 | } | ||
247 | /* fill nops, roll back and start at position 0 */ | ||
236 | while (wptr > 0) { | 248 | while (wptr > 0) { |
237 | queue_address[wptr] = kq->nop_packet; | 249 | queue_address[wptr] = kq->nop_packet; |
238 | wptr = (wptr + 1) % queue_size_dwords; | 250 | wptr = (wptr + 1) % queue_size_dwords; |