aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDave Gordon <david.s.gordon@intel.com>2016-04-12 09:46:16 -0400
committerTvrtko Ursulin <tvrtko.ursulin@intel.com>2016-04-20 11:59:03 -0400
commit8305216ff831ebc47d6335f577448e6c0453fc82 (patch)
tree5c4f2130dd75a4f120ad448bedcc194db060cbaf
parent86e06cc0c0ecf3fdfe04ff48fccb34891767d514 (diff)
drm/i915: check for ERR_PTR from i915_gem_object_pin_map()
The newly-introduced function i915_gem_object_pin_map() returns an ERR_PTR (not NULL) if the pin-and-map opertaion fails, so that's what we must check for. And it's nicer not to assign such a pointer-or-error to a structure being filled in until after it's been validated, so we should keep it local and avoid exporting a bogus pointer. Also, for clarity and symmetry, we should clear 'virtual_start' along with 'vma' when unmapping a ringbuffer. Signed-off-by: Dave Gordon <david.s.gordon@intel.com> Cc: Chris Wilson <chris@chris-wilson.co.uk> Cc: Tvrtko Ursulin <tvrtko.ursulin@linux.intel.com> Reviewed-by: Chris Wilson <chris@chris-wilson.co.uk> Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
-rw-r--r--drivers/gpu/drm/i915/i915_drv.h6
-rw-r--r--drivers/gpu/drm/i915/intel_ringbuffer.c15
2 files changed, 13 insertions, 8 deletions
diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
index 85102ad75962..6f1e0f127c0a 100644
--- a/drivers/gpu/drm/i915/i915_drv.h
+++ b/drivers/gpu/drm/i915/i915_drv.h
@@ -3018,9 +3018,11 @@ static inline void i915_gem_object_unpin_pages(struct drm_i915_gem_object *obj)
3018 * pages and then returns a contiguous mapping of the backing storage into 3018 * pages and then returns a contiguous mapping of the backing storage into
3019 * the kernel address space. 3019 * the kernel address space.
3020 * 3020 *
3021 * The caller must hold the struct_mutex. 3021 * The caller must hold the struct_mutex, and is responsible for calling
3022 * i915_gem_object_unpin_map() when the mapping is no longer required.
3022 * 3023 *
3023 * Returns the pointer through which to access the backing storage. 3024 * Returns the pointer through which to access the mapped object, or an
3025 * ERR_PTR() on error.
3024 */ 3026 */
3025void *__must_check i915_gem_object_pin_map(struct drm_i915_gem_object *obj); 3027void *__must_check i915_gem_object_pin_map(struct drm_i915_gem_object *obj);
3026 3028
diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c
index 978f0b676c68..245386e20c52 100644
--- a/drivers/gpu/drm/i915/intel_ringbuffer.c
+++ b/drivers/gpu/drm/i915/intel_ringbuffer.c
@@ -2088,6 +2088,7 @@ void intel_unpin_ringbuffer_obj(struct intel_ringbuffer *ringbuf)
2088 i915_gem_object_unpin_map(ringbuf->obj); 2088 i915_gem_object_unpin_map(ringbuf->obj);
2089 else 2089 else
2090 iounmap(ringbuf->virtual_start); 2090 iounmap(ringbuf->virtual_start);
2091 ringbuf->virtual_start = NULL;
2091 ringbuf->vma = NULL; 2092 ringbuf->vma = NULL;
2092 i915_gem_object_ggtt_unpin(ringbuf->obj); 2093 i915_gem_object_ggtt_unpin(ringbuf->obj);
2093} 2094}
@@ -2100,6 +2101,7 @@ int intel_pin_and_map_ringbuffer_obj(struct drm_device *dev,
2100 struct drm_i915_gem_object *obj = ringbuf->obj; 2101 struct drm_i915_gem_object *obj = ringbuf->obj;
2101 /* Ring wraparound at offset 0 sometimes hangs. No idea why. */ 2102 /* Ring wraparound at offset 0 sometimes hangs. No idea why. */
2102 unsigned flags = PIN_OFFSET_BIAS | 4096; 2103 unsigned flags = PIN_OFFSET_BIAS | 4096;
2104 void *addr;
2103 int ret; 2105 int ret;
2104 2106
2105 if (HAS_LLC(dev_priv) && !obj->stolen) { 2107 if (HAS_LLC(dev_priv) && !obj->stolen) {
@@ -2111,9 +2113,9 @@ int intel_pin_and_map_ringbuffer_obj(struct drm_device *dev,
2111 if (ret) 2113 if (ret)
2112 goto err_unpin; 2114 goto err_unpin;
2113 2115
2114 ringbuf->virtual_start = i915_gem_object_pin_map(obj); 2116 addr = i915_gem_object_pin_map(obj);
2115 if (ringbuf->virtual_start == NULL) { 2117 if (IS_ERR(addr)) {
2116 ret = -ENOMEM; 2118 ret = PTR_ERR(addr);
2117 goto err_unpin; 2119 goto err_unpin;
2118 } 2120 }
2119 } else { 2121 } else {
@@ -2129,14 +2131,15 @@ int intel_pin_and_map_ringbuffer_obj(struct drm_device *dev,
2129 /* Access through the GTT requires the device to be awake. */ 2131 /* Access through the GTT requires the device to be awake. */
2130 assert_rpm_wakelock_held(dev_priv); 2132 assert_rpm_wakelock_held(dev_priv);
2131 2133
2132 ringbuf->virtual_start = ioremap_wc(ggtt->mappable_base + 2134 addr = ioremap_wc(ggtt->mappable_base +
2133 i915_gem_obj_ggtt_offset(obj), ringbuf->size); 2135 i915_gem_obj_ggtt_offset(obj), ringbuf->size);
2134 if (ringbuf->virtual_start == NULL) { 2136 if (addr == NULL) {
2135 ret = -ENOMEM; 2137 ret = -ENOMEM;
2136 goto err_unpin; 2138 goto err_unpin;
2137 } 2139 }
2138 } 2140 }
2139 2141
2142 ringbuf->virtual_start = addr;
2140 ringbuf->vma = i915_gem_obj_to_ggtt(obj); 2143 ringbuf->vma = i915_gem_obj_to_ggtt(obj);
2141 return 0; 2144 return 0;
2142 2145