From patchwork Wed Apr 13 10:09:36 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Chris Wilson X-Patchwork-Id: 703501 Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) by demeter1.kernel.org (8.14.4/8.14.3) with ESMTP id p3DAA43v028798 for ; Wed, 13 Apr 2011 10:10:25 GMT Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 7C5FE9F01F for ; Wed, 13 Apr 2011 03:10:03 -0700 (PDT) X-Original-To: intel-gfx@lists.freedesktop.org Delivered-To: intel-gfx@lists.freedesktop.org Received: from fireflyinternet.com (server109-228-6-236.live-servers.net [109.228.6.236]) by gabe.freedesktop.org (Postfix) with ESMTP id 3A7779E755 for ; Wed, 13 Apr 2011 03:09:44 -0700 (PDT) X-Default-Received-SPF: pass (skip=forwardok (res=PASS)) x-ip-name=78.156.66.37; Received: from arrandale.alporthouse.com (unverified [78.156.66.37]) by fireflyinternet.com (Firefly Internet SMTP) with ESMTP id 31931080-1500050 for multiple; Wed, 13 Apr 2011 11:09:35 +0100 From: Chris Wilson To: intel-gfx@lists.freedesktop.org Date: Wed, 13 Apr 2011 11:09:36 +0100 Message-Id: <1302689376-25072-1-git-send-email-chris@chris-wilson.co.uk> X-Mailer: git-send-email 1.7.4.1 X-Originating-IP: 78.156.66.37 Subject: [Intel-gfx] [PATCH] drm/i915: Prevent mixing of snooped and tiling modes for old chipsets X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.11 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Sender: intel-gfx-bounces+patchwork-intel-gfx=patchwork.kernel.org@lists.freedesktop.org Errors-To: intel-gfx-bounces+patchwork-intel-gfx=patchwork.kernel.org@lists.freedesktop.org X-Greylist: IP, sender and recipient auto-whitelisted, not delayed by milter-greylist-4.2.6 (demeter1.kernel.org [140.211.167.41]); Wed, 13 Apr 2011 10:10:25 +0000 (UTC) Older chipsets do not support snooping (i.e. cache sharing between the CPU and GPU) on tiled surfaces. So prevent userspace from being silly should we one day expose the ability to change cache levels from userspace. It does enforce a strict ordering for mode changing though. So in order to change a buffer to snooped, the driver has to clear any tiling first and then change the cache level. This is consistent with how we flush and update the PTEs and seems a reasonable imposition on the driver. Deferring the check until use, whilst providing flexibilty here, implies forcing extra unbinds and a more complicated error message from, for example, execbuffer. Signed-off-by: Chris Wilson --- drivers/gpu/drm/i915/i915_gem.c | 8 ++++++++ drivers/gpu/drm/i915/i915_gem_tiling.c | 9 +++++++++ 2 files changed, 17 insertions(+), 0 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 9fbe1b5..6ca026d 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -3342,6 +3342,14 @@ int i915_gem_object_set_cache_level(struct drm_i915_gem_object *obj, if (obj->cache_level == cache_level) return 0; + if (INTEL_INFO(obj->base.dev)->gen < 6 && + obj->tiling_mode != I915_TILING_NONE && + cache_level != I915_CACHE_NONE) { + DRM_DEBUG("can not enable snooping on a tiled surface, " + "it must be linear for pre-SandyBridge chipsets\n"); + return -EINVAL; + } + if (obj->gtt_space) { ret = i915_gem_object_flush_gpu(obj); if (ret) diff --git a/drivers/gpu/drm/i915/i915_gem_tiling.c b/drivers/gpu/drm/i915/i915_gem_tiling.c index e4d5c58..cf48d91 100644 --- a/drivers/gpu/drm/i915/i915_gem_tiling.c +++ b/drivers/gpu/drm/i915/i915_gem_tiling.c @@ -331,6 +331,14 @@ i915_gem_set_tiling(struct drm_device *dev, void *data, } mutex_lock(&dev->struct_mutex); + if (INTEL_INFO(dev)->gen < 6 && + args->tiling_mode != I915_TILING_NONE && + obj->cache_level != I915_CACHE_NONE) { + DRM_DEBUG("can't not set a tiling mode on snooped memory," + "it must be linear for pre-SandyBridge chipsets\n"); + ret = -EINVAL; + goto err; + } if (args->tiling_mode != obj->tiling_mode || args->stride != obj->stride) { /* We need to rebind the object if its current allocation @@ -363,6 +371,7 @@ i915_gem_set_tiling(struct drm_device *dev, void *data, } } /* we have to maintain this existing ABI... */ +err: args->stride = obj->stride; args->tiling_mode = obj->tiling_mode; drm_gem_object_unreference(&obj->base);