summaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/i915/i915_gem_gtt.c
diff options
context:
space:
mode:
authorBen Widawsky2013-12-06 23:11:08 +0100
committerDaniel Vetter2013-12-18 15:27:58 +0100
commite3cc19957f519dede119d6fc2fc51869bfb09e0e (patch)
tree0b51b502315475397a3443cbea05b4f454939d59 /drivers/gpu/drm/i915/i915_gem_gtt.c
parentdrm/i915: Use drm_mm for PPGTT PDEs (diff)
downloadkernel-qcow2-linux-e3cc19957f519dede119d6fc2fc51869bfb09e0e.tar.gz
kernel-qcow2-linux-e3cc19957f519dede119d6fc2fc51869bfb09e0e.tar.xz
kernel-qcow2-linux-e3cc19957f519dede119d6fc2fc51869bfb09e0e.zip
drm/i915: One hopeful eviction on PPGTT alloc
The patch before this changed the way in which we allocate space for the PPGTT PDEs. It began carving out the PPGTT PDEs (which live in the Global GTT) from the GGTT's drm_mm. Prior to that patch, the PDEs were hidden from the drm_mm, and therefore could never fail to be allocated. In unfortunate cases, the drm_mm may be full when we want to allocate the space. This can technically occur whenever we try to allocate, which happens in two places currently. Practically, it can only really ever happen at GPU reset. Later, when we allocate more PDEs for multiple PPGTTs this will potentially even more useful. Signed-off-by: Ben Widawsky <ben@bwidawsk.net> Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm/i915/i915_gem_gtt.c')
-rw-r--r--drivers/gpu/drm/i915/i915_gem_gtt.c14
1 files changed, 12 insertions, 2 deletions
diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c
index 926b2a669de1..91a76dfd6490 100644
--- a/drivers/gpu/drm/i915/i915_gem_gtt.c
+++ b/drivers/gpu/drm/i915/i915_gem_gtt.c
@@ -640,6 +640,7 @@ static int gen6_ppgtt_init(struct i915_hw_ppgtt *ppgtt)
#define GEN6_PD_SIZE (GEN6_PPGTT_PD_ENTRIES * PAGE_SIZE)
struct drm_device *dev = ppgtt->base.dev;
struct drm_i915_private *dev_priv = dev->dev_private;
+ bool retried = false;
int i, ret;
/* PPGTT PDEs reside in the GGTT and consists of 512 entries. The
@@ -647,13 +648,22 @@ static int gen6_ppgtt_init(struct i915_hw_ppgtt *ppgtt)
* size. We allocate at the top of the GTT to avoid fragmentation.
*/
BUG_ON(!drm_mm_initialized(&dev_priv->gtt.base.mm));
+alloc:
ret = drm_mm_insert_node_in_range_generic(&dev_priv->gtt.base.mm,
&ppgtt->node, GEN6_PD_SIZE,
GEN6_PD_ALIGN, 0,
0, dev_priv->gtt.base.total,
DRM_MM_SEARCH_DEFAULT);
- if (ret)
- return ret;
+ if (ret == -ENOSPC && !retried) {
+ ret = i915_gem_evict_something(dev, &dev_priv->gtt.base,
+ GEN6_PD_SIZE, GEN6_PD_ALIGN,
+ I915_CACHE_NONE, false, true);
+ if (ret)
+ return ret;
+
+ retried = true;
+ goto alloc;
+ }
if (ppgtt->node.start < dev_priv->gtt.mappable_end)
DRM_DEBUG("Forced to use aperture for PDEs\n");