diff options
Diffstat (limited to 'linux-core')
| -rw-r--r-- | linux-core/drm_objects.h | 1 | ||||
| -rw-r--r-- | linux-core/drm_ttm.c | 7 | ||||
| -rw-r--r-- | linux-core/i915_buffer.c | 33 | ||||
| -rw-r--r-- | linux-core/i915_drv.c | 1 | 
4 files changed, 40 insertions, 2 deletions
diff --git a/linux-core/drm_objects.h b/linux-core/drm_objects.h index 8b14ac6f..cea811eb 100644 --- a/linux-core/drm_objects.h +++ b/linux-core/drm_objects.h @@ -464,6 +464,7 @@ struct drm_bo_driver {  	 uint32_t(*evict_mask) (struct drm_buffer_object *bo);  	int (*move) (struct drm_buffer_object * bo,  		     int evict, int no_wait, struct drm_bo_mem_reg * new_mem); +	void (*ttm_cache_flush)(struct drm_ttm *ttm);  };  /* diff --git a/linux-core/drm_ttm.c b/linux-core/drm_ttm.c index 33bbe1d4..df9e7e44 100644 --- a/linux-core/drm_ttm.c +++ b/linux-core/drm_ttm.c @@ -207,6 +207,7 @@ struct page *drm_ttm_get_page(struct drm_ttm * ttm, int index)  	}  	return p;  } +EXPORT_SYMBOL(drm_ttm_get_page);  int drm_ttm_populate(struct drm_ttm * ttm)  { @@ -311,7 +312,7 @@ void drm_ttm_unbind(struct drm_ttm * ttm)  int drm_bind_ttm(struct drm_ttm * ttm, struct drm_bo_mem_reg *bo_mem)  { - +	struct drm_bo_driver *bo_driver = ttm->dev->driver->bo_driver;  	int ret = 0;  	struct drm_ttm_backend *be; @@ -328,7 +329,9 @@ int drm_bind_ttm(struct drm_ttm * ttm, struct drm_bo_mem_reg *bo_mem)  	if (ttm->state == ttm_unbound && !(bo_mem->flags & DRM_BO_FLAG_CACHED)) {  		drm_set_caching(ttm, DRM_TTM_PAGE_UNCACHED); -	} +	} else if ((bo_mem->flags & DRM_BO_FLAG_CACHED) && +		   bo_driver->ttm_cache_flush) +		bo_driver->ttm_cache_flush(ttm);  	if ((ret = be->func->bind(be, bo_mem))) {  		ttm->state = ttm_evicted; diff --git a/linux-core/i915_buffer.c b/linux-core/i915_buffer.c index f81def8f..bbc7e1db 100644 --- a/linux-core/i915_buffer.c +++ b/linux-core/i915_buffer.c @@ -249,3 +249,36 @@ int i915_move(struct drm_buffer_object * bo,  	}  	return 0;  } + +#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)) +static inline void clflush(volatile void *__p) +{ +	asm volatile("clflush %0" : "+m" (*(char __force *)__p)); +} +#endif + +static inline void drm_cache_flush_addr(void *virt) +{  +        int i; + +	for (i = 0; i < PAGE_SIZE; i += boot_cpu_data.x86_clflush_size) +		clflush(virt+i); +} + +static inline void drm_cache_flush_page(struct page *p) +{ +	drm_cache_flush_addr(page_address(p)); +} + +void i915_flush_ttm(struct drm_ttm *ttm) +{ +	int i; + +	if (!ttm) +		return; + +	DRM_MEMORYBARRIER(); +	for (i = ttm->num_pages-1; i >= 0; i--) +		drm_cache_flush_page(drm_ttm_get_page(ttm, i)); +	DRM_MEMORYBARRIER(); +} diff --git a/linux-core/i915_drv.c b/linux-core/i915_drv.c index f34d218c..124db68f 100644 --- a/linux-core/i915_drv.c +++ b/linux-core/i915_drv.c @@ -66,6 +66,7 @@ static struct drm_bo_driver i915_bo_driver = {  	.init_mem_type = i915_init_mem_type,  	.evict_mask = i915_evict_mask,  	.move = i915_move, +	.ttm_cache_flush = i915_flush_ttm,  };  #endif  | 
