drm/i915: Gracefully handle obj not bound to GGTT in is_pin_display
[deliverable/linux.git] / drivers / gpu / drm / i915 / i915_gem.c
index 034ba2c6064aa31598dced1a984e232129af236f..f6c03513de521533288d7d0b7a50c21a80517851 100644 (file)
@@ -3641,6 +3641,15 @@ unlock:
 
 static bool is_pin_display(struct drm_i915_gem_object *obj)
 {
+       struct i915_vma *vma;
+
+       if (list_empty(&obj->vma_list))
+               return false;
+
+       vma = i915_gem_obj_to_ggtt(obj);
+       if (!vma)
+               return false;
+
        /* There are 3 sources that pin objects:
         *   1. The display engine (scanouts, sprites, cursors);
         *   2. Reservations for execbuffer;
@@ -3652,7 +3661,7 @@ static bool is_pin_display(struct drm_i915_gem_object *obj)
         * subtracting the potential reference by the user, any pin_count
         * remains, it must be due to another use by the display engine.
         */
-       return i915_gem_obj_to_ggtt(obj)->pin_count - !!obj->user_pin_count;
+       return vma->pin_count - !!obj->user_pin_count;
 }
 
 /*
@@ -3666,6 +3675,7 @@ i915_gem_object_pin_to_display_plane(struct drm_i915_gem_object *obj,
                                     struct intel_ring_buffer *pipelined)
 {
        u32 old_read_domains, old_write_domain;
+       bool was_pin_display;
        int ret;
 
        if (pipelined != obj->ring) {
@@ -3677,6 +3687,7 @@ i915_gem_object_pin_to_display_plane(struct drm_i915_gem_object *obj,
        /* Mark the pin_display early so that we account for the
         * display coherency whilst setting up the cache domains.
         */
+       was_pin_display = obj->pin_display;
        obj->pin_display = true;
 
        /* The display engine is not coherent with the LLC cache on gen6.  As
@@ -3719,7 +3730,8 @@ i915_gem_object_pin_to_display_plane(struct drm_i915_gem_object *obj,
        return 0;
 
 err_unpin_display:
-       obj->pin_display = is_pin_display(obj);
+       WARN_ON(was_pin_display != is_pin_display(obj));
+       obj->pin_display = was_pin_display;
        return ret;
 }
 
@@ -5115,6 +5127,9 @@ struct i915_vma *i915_gem_obj_to_ggtt(struct drm_i915_gem_object *obj)
 {
        struct i915_vma *vma;
 
+       /* This WARN has probably outlived its usefulness (callers already
+        * WARN if they don't find the GGTT vma they expect). When removing,
+        * remember to remove the pre-check in is_pin_display() as well */
        if (WARN_ON(list_empty(&obj->vma_list)))
                return NULL;
 
This page took 0.042174 seconds and 5 git commands to generate.