aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMikko Perttunen <mperttunen@nvidia.com>2017-06-22 03:18:33 -0400
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>2017-06-28 19:24:34 -0400
commit10da65423fdbee185da5bb65f829a9d9312c1198 (patch)
tree01cea6d79416526ccdd277c486541735a2ecb4d5
parentd8600c8b0cd11d2249e14bf8b2eccbf4fa0db770 (diff)
PM / Domains: Call driver's noirq callbacks
Currently genpd installs its own noirq callbacks, but never calls down to the driver's corresponding callbacks. Add these calls. Signed-off-by: Mikko Perttunen <mperttunen@nvidia.com> Acked-by: Ulf Hansson <ulf.hansson@linaro.org> Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
-rw-r--r--drivers/base/power/domain.c68
1 files changed, 59 insertions, 9 deletions
diff --git a/drivers/base/power/domain.c b/drivers/base/power/domain.c
index 0f7b1bd3680e..bbbb1d72395b 100644
--- a/drivers/base/power/domain.c
+++ b/drivers/base/power/domain.c
@@ -902,19 +902,19 @@ static int pm_genpd_prepare(struct device *dev)
902} 902}
903 903
904/** 904/**
905 * pm_genpd_suspend_noirq - Completion of suspend of device in an I/O PM domain. 905 * genpd_finish_suspend - Completion of suspend or hibernation of device in an
906 * I/O pm domain.
906 * @dev: Device to suspend. 907 * @dev: Device to suspend.
908 * @poweroff: Specifies if this is a poweroff_noirq or suspend_noirq callback.
907 * 909 *
908 * Stop the device and remove power from the domain if all devices in it have 910 * Stop the device and remove power from the domain if all devices in it have
909 * been stopped. 911 * been stopped.
910 */ 912 */
911static int pm_genpd_suspend_noirq(struct device *dev) 913static int genpd_finish_suspend(struct device *dev, bool poweroff)
912{ 914{
913 struct generic_pm_domain *genpd; 915 struct generic_pm_domain *genpd;
914 int ret; 916 int ret;
915 917
916 dev_dbg(dev, "%s()\n", __func__);
917
918 genpd = dev_to_genpd(dev); 918 genpd = dev_to_genpd(dev);
919 if (IS_ERR(genpd)) 919 if (IS_ERR(genpd))
920 return -EINVAL; 920 return -EINVAL;
@@ -922,6 +922,13 @@ static int pm_genpd_suspend_noirq(struct device *dev)
922 if (dev->power.wakeup_path && genpd_dev_active_wakeup(genpd, dev)) 922 if (dev->power.wakeup_path && genpd_dev_active_wakeup(genpd, dev))
923 return 0; 923 return 0;
924 924
925 if (poweroff)
926 ret = pm_generic_poweroff_noirq(dev);
927 else
928 ret = pm_generic_suspend_noirq(dev);
929 if (ret)
930 return ret;
931
925 if (genpd->dev_ops.stop && genpd->dev_ops.start) { 932 if (genpd->dev_ops.stop && genpd->dev_ops.start) {
926 ret = pm_runtime_force_suspend(dev); 933 ret = pm_runtime_force_suspend(dev);
927 if (ret) 934 if (ret)
@@ -937,6 +944,20 @@ static int pm_genpd_suspend_noirq(struct device *dev)
937} 944}
938 945
939/** 946/**
947 * pm_genpd_suspend_noirq - Completion of suspend of device in an I/O PM domain.
948 * @dev: Device to suspend.
949 *
950 * Stop the device and remove power from the domain if all devices in it have
951 * been stopped.
952 */
953static int pm_genpd_suspend_noirq(struct device *dev)
954{
955 dev_dbg(dev, "%s()\n", __func__);
956
957 return genpd_finish_suspend(dev, false);
958}
959
960/**
940 * pm_genpd_resume_noirq - Start of resume of device in an I/O PM domain. 961 * pm_genpd_resume_noirq - Start of resume of device in an I/O PM domain.
941 * @dev: Device to resume. 962 * @dev: Device to resume.
942 * 963 *
@@ -964,6 +985,10 @@ static int pm_genpd_resume_noirq(struct device *dev)
964 if (genpd->dev_ops.stop && genpd->dev_ops.start) 985 if (genpd->dev_ops.stop && genpd->dev_ops.start)
965 ret = pm_runtime_force_resume(dev); 986 ret = pm_runtime_force_resume(dev);
966 987
988 ret = pm_generic_resume_noirq(dev);
989 if (ret)
990 return ret;
991
967 return ret; 992 return ret;
968} 993}
969 994
@@ -987,6 +1012,10 @@ static int pm_genpd_freeze_noirq(struct device *dev)
987 if (IS_ERR(genpd)) 1012 if (IS_ERR(genpd))
988 return -EINVAL; 1013 return -EINVAL;
989 1014
1015 ret = pm_generic_freeze_noirq(dev);
1016 if (ret)
1017 return ret;
1018
990 if (genpd->dev_ops.stop && genpd->dev_ops.start) 1019 if (genpd->dev_ops.stop && genpd->dev_ops.start)
991 ret = pm_runtime_force_suspend(dev); 1020 ret = pm_runtime_force_suspend(dev);
992 1021
@@ -1011,10 +1040,28 @@ static int pm_genpd_thaw_noirq(struct device *dev)
1011 if (IS_ERR(genpd)) 1040 if (IS_ERR(genpd))
1012 return -EINVAL; 1041 return -EINVAL;
1013 1042
1014 if (genpd->dev_ops.stop && genpd->dev_ops.start) 1043 if (genpd->dev_ops.stop && genpd->dev_ops.start) {
1015 ret = pm_runtime_force_resume(dev); 1044 ret = pm_runtime_force_resume(dev);
1045 if (ret)
1046 return ret;
1047 }
1016 1048
1017 return ret; 1049 return pm_generic_thaw_noirq(dev);
1050}
1051
1052/**
1053 * pm_genpd_poweroff_noirq - Completion of hibernation of device in an
1054 * I/O PM domain.
1055 * @dev: Device to poweroff.
1056 *
1057 * Stop the device and remove power from the domain if all devices in it have
1058 * been stopped.
1059 */
1060static int pm_genpd_poweroff_noirq(struct device *dev)
1061{
1062 dev_dbg(dev, "%s()\n", __func__);
1063
1064 return genpd_finish_suspend(dev, true);
1018} 1065}
1019 1066
1020/** 1067/**
@@ -1051,10 +1098,13 @@ static int pm_genpd_restore_noirq(struct device *dev)
1051 genpd_sync_power_on(genpd, true, 0); 1098 genpd_sync_power_on(genpd, true, 0);
1052 genpd_unlock(genpd); 1099 genpd_unlock(genpd);
1053 1100
1054 if (genpd->dev_ops.stop && genpd->dev_ops.start) 1101 if (genpd->dev_ops.stop && genpd->dev_ops.start) {
1055 ret = pm_runtime_force_resume(dev); 1102 ret = pm_runtime_force_resume(dev);
1103 if (ret)
1104 return ret;
1105 }
1056 1106
1057 return ret; 1107 return pm_generic_restore_noirq(dev);
1058} 1108}
1059 1109
1060/** 1110/**
@@ -1496,7 +1546,7 @@ int pm_genpd_init(struct generic_pm_domain *genpd,
1496 genpd->domain.ops.resume_noirq = pm_genpd_resume_noirq; 1546 genpd->domain.ops.resume_noirq = pm_genpd_resume_noirq;
1497 genpd->domain.ops.freeze_noirq = pm_genpd_freeze_noirq; 1547 genpd->domain.ops.freeze_noirq = pm_genpd_freeze_noirq;
1498 genpd->domain.ops.thaw_noirq = pm_genpd_thaw_noirq; 1548 genpd->domain.ops.thaw_noirq = pm_genpd_thaw_noirq;
1499 genpd->domain.ops.poweroff_noirq = pm_genpd_suspend_noirq; 1549 genpd->domain.ops.poweroff_noirq = pm_genpd_poweroff_noirq;
1500 genpd->domain.ops.restore_noirq = pm_genpd_restore_noirq; 1550 genpd->domain.ops.restore_noirq = pm_genpd_restore_noirq;
1501 genpd->domain.ops.complete = pm_genpd_complete; 1551 genpd->domain.ops.complete = pm_genpd_complete;
1502 1552