From 638353103d009d44bd5bdbe97cc7cef1bf011cdf Mon Sep 17 00:00:00 2001 From: "Xiang, Haihao" Date: Wed, 5 Mar 2008 15:08:46 +0800 Subject: i915: Evict if relocatee buffer is CACHED_MAPPED before writting relocations, otherwise the GPU probably sees some inconsistent data. Fix fd.o bug#14656 --- linux-core/drm_bo.c | 3 ++- linux-core/drm_objects.h | 2 +- shared-core/i915_dma.c | 7 +++++++ 3 files changed, 10 insertions(+), 2 deletions(-) diff --git a/linux-core/drm_bo.c b/linux-core/drm_bo.c index 3b180d15..17180d8d 100644 --- a/linux-core/drm_bo.c +++ b/linux-core/drm_bo.c @@ -1066,7 +1066,7 @@ static int drm_bo_busy(struct drm_buffer_object *bo) return 0; } -static int drm_bo_evict_cached(struct drm_buffer_object *bo) +int drm_bo_evict_cached(struct drm_buffer_object *bo) { int ret = 0; @@ -1076,6 +1076,7 @@ static int drm_bo_evict_cached(struct drm_buffer_object *bo) return ret; } +EXPORT_SYMBOL(drm_bo_evict_cached); /* * Wait until a buffer is unmapped. */ diff --git a/linux-core/drm_objects.h b/linux-core/drm_objects.h index 69a5c27f..fd32f0f4 100644 --- a/linux-core/drm_objects.h +++ b/linux-core/drm_objects.h @@ -697,7 +697,7 @@ extern int drm_bo_do_validate(struct drm_buffer_object *bo, uint64_t flags, uint64_t mask, uint32_t hint, uint32_t fence_class, struct drm_bo_info_rep *rep); - +extern int drm_bo_evict_cached(struct drm_buffer_object *bo); /* * Buffer object memory move- and map helpers. * drm_bo_move.c diff --git a/shared-core/i915_dma.c b/shared-core/i915_dma.c index f9e02c77..9e474bc6 100644 --- a/shared-core/i915_dma.c +++ b/shared-core/i915_dma.c @@ -806,6 +806,7 @@ struct i915_relocatee_info { struct drm_bo_kmap_obj kmap; int is_iomem; int idle; + int evicted; }; struct drm_i915_validate_buffer { @@ -878,6 +879,12 @@ int i915_apply_reloc(struct drm_file *file_priv, int num_buffers, relocatee->data_page = drm_bmo_virtual(&relocatee->kmap, &relocatee->is_iomem); relocatee->page_offset = (relocatee->offset & PAGE_MASK); + + if (!relocatee->evicted && + relocatee->buf->mem.flags & DRM_BO_FLAG_CACHED_MAPPED) { + drm_bo_evict_cached(relocatee->buf); + relocatee->evicted = 1; + } } val = buffers[buf_index].buffer->offset; -- cgit v1.2.3