| 1 | |
| 2 | |
| 3 |
|
| 4 | ====================
|
| 5 | Power Sequencing API
|
| 6 | ====================
|
| 7 |
|
| 8 | :Author: Bartosz Golaszewski
|
| 9 |
|
| 10 | Introduction
|
| 11 | ============
|
| 12 |
|
| 13 | This framework is designed to abstract complex power-up sequences that are
|
| 14 | shared between multiple logical devices in the Linux kernel.
|
| 15 |
|
| 16 | The intention is to allow consumers to obtain a power sequencing handle
|
| 17 | exposed by the power sequence provider and delegate the actual requesting and
|
| 18 | control of the underlying resources as well as to allow the provider to
|
| 19 | mitigate any potential conflicts between multiple users behind the scenes.
|
| 20 |
|
| 21 | Glossary
|
| 22 | --------
|
| 23 |
|
| 24 | The power sequencing API uses a number of terms specific to the subsystem:
|
| 25 |
|
| 26 | Unit
|
| 27 |
|
| 28 | A unit is a discrete chunk of a power sequence. For instance one unit may
|
| 29 | enable a set of regulators, another may enable a specific GPIO. Units can
|
| 30 | define dependencies in the form of other units that must be enabled before
|
| 31 | it itself can be.
|
| 32 |
|
| 33 | Target
|
| 34 |
|
| 35 | A target is a set of units (composed of the "final" unit and its
|
| 36 | dependencies) that a consumer selects by its name when requesting a handle
|
| 37 | to the power sequencer. Via the dependency system, multiple targets may
|
| 38 | share the same parts of a power sequence but ignore parts that are
|
| 39 | irrelevant.
|
| 40 |
|
| 41 | Descriptor
|
| 42 |
|
| 43 | A handle passed by the pwrseq core to every consumer that serves as the
|
| 44 | entry point to the provider layer. It ensures coherence between different
|
| 45 | users and keeps reference counting consistent.
|
| 46 |
|
| 47 | Consumer interface
|
| 48 | ==================
|
| 49 |
|
| 50 | The consumer API is aimed to be as simple as possible. The driver interested in
|
| 51 | getting a descriptor from the power sequencer should call pwrseq_get() and
|
| 52 | specify the name of the target it wants to reach in the sequence after calling
|
| 53 | pwrseq_enable(). The descriptor can be released by calling pwrseq_put() and
|
| 54 | the consumer can request the powering down of its target with
|
| 55 | pwrseq_disable(). Note that there is no guarantee that pwrseq_disable()
|
| 56 | will have any effect as there may be multiple users of the underlying resources
|
| 57 | who may keep them active.
|
| 58 |
|
| 59 | Provider interface
|
| 60 | ==================
|
| 61 |
|
| 62 | The provider API is admittedly not nearly as straightforward as the one for
|
| 63 | consumers but it makes up for it in flexibility.
|
| 64 |
|
| 65 | Each provider can logically split the power-up sequence into discrete chunks
|
| 66 | (units) and define their dependencies. They can then expose named targets that
|
| 67 | consumers may use as the final point in the sequence that they wish to reach.
|
| 68 |
|
| 69 | To that end the providers fill out a set of configuration structures and
|
| 70 | register with the pwrseq subsystem by calling pwrseq_device_register().
|
| 71 |
|
| 72 | Dynamic consumer matching
|
| 73 | -------------------------
|
| 74 |
|
| 75 | The main difference between pwrseq and other Linux kernel providers is the
|
| 76 | mechanism for dynamic matching of consumers and providers. Every power sequence
|
| 77 | provider driver must implement the `match()` callback and pass it to the pwrseq
|
| 78 | core when registering with the subsystems.
|
| 79 |
|
| 80 | When a client requests a sequencer handle, the core will call this callback for
|
| 81 | every registered provider and let it flexibly figure out whether the proposed
|
| 82 | client device is indeed its consumer. For example: if the provider binds to the
|
| 83 | device-tree node representing a power management unit of a chipset and the
|
| 84 | consumer driver controls one of its modules, the provider driver may parse the
|
| 85 | relevant regulator supply properties in device tree and see if they lead from
|
| 86 | the PMU to the consumer.
|
| 87 |
|
| 88 | API reference
|
| 89 | =============
|
| 90 |
|
| 91 | .. kernel-doc:: include/linux/pwrseq/provider.h
|
| 92 | :internal:
|
| 93 |
|
| 94 | .. kernel-doc:: drivers/power/sequencing/core.c
|
| 95 | :export:
|