xref: /linux/drivers/base/power/generic_ops.c (revision 7fc2cd2e4b398c57c9cf961cfea05eadbf34c05c)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * drivers/base/power/generic_ops.c - Generic PM callbacks for subsystems
4  *
5  * Copyright (c) 2010 Rafael J. Wysocki <rjw@sisk.pl>, Novell Inc.
6  */
7 #include <linux/pm.h>
8 #include <linux/pm_runtime.h>
9 #include <linux/export.h>
10 
11 #define CALL_PM_OP(dev, op) \
12 ({ \
13 	struct device *_dev = (dev); \
14 	const struct dev_pm_ops *pm = _dev->driver ? _dev->driver->pm : NULL; \
15 	pm && pm->op ? pm->op(_dev) : 0; \
16 })
17 
18 #ifdef CONFIG_PM
19 /**
20  * pm_generic_runtime_suspend - Generic runtime suspend callback for subsystems.
21  * @dev: Device to suspend.
22  *
23  * If PM operations are defined for the @dev's driver and they include
24  * ->runtime_suspend(), execute it and return its error code.  Otherwise,
25  * return 0.
26  */
27 int pm_generic_runtime_suspend(struct device *dev)
28 {
29 	return CALL_PM_OP(dev, runtime_suspend);
30 }
31 EXPORT_SYMBOL_GPL(pm_generic_runtime_suspend);
32 
33 /**
34  * pm_generic_runtime_resume - Generic runtime resume callback for subsystems.
35  * @dev: Device to resume.
36  *
37  * If PM operations are defined for the @dev's driver and they include
38  * ->runtime_resume(), execute it and return its error code.  Otherwise,
39  * return 0.
40  */
41 int pm_generic_runtime_resume(struct device *dev)
42 {
43 	return CALL_PM_OP(dev, runtime_resume);
44 }
45 EXPORT_SYMBOL_GPL(pm_generic_runtime_resume);
46 #endif /* CONFIG_PM */
47 
48 #ifdef CONFIG_PM_SLEEP
49 /**
50  * pm_generic_prepare - Generic routine preparing a device for power transition.
51  * @dev: Device to prepare.
52  *
53  * Prepare a device for a system-wide power transition.
54  */
55 int pm_generic_prepare(struct device *dev)
56 {
57 	struct device_driver *drv = dev->driver;
58 	int ret = 0;
59 
60 	if (drv && drv->pm && drv->pm->prepare)
61 		ret = drv->pm->prepare(dev);
62 
63 	return ret;
64 }
65 
66 /**
67  * pm_generic_suspend_noirq - Generic suspend_noirq callback for subsystems.
68  * @dev: Device to suspend.
69  */
70 int pm_generic_suspend_noirq(struct device *dev)
71 {
72 	return CALL_PM_OP(dev, suspend_noirq);
73 }
74 EXPORT_SYMBOL_GPL(pm_generic_suspend_noirq);
75 
76 /**
77  * pm_generic_suspend_late - Generic suspend_late callback for subsystems.
78  * @dev: Device to suspend.
79  */
80 int pm_generic_suspend_late(struct device *dev)
81 {
82 	return CALL_PM_OP(dev, suspend_late);
83 }
84 EXPORT_SYMBOL_GPL(pm_generic_suspend_late);
85 
86 /**
87  * pm_generic_suspend - Generic suspend callback for subsystems.
88  * @dev: Device to suspend.
89  */
90 int pm_generic_suspend(struct device *dev)
91 {
92 	return CALL_PM_OP(dev, suspend);
93 }
94 EXPORT_SYMBOL_GPL(pm_generic_suspend);
95 
96 /**
97  * pm_generic_freeze_noirq - Generic freeze_noirq callback for subsystems.
98  * @dev: Device to freeze.
99  */
100 int pm_generic_freeze_noirq(struct device *dev)
101 {
102 	return CALL_PM_OP(dev, freeze_noirq);
103 }
104 EXPORT_SYMBOL_GPL(pm_generic_freeze_noirq);
105 
106 /**
107  * pm_generic_freeze - Generic freeze callback for subsystems.
108  * @dev: Device to freeze.
109  */
110 int pm_generic_freeze(struct device *dev)
111 {
112 	return CALL_PM_OP(dev, freeze);
113 }
114 EXPORT_SYMBOL_GPL(pm_generic_freeze);
115 
116 /**
117  * pm_generic_poweroff_noirq - Generic poweroff_noirq callback for subsystems.
118  * @dev: Device to handle.
119  */
120 int pm_generic_poweroff_noirq(struct device *dev)
121 {
122 	return CALL_PM_OP(dev, poweroff_noirq);
123 }
124 EXPORT_SYMBOL_GPL(pm_generic_poweroff_noirq);
125 
126 /**
127  * pm_generic_poweroff_late - Generic poweroff_late callback for subsystems.
128  * @dev: Device to handle.
129  */
130 int pm_generic_poweroff_late(struct device *dev)
131 {
132 	return CALL_PM_OP(dev, poweroff_late);
133 }
134 EXPORT_SYMBOL_GPL(pm_generic_poweroff_late);
135 
136 /**
137  * pm_generic_poweroff - Generic poweroff callback for subsystems.
138  * @dev: Device to handle.
139  */
140 int pm_generic_poweroff(struct device *dev)
141 {
142 	return CALL_PM_OP(dev, poweroff);
143 }
144 EXPORT_SYMBOL_GPL(pm_generic_poweroff);
145 
146 /**
147  * pm_generic_thaw_noirq - Generic thaw_noirq callback for subsystems.
148  * @dev: Device to thaw.
149  */
150 int pm_generic_thaw_noirq(struct device *dev)
151 {
152 	return CALL_PM_OP(dev, thaw_noirq);
153 }
154 EXPORT_SYMBOL_GPL(pm_generic_thaw_noirq);
155 
156 /**
157  * pm_generic_thaw - Generic thaw callback for subsystems.
158  * @dev: Device to thaw.
159  */
160 int pm_generic_thaw(struct device *dev)
161 {
162 	return CALL_PM_OP(dev, thaw);
163 }
164 EXPORT_SYMBOL_GPL(pm_generic_thaw);
165 
166 /**
167  * pm_generic_resume_noirq - Generic resume_noirq callback for subsystems.
168  * @dev: Device to resume.
169  */
170 int pm_generic_resume_noirq(struct device *dev)
171 {
172 	return CALL_PM_OP(dev, resume_noirq);
173 }
174 EXPORT_SYMBOL_GPL(pm_generic_resume_noirq);
175 
176 /**
177  * pm_generic_resume_early - Generic resume_early callback for subsystems.
178  * @dev: Device to resume.
179  */
180 int pm_generic_resume_early(struct device *dev)
181 {
182 	return CALL_PM_OP(dev, resume_early);
183 }
184 EXPORT_SYMBOL_GPL(pm_generic_resume_early);
185 
186 /**
187  * pm_generic_resume - Generic resume callback for subsystems.
188  * @dev: Device to resume.
189  */
190 int pm_generic_resume(struct device *dev)
191 {
192 	return CALL_PM_OP(dev, resume);
193 }
194 EXPORT_SYMBOL_GPL(pm_generic_resume);
195 
196 /**
197  * pm_generic_restore_noirq - Generic restore_noirq callback for subsystems.
198  * @dev: Device to restore.
199  */
200 int pm_generic_restore_noirq(struct device *dev)
201 {
202 	return CALL_PM_OP(dev, restore_noirq);
203 }
204 EXPORT_SYMBOL_GPL(pm_generic_restore_noirq);
205 
206 /**
207  * pm_generic_restore_early - Generic restore_early callback for subsystems.
208  * @dev: Device to resume.
209  */
210 int pm_generic_restore_early(struct device *dev)
211 {
212 	return CALL_PM_OP(dev, restore_early);
213 }
214 EXPORT_SYMBOL_GPL(pm_generic_restore_early);
215 
216 /**
217  * pm_generic_restore - Generic restore callback for subsystems.
218  * @dev: Device to restore.
219  */
220 int pm_generic_restore(struct device *dev)
221 {
222 	return CALL_PM_OP(dev, restore);
223 }
224 EXPORT_SYMBOL_GPL(pm_generic_restore);
225 
226 /**
227  * pm_generic_complete - Generic routine completing a device power transition.
228  * @dev: Device to handle.
229  *
230  * Complete a device power transition during a system-wide power transition.
231  */
232 void pm_generic_complete(struct device *dev)
233 {
234 	struct device_driver *drv = dev->driver;
235 
236 	if (drv && drv->pm && drv->pm->complete)
237 		drv->pm->complete(dev);
238 }
239 #endif /* CONFIG_PM_SLEEP */
240