From dc61705a6e425952de4c81c2320382af07cf948a Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Tue, 5 Nov 2013 08:49:28 +0000 Subject: [PATCH] sna: Use an inplace exchange for large untiled BO On older architectures, large BO have to be untiled and so we can reuse an existing CPU bo by adjusting its caching mode. References: https://bugs.freedesktop.org/show_bug.cgi?id=70924 Signed-off-by: Chris Wilson --- src/sna/kgem.c | 10 ++++++++++ src/sna/kgem.h | 2 ++ src/sna/sna_accel.c | 14 ++++++++++++++ 3 files changed, 26 insertions(+) diff --git a/src/sna/kgem.c b/src/sna/kgem.c index 00d0723..3a74616 100644 --- a/src/sna/kgem.c +++ b/src/sna/kgem.c @@ -6541,3 +6541,13 @@ kgem_replace_bo(struct kgem *kgem, return dst; } + +bool kgem_bo_convert_to_gpu(struct kgem *kgem, struct kgem_bo *bo) +{ + assert(bo->tiling == I915_TILING_NONE); + + if (kgem->has_llc) + return true; + + return gem_set_caching(kgem->fd, bo->handle, UNCACHED); +} diff --git a/src/sna/kgem.h b/src/sna/kgem.h index f2abb04..6abab08 100644 --- a/src/sna/kgem.h +++ b/src/sna/kgem.h @@ -299,6 +299,8 @@ struct kgem_bo *kgem_create_cpu_2d(struct kgem *kgem, int bpp, uint32_t flags); +bool kgem_bo_convert_to_gpu(struct kgem *kgem, struct kgem_bo *bo); + uint32_t kgem_bo_get_binding(struct kgem_bo *bo, uint32_t format); void kgem_bo_set_binding(struct kgem_bo *bo, uint32_t format, uint16_t offset); diff --git a/src/sna/sna_accel.c b/src/sna/sna_accel.c index 28cdd74..2aae0e2 100644 --- a/src/sna/sna_accel.c +++ b/src/sna/sna_accel.c @@ -3772,6 +3772,20 @@ sna_pixmap_move_to_gpu(PixmapPtr pixmap, unsigned flags) tiling = (flags & MOVE_SOURCE_HINT) ? I915_TILING_Y : DEFAULT_TILING; tiling = sna_pixmap_choose_tiling(pixmap, tiling); + if (tiling == I915_TILING_NONE && + priv->cpu_bo && !priv->shm && + kgem_bo_convert_to_gpu(&sna->kgem, priv->cpu_bo)) { + assert(!priv->mapped); + priv->gpu_bo = priv->cpu_bo; + priv->cpu_bo = NULL; + priv->ptr = NULL; + sna_damage_all(&priv->gpu_damage, + pixmap->drawable.width, + pixmap->drawable.height); + sna_damage_destroy(&priv->cpu_damage); + goto done; + } + create = 0; if (flags & MOVE_INPLACE_HINT || (priv->cpu_damage && priv->cpu_bo == NULL)) create = CREATE_GTT_MAP | CREATE_INACTIVE; -- 2.7.4