aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/gpu/drm/radeon/radeon.h3
-rw-r--r--drivers/gpu/drm/radeon/radeon_cs.c47
-rw-r--r--drivers/gpu/drm/radeon/radeon_ring.c1
-rw-r--r--include/drm/radeon_drm.h1
4 files changed, 52 insertions, 0 deletions
diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h
index 972f1679d1c9..f467fe5edf09 100644
--- a/drivers/gpu/drm/radeon/radeon.h
+++ b/drivers/gpu/drm/radeon/radeon.h
@@ -632,6 +632,7 @@ struct radeon_ib {
632 uint32_t *ptr; 632 uint32_t *ptr;
633 struct radeon_fence *fence; 633 struct radeon_fence *fence;
634 unsigned vm_id; 634 unsigned vm_id;
635 bool is_const_ib;
635}; 636};
636 637
637/* 638/*
@@ -836,7 +837,9 @@ struct radeon_cs_parser {
836 int chunk_ib_idx; 837 int chunk_ib_idx;
837 int chunk_relocs_idx; 838 int chunk_relocs_idx;
838 int chunk_flags_idx; 839 int chunk_flags_idx;
840 int chunk_const_ib_idx;
839 struct radeon_ib *ib; 841 struct radeon_ib *ib;
842 struct radeon_ib *const_ib;
840 void *track; 843 void *track;
841 unsigned family; 844 unsigned family;
842 int parser_error; 845 int parser_error;
diff --git a/drivers/gpu/drm/radeon/radeon_cs.c b/drivers/gpu/drm/radeon/radeon_cs.c
index d9d9f5a59c42..087bd5053774 100644
--- a/drivers/gpu/drm/radeon/radeon_cs.c
+++ b/drivers/gpu/drm/radeon/radeon_cs.c
@@ -170,6 +170,7 @@ int radeon_cs_parser_init(struct radeon_cs_parser *p, void *data)
170 p->chunk_ib_idx = -1; 170 p->chunk_ib_idx = -1;
171 p->chunk_relocs_idx = -1; 171 p->chunk_relocs_idx = -1;
172 p->chunk_flags_idx = -1; 172 p->chunk_flags_idx = -1;
173 p->chunk_const_ib_idx = -1;
173 p->chunks_array = kcalloc(cs->num_chunks, sizeof(uint64_t), GFP_KERNEL); 174 p->chunks_array = kcalloc(cs->num_chunks, sizeof(uint64_t), GFP_KERNEL);
174 if (p->chunks_array == NULL) { 175 if (p->chunks_array == NULL) {
175 return -ENOMEM; 176 return -ENOMEM;
@@ -208,6 +209,12 @@ int radeon_cs_parser_init(struct radeon_cs_parser *p, void *data)
208 if (p->chunks[i].length_dw == 0) 209 if (p->chunks[i].length_dw == 0)
209 return -EINVAL; 210 return -EINVAL;
210 } 211 }
212 if (p->chunks[i].chunk_id == RADEON_CHUNK_ID_CONST_IB) {
213 p->chunk_const_ib_idx = i;
214 /* zero length CONST IB isn't useful */
215 if (p->chunks[i].length_dw == 0)
216 return -EINVAL;
217 }
211 if (p->chunks[i].chunk_id == RADEON_CHUNK_ID_FLAGS) { 218 if (p->chunks[i].chunk_id == RADEON_CHUNK_ID_FLAGS) {
212 p->chunk_flags_idx = i; 219 p->chunk_flags_idx = i;
213 /* zero length flags aren't useful */ 220 /* zero length flags aren't useful */
@@ -389,6 +396,32 @@ static int radeon_cs_ib_vm_chunk(struct radeon_device *rdev,
389 if ((parser->cs_flags & RADEON_CS_USE_VM) == 0) 396 if ((parser->cs_flags & RADEON_CS_USE_VM) == 0)
390 return 0; 397 return 0;
391 398
399 if ((rdev->family >= CHIP_TAHITI) &&
400 (parser->chunk_const_ib_idx != -1)) {
401 ib_chunk = &parser->chunks[parser->chunk_const_ib_idx];
402 if (ib_chunk->length_dw > RADEON_IB_VM_MAX_SIZE) {
403 DRM_ERROR("cs IB CONST too big: %d\n", ib_chunk->length_dw);
404 return -EINVAL;
405 }
406 r = radeon_ib_get(rdev, parser->ring, &parser->const_ib,
407 ib_chunk->length_dw * 4);
408 if (r) {
409 DRM_ERROR("Failed to get const ib !\n");
410 return r;
411 }
412 parser->const_ib->is_const_ib = true;
413 parser->const_ib->length_dw = ib_chunk->length_dw;
414 /* Copy the packet into the IB */
415 if (DRM_COPY_FROM_USER(parser->const_ib->ptr, ib_chunk->user_ptr,
416 ib_chunk->length_dw * 4)) {
417 return -EFAULT;
418 }
419 r = radeon_ring_ib_parse(rdev, parser->ring, parser->const_ib);
420 if (r) {
421 return r;
422 }
423 }
424
392 ib_chunk = &parser->chunks[parser->chunk_ib_idx]; 425 ib_chunk = &parser->chunks[parser->chunk_ib_idx];
393 if (ib_chunk->length_dw > RADEON_IB_VM_MAX_SIZE) { 426 if (ib_chunk->length_dw > RADEON_IB_VM_MAX_SIZE) {
394 DRM_ERROR("cs IB too big: %d\n", ib_chunk->length_dw); 427 DRM_ERROR("cs IB too big: %d\n", ib_chunk->length_dw);
@@ -424,11 +457,25 @@ static int radeon_cs_ib_vm_chunk(struct radeon_device *rdev,
424 if (r) { 457 if (r) {
425 DRM_ERROR("Failed to synchronize rings !\n"); 458 DRM_ERROR("Failed to synchronize rings !\n");
426 } 459 }
460
461 if ((rdev->family >= CHIP_TAHITI) &&
462 (parser->chunk_const_ib_idx != -1)) {
463 parser->const_ib->vm_id = vm->id;
464 /* ib pool is bind at 0 in virtual address space to gpu_addr is the
465 * offset inside the pool bo
466 */
467 parser->const_ib->gpu_addr = parser->const_ib->sa_bo.offset;
468 r = radeon_ib_schedule(rdev, parser->const_ib);
469 if (r)
470 goto out;
471 }
472
427 parser->ib->vm_id = vm->id; 473 parser->ib->vm_id = vm->id;
428 /* ib pool is bind at 0 in virtual address space to gpu_addr is the 474 /* ib pool is bind at 0 in virtual address space to gpu_addr is the
429 * offset inside the pool bo 475 * offset inside the pool bo
430 */ 476 */
431 parser->ib->gpu_addr = parser->ib->sa_bo.offset; 477 parser->ib->gpu_addr = parser->ib->sa_bo.offset;
478 parser->ib->is_const_ib = false;
432 r = radeon_ib_schedule(rdev, parser->ib); 479 r = radeon_ib_schedule(rdev, parser->ib);
433out: 480out:
434 if (!r) { 481 if (!r) {
diff --git a/drivers/gpu/drm/radeon/radeon_ring.c b/drivers/gpu/drm/radeon/radeon_ring.c
index 30566201dffb..cc33b3d7c33b 100644
--- a/drivers/gpu/drm/radeon/radeon_ring.c
+++ b/drivers/gpu/drm/radeon/radeon_ring.c
@@ -133,6 +133,7 @@ retry:
133 (*ib)->gpu_addr += (*ib)->sa_bo.offset; 133 (*ib)->gpu_addr += (*ib)->sa_bo.offset;
134 (*ib)->fence = fence; 134 (*ib)->fence = fence;
135 (*ib)->vm_id = 0; 135 (*ib)->vm_id = 0;
136 (*ib)->is_const_ib = false;
136 /* ib are most likely to be allocated in a ring fashion 137 /* ib are most likely to be allocated in a ring fashion
137 * thus rdev->ib_pool.head_id should be the id of the 138 * thus rdev->ib_pool.head_id should be the id of the
138 * oldest ib 139 * oldest ib
diff --git a/include/drm/radeon_drm.h b/include/drm/radeon_drm.h
index 6cde931d8e68..7c491b4bcf65 100644
--- a/include/drm/radeon_drm.h
+++ b/include/drm/radeon_drm.h
@@ -908,6 +908,7 @@ struct drm_radeon_gem_va {
908#define RADEON_CHUNK_ID_RELOCS 0x01 908#define RADEON_CHUNK_ID_RELOCS 0x01
909#define RADEON_CHUNK_ID_IB 0x02 909#define RADEON_CHUNK_ID_IB 0x02
910#define RADEON_CHUNK_ID_FLAGS 0x03 910#define RADEON_CHUNK_ID_FLAGS 0x03
911#define RADEON_CHUNK_ID_CONST_IB 0x04
911 912
912/* The first dword of RADEON_CHUNK_ID_FLAGS is a uint32 of these flags: */ 913/* The first dword of RADEON_CHUNK_ID_FLAGS is a uint32 of these flags: */
913#define RADEON_CS_KEEP_TILING_FLAGS 0x01 914#define RADEON_CS_KEEP_TILING_FLAGS 0x01