drm/i915/gt: Call intel_gt_sanitize() directly
authorChris Wilson <chris@chris-wilson.co.uk>
Fri, 1 Nov 2019 14:10:06 +0000 (14:10 +0000)
committerJoonas Lahtinen <joonas.lahtinen@linux.intel.com>
Tue, 5 Nov 2019 14:04:16 +0000 (16:04 +0200)
Assume all responsibility for operating on the HW to sanitize the GT
state upon load/resume in intel_gt_sanitize() itself.

Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Reviewed-by: Andi Shyti <andi.shyti@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20191101141009.15581-1-chris@chris-wilson.co.uk
(cherry picked from commit 797a615357ac0feb79c9ce41f5eaac3eb738a51f)
Signed-off-by: Joonas Lahtinen <joonas.lahtinen@linux.intel.com>
drivers/gpu/drm/i915/gem/i915_gem_pm.c
drivers/gpu/drm/i915/gt/intel_gt.c
drivers/gpu/drm/i915/gt/intel_gt.h
drivers/gpu/drm/i915/gt/intel_gt_pm.c
drivers/gpu/drm/i915/i915_drv.c
drivers/gpu/drm/i915/i915_drv.h
drivers/gpu/drm/i915/i915_gem.c
drivers/gpu/drm/i915/selftests/i915_gem.c
drivers/gpu/drm/i915/selftests/mock_gem_device.c
drivers/gpu/drm/i915/selftests/mock_gtt.c

index c99bb94..e2ee9c0 100644 (file)
@@ -74,7 +74,6 @@ void i915_gem_suspend(struct drm_i915_private *i915)
         * not rely on its state.
         */
        intel_gt_suspend(&i915->gt);
-       intel_uc_suspend(&i915->gt.uc);
 
        i915_gem_drain_freed_objects(i915);
 }
@@ -140,8 +139,6 @@ void i915_gem_suspend_late(struct drm_i915_private *i915)
                list_splice_tail(&keep, *phase);
        }
        spin_unlock_irqrestore(&i915->mm.obj_lock, flags);
-
-       i915_gem_sanitize(i915);
 }
 
 void i915_gem_resume(struct drm_i915_private *i915)
@@ -161,8 +158,6 @@ void i915_gem_resume(struct drm_i915_private *i915)
        if (intel_gt_resume(&i915->gt))
                goto err_wedged;
 
-       intel_uc_resume(&i915->gt.uc);
-
        /* Always reload a context for powersaving. */
        if (!switch_to_kernel_context_sync(&i915->gt))
                goto err_wedged;
index 898662c..4c26daf 100644 (file)
@@ -31,9 +31,11 @@ void intel_gt_init_early(struct intel_gt *gt, struct drm_i915_private *i915)
        intel_uc_init_early(&gt->uc);
 }
 
-void intel_gt_init_hw_early(struct drm_i915_private *i915)
+void intel_gt_init_hw_early(struct intel_gt *gt, struct i915_ggtt *ggtt)
 {
-       i915->gt.ggtt = &i915->ggtt;
+       gt->ggtt = ggtt;
+
+       intel_gt_sanitize(gt, false);
 }
 
 static void init_unused_ring(struct intel_gt *gt, u32 base)
index 5b6effe..5436f8c 100644 (file)
@@ -28,7 +28,7 @@ static inline struct intel_gt *huc_to_gt(struct intel_huc *huc)
 }
 
 void intel_gt_init_early(struct intel_gt *gt, struct drm_i915_private *i915);
-void intel_gt_init_hw_early(struct drm_i915_private *i915);
+void intel_gt_init_hw_early(struct intel_gt *gt, struct i915_ggtt *ggtt);
 int __must_check intel_gt_init_hw(struct intel_gt *gt);
 int intel_gt_init(struct intel_gt *gt);
 void intel_gt_driver_register(struct intel_gt *gt);
index 32becf1..1679f4f 100644 (file)
@@ -118,8 +118,22 @@ void intel_gt_sanitize(struct intel_gt *gt, bool force)
 {
        struct intel_engine_cs *engine;
        enum intel_engine_id id;
+       intel_wakeref_t wakeref;
 
-       GEM_TRACE("\n");
+       GEM_TRACE("force:%s\n", yesno(force));
+
+       /* Use a raw wakeref to avoid calling intel_display_power_get early */
+       wakeref = intel_runtime_pm_get(gt->uncore->rpm);
+       intel_uncore_forcewake_get(gt->uncore, FORCEWAKE_ALL);
+
+       /*
+        * As we have just resumed the machine and woken the device up from
+        * deep PCI sleep (presumably D3_cold), assume the HW has been reset
+        * back to defaults, recovering from whatever wedged state we left it
+        * in and so worth trying to use the device once more.
+        */
+       if (intel_gt_is_wedged(gt))
+               intel_gt_unset_wedged(gt);
 
        intel_uc_sanitize(&gt->uc);
 
@@ -127,6 +141,8 @@ void intel_gt_sanitize(struct intel_gt *gt, bool force)
                if (engine->reset.prepare)
                        engine->reset.prepare(engine);
 
+       intel_uc_reset_prepare(&gt->uc);
+
        if (reset_engines(gt) || force) {
                for_each_engine(engine, gt, id)
                        __intel_engine_reset(engine, false);
@@ -135,6 +151,9 @@ void intel_gt_sanitize(struct intel_gt *gt, bool force)
        for_each_engine(engine, gt, id)
                if (engine->reset.finish)
                        engine->reset.finish(engine);
+
+       intel_uncore_forcewake_put(gt->uncore, FORCEWAKE_ALL);
+       intel_runtime_pm_put(gt->uncore->rpm, wakeref);
 }
 
 void intel_gt_pm_fini(struct intel_gt *gt)
@@ -148,6 +167,8 @@ int intel_gt_resume(struct intel_gt *gt)
        enum intel_engine_id id;
        int err = 0;
 
+       GEM_TRACE("\n");
+
        /*
         * After resume, we may need to poke into the pinned kernel
         * contexts to paper over any damage caused by the sudden suspend.
@@ -186,6 +207,9 @@ int intel_gt_resume(struct intel_gt *gt)
        }
 
        intel_rc6_enable(&gt->rc6);
+
+       intel_uc_resume(&gt->uc);
+
        intel_uncore_forcewake_put(gt->uncore, FORCEWAKE_ALL);
        intel_gt_pm_put(gt);
 
@@ -212,20 +236,30 @@ void intel_gt_suspend(struct intel_gt *gt)
        /* We expect to be idle already; but also want to be independent */
        wait_for_idle(gt);
 
+       intel_uc_suspend(&gt->uc);
+
        with_intel_runtime_pm(gt->uncore->rpm, wakeref) {
                intel_rps_disable(&gt->rps);
                intel_rc6_disable(&gt->rc6);
                intel_llc_disable(&gt->llc);
        }
+
+       intel_gt_sanitize(gt, false);
+
+       GEM_TRACE("\n");
 }
 
 void intel_gt_runtime_suspend(struct intel_gt *gt)
 {
        intel_uc_runtime_suspend(&gt->uc);
+
+       GEM_TRACE("\n");
 }
 
 int intel_gt_runtime_resume(struct intel_gt *gt)
 {
+       GEM_TRACE("\n");
+
        intel_gt_init_swizzling(gt);
 
        return intel_uc_runtime_resume(&gt->uc);
index 3340485..ccb5b56 100644 (file)
@@ -603,8 +603,6 @@ static int i915_driver_mmio_probe(struct drm_i915_private *dev_priv)
        if (ret)
                goto err_uncore;
 
-       i915_gem_init_mmio(dev_priv);
-
        return 0;
 
 err_uncore:
@@ -1177,7 +1175,7 @@ static int i915_driver_hw_probe(struct drm_i915_private *dev_priv)
        if (ret)
                goto err_ggtt;
 
-       intel_gt_init_hw_early(dev_priv);
+       intel_gt_init_hw_early(&dev_priv->gt, &dev_priv->ggtt);
 
        ret = i915_ggtt_enable_hw(dev_priv);
        if (ret) {
@@ -1821,7 +1819,7 @@ static int i915_drm_resume(struct drm_device *dev)
 
        disable_rpm_wakeref_asserts(&dev_priv->runtime_pm);
 
-       i915_gem_sanitize(dev_priv);
+       intel_gt_sanitize(&dev_priv->gt, true);
 
        ret = i915_ggtt_enable_hw(dev_priv);
        if (ret)
@@ -1952,8 +1950,6 @@ static int i915_drm_resume_early(struct drm_device *dev)
 
        intel_power_domains_resume(dev_priv);
 
-       intel_gt_sanitize(&dev_priv->gt, true);
-
        enable_rpm_wakeref_asserts(&dev_priv->runtime_pm);
 
        return ret;
index 1e6118f..0567fe6 100644 (file)
@@ -1779,7 +1779,6 @@ int i915_getparam_ioctl(struct drm_device *dev, void *data,
 /* i915_gem.c */
 int i915_gem_init_userptr(struct drm_i915_private *dev_priv);
 void i915_gem_cleanup_userptr(struct drm_i915_private *dev_priv);
-void i915_gem_sanitize(struct drm_i915_private *i915);
 void i915_gem_init_early(struct drm_i915_private *dev_priv);
 void i915_gem_cleanup_early(struct drm_i915_private *dev_priv);
 int i915_gem_freeze(struct drm_i915_private *dev_priv);
@@ -1863,7 +1862,6 @@ static inline u32 i915_reset_engine_count(struct i915_gpu_error *error,
        return atomic_read(&error->reset_engine_count[engine->uabi_class]);
 }
 
-void i915_gem_init_mmio(struct drm_i915_private *i915);
 int __must_check i915_gem_init(struct drm_i915_private *dev_priv);
 void i915_gem_driver_register(struct drm_i915_private *i915);
 void i915_gem_driver_unregister(struct drm_i915_private *i915);
index b1574ab..ac23322 100644 (file)
@@ -1039,38 +1039,6 @@ out:
        return err;
 }
 
-void i915_gem_sanitize(struct drm_i915_private *i915)
-{
-       intel_wakeref_t wakeref;
-
-       GEM_TRACE("\n");
-
-       wakeref = intel_runtime_pm_get(&i915->runtime_pm);
-       intel_uncore_forcewake_get(&i915->uncore, FORCEWAKE_ALL);
-
-       /*
-        * As we have just resumed the machine and woken the device up from
-        * deep PCI sleep (presumably D3_cold), assume the HW has been reset
-        * back to defaults, recovering from whatever wedged state we left it
-        * in and so worth trying to use the device once more.
-        */
-       if (intel_gt_is_wedged(&i915->gt))
-               intel_gt_unset_wedged(&i915->gt);
-
-       /*
-        * If we inherit context state from the BIOS or earlier occupants
-        * of the GPU, the GPU may be in an inconsistent state when we
-        * try to take over. The only way to remove the earlier state
-        * is by resetting. However, resetting on earlier gen is tricky as
-        * it may impact the display and we are uncertain about the stability
-        * of the reset, so this could be applied to even earlier gen.
-        */
-       intel_gt_sanitize(&i915->gt, false);
-
-       intel_uncore_forcewake_put(&i915->uncore, FORCEWAKE_ALL);
-       intel_runtime_pm_put(&i915->runtime_pm, wakeref);
-}
-
 static int __intel_engines_record_defaults(struct intel_gt *gt)
 {
        struct i915_request *requests[I915_NUM_ENGINES] = {};
@@ -1413,11 +1381,6 @@ void i915_gem_driver_release(struct drm_i915_private *dev_priv)
        WARN_ON(!list_empty(&dev_priv->gem.contexts.list));
 }
 
-void i915_gem_init_mmio(struct drm_i915_private *i915)
-{
-       i915_gem_sanitize(i915);
-}
-
 static void i915_gem_init__mm(struct drm_i915_private *i915)
 {
        spin_lock_init(&i915->mm.obj_lock);
index e378543..d83f6bf 100644 (file)
@@ -124,7 +124,6 @@ static void pm_resume(struct drm_i915_private *i915)
         */
        with_intel_runtime_pm(&i915->runtime_pm, wakeref) {
                intel_gt_sanitize(&i915->gt, false);
-               i915_gem_sanitize(i915);
 
                i915_gem_restore_gtt_mappings(i915);
                i915_gem_restore_fences(&i915->ggtt);
index a0da594..27ed3ce 100644 (file)
@@ -183,7 +183,6 @@ struct drm_i915_private *mock_gem_device(void)
        intel_timelines_init(i915);
 
        mock_init_ggtt(i915, &i915->ggtt);
-       i915->gt.ggtt = &i915->ggtt;
 
        mkwrite_device_info(i915)->engine_mask = BIT(0);
 
index 9ec93dc..20ac384 100644 (file)
@@ -118,8 +118,7 @@ void mock_init_ggtt(struct drm_i915_private *i915, struct i915_ggtt *ggtt)
        ggtt->vm.vma_ops.clear_pages = clear_pages;
 
        i915_address_space_init(&ggtt->vm, VM_CLASS_GGTT);
-
-       intel_gt_init_hw_early(i915);
+       i915->gt.ggtt = ggtt;
 }
 
 void mock_fini_ggtt(struct i915_ggtt *ggtt)