1 /* 2 * drivers/base/power/clock_ops.c - Generic clock manipulation PM callbacks 3 * 4 * Copyright (c) 2011 Rafael J. Wysocki <rjw@sisk.pl>, Renesas Electronics Corp. 5 * 6 * This file is released under the GPLv2. 7 */ 8 9 #include <linux/init.h> 10 #include <linux/kernel.h> 11 #include <linux/io.h> 12 #include <linux/pm.h> 13 #include <linux/pm_runtime.h> 14 #include <linux/clk.h> 15 #include <linux/slab.h> 16 #include <linux/err.h> 17 18 #ifdef CONFIG_PM 19 20 enum pce_status { 21 PCE_STATUS_NONE = 0, 22 PCE_STATUS_ACQUIRED, 23 PCE_STATUS_ENABLED, 24 PCE_STATUS_ERROR, 25 }; 26 27 struct pm_clock_entry { 28 struct list_head node; 29 char *con_id; 30 struct clk *clk; 31 enum pce_status status; 32 }; 33 34 /** 35 * pm_clk_add - Start using a device clock for power management. 36 * @dev: Device whose clock is going to be used for power management. 37 * @con_id: Connection ID of the clock. 38 * 39 * Add the clock represented by @con_id to the list of clocks used for 40 * the power management of @dev. 41 */ 42 int pm_clk_add(struct device *dev, const char *con_id) 43 { 44 struct pm_subsys_data *psd = dev_to_psd(dev); 45 struct pm_clock_entry *ce; 46 47 if (!psd) 48 return -EINVAL; 49 50 ce = kzalloc(sizeof(*ce), GFP_KERNEL); 51 if (!ce) { 52 dev_err(dev, "Not enough memory for clock entry.\n"); 53 return -ENOMEM; 54 } 55 56 if (con_id) { 57 ce->con_id = kstrdup(con_id, GFP_KERNEL); 58 if (!ce->con_id) { 59 dev_err(dev, 60 "Not enough memory for clock connection ID.\n"); 61 kfree(ce); 62 return -ENOMEM; 63 } 64 } 65 66 spin_lock_irq(&psd->lock); 67 list_add_tail(&ce->node, &psd->clock_list); 68 spin_unlock_irq(&psd->lock); 69 return 0; 70 } 71 72 /** 73 * __pm_clk_remove - Destroy PM clock entry. 74 * @ce: PM clock entry to destroy. 75 * 76 * This routine must be called under the spinlock protecting the PM list of 77 * clocks corresponding the the @ce's device. 78 */ 79 static void __pm_clk_remove(struct pm_clock_entry *ce) 80 { 81 if (!ce) 82 return; 83 84 list_del(&ce->node); 85 86 if (ce->status < PCE_STATUS_ERROR) { 87 if (ce->status == PCE_STATUS_ENABLED) 88 clk_disable(ce->clk); 89 90 if (ce->status >= PCE_STATUS_ACQUIRED) 91 clk_put(ce->clk); 92 } 93 94 if (ce->con_id) 95 kfree(ce->con_id); 96 97 kfree(ce); 98 } 99 100 /** 101 * pm_clk_remove - Stop using a device clock for power management. 102 * @dev: Device whose clock should not be used for PM any more. 103 * @con_id: Connection ID of the clock. 104 * 105 * Remove the clock represented by @con_id from the list of clocks used for 106 * the power management of @dev. 107 */ 108 void pm_clk_remove(struct device *dev, const char *con_id) 109 { 110 struct pm_subsys_data *psd = dev_to_psd(dev); 111 struct pm_clock_entry *ce; 112 113 if (!psd) 114 return; 115 116 spin_lock_irq(&psd->lock); 117 118 list_for_each_entry(ce, &psd->clock_list, node) { 119 if (!con_id && !ce->con_id) { 120 __pm_clk_remove(ce); 121 break; 122 } else if (!con_id || !ce->con_id) { 123 continue; 124 } else if (!strcmp(con_id, ce->con_id)) { 125 __pm_clk_remove(ce); 126 break; 127 } 128 } 129 130 spin_unlock_irq(&psd->lock); 131 } 132 133 /** 134 * pm_clk_init - Initialize a device's list of power management clocks. 135 * @dev: Device to initialize the list of PM clocks for. 136 * 137 * Initialize the lock and clock_list members of the device's pm_subsys_data 138 * object. 139 */ 140 void pm_clk_init(struct device *dev) 141 { 142 struct pm_subsys_data *psd = dev_to_psd(dev); 143 144 if (!psd) 145 return; 146 147 INIT_LIST_HEAD(&psd->clock_list); 148 spin_lock_init(&psd->lock); 149 } 150 151 /** 152 * pm_clk_create - Create and initialize a device's list of PM clocks. 153 * @dev: Device to create and initialize the list of PM clocks for. 154 * 155 * Allocate a struct pm_subsys_data object, initialize its lock and clock_list 156 * members and make the @dev's power.subsys_data field point to it. 157 */ 158 int pm_clk_create(struct device *dev) 159 { 160 struct pm_subsys_data *psd; 161 162 psd = kzalloc(sizeof(*psd), GFP_KERNEL); 163 if (!psd) { 164 dev_err(dev, "Not enough memory for PM clock data.\n"); 165 return -ENOMEM; 166 } 167 dev->power.subsys_data = psd; 168 pm_clk_init(dev); 169 return 0; 170 } 171 172 /** 173 * pm_clk_destroy - Destroy a device's list of power management clocks. 174 * @dev: Device to destroy the list of PM clocks for. 175 * 176 * Clear the @dev's power.subsys_data field, remove the list of clock entries 177 * from the struct pm_subsys_data object pointed to by it before and free 178 * that object. 179 */ 180 void pm_clk_destroy(struct device *dev) 181 { 182 struct pm_subsys_data *psd = dev_to_psd(dev); 183 struct pm_clock_entry *ce, *c; 184 185 if (!psd) 186 return; 187 188 dev->power.subsys_data = NULL; 189 190 spin_lock_irq(&psd->lock); 191 192 list_for_each_entry_safe_reverse(ce, c, &psd->clock_list, node) 193 __pm_clk_remove(ce); 194 195 spin_unlock_irq(&psd->lock); 196 197 kfree(psd); 198 } 199 200 #endif /* CONFIG_PM */ 201 202 #ifdef CONFIG_PM_RUNTIME 203 204 /** 205 * pm_clk_acquire - Acquire a device clock. 206 * @dev: Device whose clock is to be acquired. 207 * @con_id: Connection ID of the clock. 208 */ 209 static void pm_clk_acquire(struct device *dev, 210 struct pm_clock_entry *ce) 211 { 212 ce->clk = clk_get(dev, ce->con_id); 213 if (IS_ERR(ce->clk)) { 214 ce->status = PCE_STATUS_ERROR; 215 } else { 216 ce->status = PCE_STATUS_ACQUIRED; 217 dev_dbg(dev, "Clock %s managed by runtime PM.\n", ce->con_id); 218 } 219 } 220 221 /** 222 * pm_clk_suspend - Disable clocks in a device's PM clock list. 223 * @dev: Device to disable the clocks for. 224 */ 225 int pm_clk_suspend(struct device *dev) 226 { 227 struct pm_subsys_data *psd = dev_to_psd(dev); 228 struct pm_clock_entry *ce; 229 unsigned long flags; 230 231 dev_dbg(dev, "%s()\n", __func__); 232 233 if (!psd) 234 return 0; 235 236 spin_lock_irqsave(&psd->lock, flags); 237 238 list_for_each_entry_reverse(ce, &psd->clock_list, node) { 239 if (ce->status == PCE_STATUS_NONE) 240 pm_clk_acquire(dev, ce); 241 242 if (ce->status < PCE_STATUS_ERROR) { 243 clk_disable(ce->clk); 244 ce->status = PCE_STATUS_ACQUIRED; 245 } 246 } 247 248 spin_unlock_irqrestore(&psd->lock, flags); 249 250 return 0; 251 } 252 253 /** 254 * pm_clk_resume - Enable clocks in a device's PM clock list. 255 * @dev: Device to enable the clocks for. 256 */ 257 int pm_clk_resume(struct device *dev) 258 { 259 struct pm_subsys_data *psd = dev_to_psd(dev); 260 struct pm_clock_entry *ce; 261 unsigned long flags; 262 263 dev_dbg(dev, "%s()\n", __func__); 264 265 if (!psd) 266 return 0; 267 268 spin_lock_irqsave(&psd->lock, flags); 269 270 list_for_each_entry(ce, &psd->clock_list, node) { 271 if (ce->status == PCE_STATUS_NONE) 272 pm_clk_acquire(dev, ce); 273 274 if (ce->status < PCE_STATUS_ERROR) { 275 clk_enable(ce->clk); 276 ce->status = PCE_STATUS_ENABLED; 277 } 278 } 279 280 spin_unlock_irqrestore(&psd->lock, flags); 281 282 return 0; 283 } 284 285 /** 286 * pm_clk_notify - Notify routine for device addition and removal. 287 * @nb: Notifier block object this function is a member of. 288 * @action: Operation being carried out by the caller. 289 * @data: Device the routine is being run for. 290 * 291 * For this function to work, @nb must be a member of an object of type 292 * struct pm_clk_notifier_block containing all of the requisite data. 293 * Specifically, the pm_domain member of that object is copied to the device's 294 * pm_domain field and its con_ids member is used to populate the device's list 295 * of PM clocks, depending on @action. 296 * 297 * If the device's pm_domain field is already populated with a value different 298 * from the one stored in the struct pm_clk_notifier_block object, the function 299 * does nothing. 300 */ 301 static int pm_clk_notify(struct notifier_block *nb, 302 unsigned long action, void *data) 303 { 304 struct pm_clk_notifier_block *clknb; 305 struct device *dev = data; 306 char **con_id; 307 int error; 308 309 dev_dbg(dev, "%s() %ld\n", __func__, action); 310 311 clknb = container_of(nb, struct pm_clk_notifier_block, nb); 312 313 switch (action) { 314 case BUS_NOTIFY_ADD_DEVICE: 315 if (dev->pm_domain) 316 break; 317 318 error = pm_clk_create(dev); 319 if (error) 320 break; 321 322 dev->pm_domain = clknb->pm_domain; 323 if (clknb->con_ids[0]) { 324 for (con_id = clknb->con_ids; *con_id; con_id++) 325 pm_clk_add(dev, *con_id); 326 } else { 327 pm_clk_add(dev, NULL); 328 } 329 330 break; 331 case BUS_NOTIFY_DEL_DEVICE: 332 if (dev->pm_domain != clknb->pm_domain) 333 break; 334 335 dev->pm_domain = NULL; 336 pm_clk_destroy(dev); 337 break; 338 } 339 340 return 0; 341 } 342 343 #else /* !CONFIG_PM_RUNTIME */ 344 345 #ifdef CONFIG_PM 346 347 /** 348 * pm_clk_suspend - Disable clocks in a device's PM clock list. 349 * @dev: Device to disable the clocks for. 350 */ 351 int pm_clk_suspend(struct device *dev) 352 { 353 struct pm_subsys_data *psd = dev_to_psd(dev); 354 struct pm_clock_entry *ce; 355 unsigned long flags; 356 357 dev_dbg(dev, "%s()\n", __func__); 358 359 /* If there is no driver, the clocks are already disabled. */ 360 if (!psd || !dev->driver) 361 return 0; 362 363 spin_lock_irqsave(&psd->lock, flags); 364 365 list_for_each_entry_reverse(ce, &psd->clock_list, node) 366 clk_disable(ce->clk); 367 368 spin_unlock_irqrestore(&psd->lock, flags); 369 370 return 0; 371 } 372 373 /** 374 * pm_clk_resume - Enable clocks in a device's PM clock list. 375 * @dev: Device to enable the clocks for. 376 */ 377 int pm_clk_resume(struct device *dev) 378 { 379 struct pm_subsys_data *psd = dev_to_psd(dev); 380 struct pm_clock_entry *ce; 381 unsigned long flags; 382 383 dev_dbg(dev, "%s()\n", __func__); 384 385 /* If there is no driver, the clocks should remain disabled. */ 386 if (!psd || !dev->driver) 387 return 0; 388 389 spin_lock_irqsave(&psd->lock, flags); 390 391 list_for_each_entry(ce, &psd->clock_list, node) 392 clk_enable(ce->clk); 393 394 spin_unlock_irqrestore(&psd->lock, flags); 395 396 return 0; 397 } 398 399 #endif /* CONFIG_PM */ 400 401 /** 402 * enable_clock - Enable a device clock. 403 * @dev: Device whose clock is to be enabled. 404 * @con_id: Connection ID of the clock. 405 */ 406 static void enable_clock(struct device *dev, const char *con_id) 407 { 408 struct clk *clk; 409 410 clk = clk_get(dev, con_id); 411 if (!IS_ERR(clk)) { 412 clk_enable(clk); 413 clk_put(clk); 414 dev_info(dev, "Runtime PM disabled, clock forced on.\n"); 415 } 416 } 417 418 /** 419 * disable_clock - Disable a device clock. 420 * @dev: Device whose clock is to be disabled. 421 * @con_id: Connection ID of the clock. 422 */ 423 static void disable_clock(struct device *dev, const char *con_id) 424 { 425 struct clk *clk; 426 427 clk = clk_get(dev, con_id); 428 if (!IS_ERR(clk)) { 429 clk_disable(clk); 430 clk_put(clk); 431 dev_info(dev, "Runtime PM disabled, clock forced off.\n"); 432 } 433 } 434 435 /** 436 * pm_clk_notify - Notify routine for device addition and removal. 437 * @nb: Notifier block object this function is a member of. 438 * @action: Operation being carried out by the caller. 439 * @data: Device the routine is being run for. 440 * 441 * For this function to work, @nb must be a member of an object of type 442 * struct pm_clk_notifier_block containing all of the requisite data. 443 * Specifically, the con_ids member of that object is used to enable or disable 444 * the device's clocks, depending on @action. 445 */ 446 static int pm_clk_notify(struct notifier_block *nb, 447 unsigned long action, void *data) 448 { 449 struct pm_clk_notifier_block *clknb; 450 struct device *dev = data; 451 char **con_id; 452 453 dev_dbg(dev, "%s() %ld\n", __func__, action); 454 455 clknb = container_of(nb, struct pm_clk_notifier_block, nb); 456 457 switch (action) { 458 case BUS_NOTIFY_BIND_DRIVER: 459 if (clknb->con_ids[0]) { 460 for (con_id = clknb->con_ids; *con_id; con_id++) 461 enable_clock(dev, *con_id); 462 } else { 463 enable_clock(dev, NULL); 464 } 465 break; 466 case BUS_NOTIFY_UNBOUND_DRIVER: 467 if (clknb->con_ids[0]) { 468 for (con_id = clknb->con_ids; *con_id; con_id++) 469 disable_clock(dev, *con_id); 470 } else { 471 disable_clock(dev, NULL); 472 } 473 break; 474 } 475 476 return 0; 477 } 478 479 #endif /* !CONFIG_PM_RUNTIME */ 480 481 /** 482 * pm_clk_add_notifier - Add bus type notifier for power management clocks. 483 * @bus: Bus type to add the notifier to. 484 * @clknb: Notifier to be added to the given bus type. 485 * 486 * The nb member of @clknb is not expected to be initialized and its 487 * notifier_call member will be replaced with pm_clk_notify(). However, 488 * the remaining members of @clknb should be populated prior to calling this 489 * routine. 490 */ 491 void pm_clk_add_notifier(struct bus_type *bus, 492 struct pm_clk_notifier_block *clknb) 493 { 494 if (!bus || !clknb) 495 return; 496 497 clknb->nb.notifier_call = pm_clk_notify; 498 bus_register_notifier(bus, &clknb->nb); 499 } 500