drm/i915: Drop ORIGIN_GTT for untracked GTT writes
If FBC is set on a framebuffer that is unmapped, all GTT faults will be from a partial mapping. Writes by the user through the partial VMA are then untracked by the FBC and so we must use the ORIGIN_CPU when flushing the I915_GEM_DOMAIN_GTT. v2: Keep ORIGIN_CPU for set-to-domain(.write=CPU) Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> Cc: Joonas Lahtinen <joonas.lahtinen@linux.intel.com> Cc: Daniel Vetter <daniel.vetter@intel.com> Cc: "Zanoni, Paulo R" <paulo.r.zanoni@intel.com> Reviewed-by: Joonas Lahtinen <joonas.lahtinen@linux.intel.com> Link: http://patchwork.freedesktop.org/patch/msgid/20160818161718.27187-25-chris@chris-wilson.co.uk
This commit is contained in:
parent
aa136d9d72
commit
50349247ea
|
@ -2198,6 +2198,7 @@ struct drm_i915_gem_object {
|
|||
unsigned int cache_dirty:1;
|
||||
|
||||
atomic_t frontbuffer_bits;
|
||||
unsigned int frontbuffer_ggtt_origin; /* write once */
|
||||
|
||||
/** Current tiling stride for the object, if it's tiled. */
|
||||
unsigned int tiling_and_stride;
|
||||
|
@ -2205,7 +2206,6 @@ struct drm_i915_gem_object {
|
|||
#define TILING_MASK (FENCE_MINIMUM_STRIDE-1)
|
||||
#define STRIDE_MASK (~TILING_MASK)
|
||||
|
||||
unsigned int has_wc_mmap;
|
||||
/** Count of VMA actually bound by this object */
|
||||
unsigned int bind_count;
|
||||
unsigned int pin_display;
|
||||
|
|
|
@ -1497,8 +1497,8 @@ err:
|
|||
static inline enum fb_op_origin
|
||||
write_origin(struct drm_i915_gem_object *obj, unsigned domain)
|
||||
{
|
||||
return domain == I915_GEM_DOMAIN_GTT && !obj->has_wc_mmap ?
|
||||
ORIGIN_GTT : ORIGIN_CPU;
|
||||
return (domain == I915_GEM_DOMAIN_GTT ?
|
||||
obj->frontbuffer_ggtt_origin : ORIGIN_CPU);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1658,7 +1658,7 @@ i915_gem_mmap_ioctl(struct drm_device *dev, void *data,
|
|||
up_write(&mm->mmap_sem);
|
||||
|
||||
/* This may race, but that's ok, it only gets set */
|
||||
WRITE_ONCE(obj->has_wc_mmap, true);
|
||||
WRITE_ONCE(obj->frontbuffer_ggtt_origin, ORIGIN_CPU);
|
||||
}
|
||||
i915_gem_object_put_unlocked(obj);
|
||||
if (IS_ERR((void *)addr))
|
||||
|
@ -1761,6 +1761,11 @@ int i915_gem_fault(struct vm_area_struct *area, struct vm_fault *vmf)
|
|||
if (chunk_size >= obj->base.size >> PAGE_SHIFT)
|
||||
view.type = I915_GGTT_VIEW_NORMAL;
|
||||
|
||||
/* Userspace is now writing through an untracked VMA, abandon
|
||||
* all hope that the hardware is able to track future writes.
|
||||
*/
|
||||
obj->frontbuffer_ggtt_origin = ORIGIN_CPU;
|
||||
|
||||
vma = i915_gem_object_ggtt_pin(obj, &view, 0, 0, PIN_MAPPABLE);
|
||||
}
|
||||
if (IS_ERR(vma)) {
|
||||
|
@ -4093,6 +4098,7 @@ void i915_gem_object_init(struct drm_i915_gem_object *obj,
|
|||
|
||||
obj->ops = ops;
|
||||
|
||||
obj->frontbuffer_ggtt_origin = ORIGIN_GTT;
|
||||
obj->madv = I915_MADV_WILLNEED;
|
||||
|
||||
i915_gem_info_add_obj(to_i915(obj->base.dev), obj->base.size);
|
||||
|
|
Loading…
Reference in a new issue