Skip to content

Commit 7226386

Browse files
committed
PM: runtime: Unify error handling during suspend and resume
There is a confusing difference in error handling between rpm_suspend() and rpm_resume() related to the special way in which -EAGAIN and -EBUSY error values are treated by the former. Also, converting -EACCES coming from the callback to I/O error, which it quite likely is not, may confuse runtime PM users. To address the above, modify rpm_callback() to convert -EACCES coming from the driver to -EAGAIN and to set power.runtime_error only if the return value is not -EAGAIN or -EBUSY. This will cause the error handling in rpm_resume() and rpm_suspend() to work consistently, so drop the no longer needed -EAGAIN or -EBUSY special case from the latter and make it retry autosuspend if power.runtime_error is unset. Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com> Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org> Link: https://patch.msgid.link/12620037.O9o76ZdvQC@rjwysocki.net
1 parent d2677d5 commit 7226386

File tree

1 file changed

+24
-16
lines changed

1 file changed

+24
-16
lines changed

drivers/base/power/runtime.c

Lines changed: 24 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -448,8 +448,19 @@ static int rpm_callback(int (*cb)(struct device *), struct device *dev)
448448
retval = __rpm_callback(cb, dev);
449449
}
450450

451-
dev->power.runtime_error = retval;
452-
return retval != -EACCES ? retval : -EIO;
451+
/*
452+
* Since -EACCES means that runtime PM is disabled for the given device,
453+
* it should not be returned by runtime PM callbacks. If it is returned
454+
* nevertheless, assume it to be a transient error and convert it to
455+
* -EAGAIN.
456+
*/
457+
if (retval == -EACCES)
458+
retval = -EAGAIN;
459+
460+
if (retval != -EAGAIN && retval != -EBUSY)
461+
dev->power.runtime_error = retval;
462+
463+
return retval;
453464
}
454465

455466
/**
@@ -725,21 +736,18 @@ static int rpm_suspend(struct device *dev, int rpmflags)
725736
dev->power.deferred_resume = false;
726737
wake_up_all(&dev->power.wait_queue);
727738

728-
if (retval == -EAGAIN || retval == -EBUSY) {
729-
dev->power.runtime_error = 0;
739+
/*
740+
* On transient errors, if the callback routine failed an autosuspend,
741+
* and if the last_busy time has been updated so that there is a new
742+
* autosuspend expiration time, automatically reschedule another
743+
* autosuspend.
744+
*/
745+
if (!dev->power.runtime_error && (rpmflags & RPM_AUTO) &&
746+
pm_runtime_autosuspend_expiration(dev) != 0)
747+
goto repeat;
748+
749+
pm_runtime_cancel_pending(dev);
730750

731-
/*
732-
* If the callback routine failed an autosuspend, and
733-
* if the last_busy time has been updated so that there
734-
* is a new autosuspend expiration time, automatically
735-
* reschedule another autosuspend.
736-
*/
737-
if ((rpmflags & RPM_AUTO) &&
738-
pm_runtime_autosuspend_expiration(dev) != 0)
739-
goto repeat;
740-
} else {
741-
pm_runtime_cancel_pending(dev);
742-
}
743751
goto out;
744752
}
745753

0 commit comments

Comments
 (0)