]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
PM: runtime: Only set runtime_error on suspend callback failures
authorPraveen Talari <praveen.talari@oss.qualcomm.com>
Mon, 6 Jul 2026 08:53:09 +0000 (14:23 +0530)
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>
Thu, 9 Jul 2026 14:50:18 +0000 (16:50 +0200)
When a runtime resume callback returns an error, rpm_callback() sets
power.runtime_error on the device.  This causes all subsequent calls to
rpm_resume() to return -EINVAL immediately at the top of the function
without invoking the callback again, making the failure permanent until
runtime PM is explicitly re-initialized.

Unlike suspend failures, resume failures should be retryable.  If a
device's resume callback fails, there is no reason to permanently block
future resume attempts on that device and all of its consumers.

Fix this by moving the power.runtime_error assignment out of the generic
rpm_callback() and into rpm_suspend() at its fail label, where suspend
callback failures are handled.  Resume callback failures now return the
error to the caller but leave power.runtime_error clear, allowing the
next resume attempt to invoke the callback normally.

Signed-off-by: Praveen Talari <praveen.talari@oss.qualcomm.com>
Link: https://patch.msgid.link/20260706-fix_sticky_-einval_after_pm_runtime_api_failure-v3-1-92feb5a7b926@oss.qualcomm.com
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
drivers/base/power/runtime.c

index 335288e8b5b312f6ec205888886d5df5ad2946ba..fab38bc981139cfac7a24ed361a05f8f3c624eff 100644 (file)
@@ -469,9 +469,6 @@ static int rpm_callback(int (*cb)(struct device *), struct device *dev)
        if (retval == -EACCES)
                retval = -EAGAIN;
 
-       if (retval != -EAGAIN && retval != -EBUSY)
-               dev->power.runtime_error = retval;
-
        return retval;
 }
 
@@ -751,6 +748,9 @@ static int rpm_suspend(struct device *dev, int rpmflags)
        dev->power.deferred_resume = false;
        wake_up_all(&dev->power.wait_queue);
 
+       if (retval != -EAGAIN && retval != -EBUSY)
+               dev->power.runtime_error = retval;
+
        /*
         * On transient errors, if the callback routine failed an autosuspend,
         * and if the last_busy time has been updated so that there is a new