0001 =====================
0002 The OMAP PM interface
0003 =====================
0004
0005 This document describes the temporary OMAP PM interface. Driver
0006 authors use these functions to communicate minimum latency or
0007 throughput constraints to the kernel power management code.
0008 Over time, the intention is to merge features from the OMAP PM
0009 interface into the Linux PM QoS code.
0010
0011 Drivers need to express PM parameters which:
0012
0013 - support the range of power management parameters present in the TI SRF;
0014
0015 - separate the drivers from the underlying PM parameter
0016 implementation, whether it is the TI SRF or Linux PM QoS or Linux
0017 latency framework or something else;
0018
0019 - specify PM parameters in terms of fundamental units, such as
0020 latency and throughput, rather than units which are specific to OMAP
0021 or to particular OMAP variants;
0022
0023 - allow drivers which are shared with other architectures (e.g.,
0024 DaVinci) to add these constraints in a way which won't affect non-OMAP
0025 systems,
0026
0027 - can be implemented immediately with minimal disruption of other
0028 architectures.
0029
0030
0031 This document proposes the OMAP PM interface, including the following
0032 five power management functions for driver code:
0033
0034 1. Set the maximum MPU wakeup latency::
0035
0036 (*pdata->set_max_mpu_wakeup_lat)(struct device *dev, unsigned long t)
0037
0038 2. Set the maximum device wakeup latency::
0039
0040 (*pdata->set_max_dev_wakeup_lat)(struct device *dev, unsigned long t)
0041
0042 3. Set the maximum system DMA transfer start latency (CORE pwrdm)::
0043
0044 (*pdata->set_max_sdma_lat)(struct device *dev, long t)
0045
0046 4. Set the minimum bus throughput needed by a device::
0047
0048 (*pdata->set_min_bus_tput)(struct device *dev, u8 agent_id, unsigned long r)
0049
0050 5. Return the number of times the device has lost context::
0051
0052 (*pdata->get_dev_context_loss_count)(struct device *dev)
0053
0054
0055 Further documentation for all OMAP PM interface functions can be
0056 found in arch/arm/plat-omap/include/mach/omap-pm.h.
0057
0058
0059 The OMAP PM layer is intended to be temporary
0060 ---------------------------------------------
0061
0062 The intention is that eventually the Linux PM QoS layer should support
0063 the range of power management features present in OMAP3. As this
0064 happens, existing drivers using the OMAP PM interface can be modified
0065 to use the Linux PM QoS code; and the OMAP PM interface can disappear.
0066
0067
0068 Driver usage of the OMAP PM functions
0069 -------------------------------------
0070
0071 As the 'pdata' in the above examples indicates, these functions are
0072 exposed to drivers through function pointers in driver .platform_data
0073 structures. The function pointers are initialized by the `board-*.c`
0074 files to point to the corresponding OMAP PM functions:
0075
0076 - set_max_dev_wakeup_lat will point to
0077 omap_pm_set_max_dev_wakeup_lat(), etc. Other architectures which do
0078 not support these functions should leave these function pointers set
0079 to NULL. Drivers should use the following idiom::
0080
0081 if (pdata->set_max_dev_wakeup_lat)
0082 (*pdata->set_max_dev_wakeup_lat)(dev, t);
0083
0084 The most common usage of these functions will probably be to specify
0085 the maximum time from when an interrupt occurs, to when the device
0086 becomes accessible. To accomplish this, driver writers should use the
0087 set_max_mpu_wakeup_lat() function to constrain the MPU wakeup
0088 latency, and the set_max_dev_wakeup_lat() function to constrain the
0089 device wakeup latency (from clk_enable() to accessibility). For
0090 example::
0091
0092 /* Limit MPU wakeup latency */
0093 if (pdata->set_max_mpu_wakeup_lat)
0094 (*pdata->set_max_mpu_wakeup_lat)(dev, tc);
0095
0096 /* Limit device powerdomain wakeup latency */
0097 if (pdata->set_max_dev_wakeup_lat)
0098 (*pdata->set_max_dev_wakeup_lat)(dev, td);
0099
0100 /* total wakeup latency in this example: (tc + td) */
0101
0102 The PM parameters can be overwritten by calling the function again
0103 with the new value. The settings can be removed by calling the
0104 function with a t argument of -1 (except in the case of
0105 set_max_bus_tput(), which should be called with an r argument of 0).
0106
0107 The fifth function above, omap_pm_get_dev_context_loss_count(),
0108 is intended as an optimization to allow drivers to determine whether the
0109 device has lost its internal context. If context has been lost, the
0110 driver must restore its internal context before proceeding.
0111
0112
0113 Other specialized interface functions
0114 -------------------------------------
0115
0116 The five functions listed above are intended to be usable by any
0117 device driver. DSPBridge and CPUFreq have a few special requirements.
0118 DSPBridge expresses target DSP performance levels in terms of OPP IDs.
0119 CPUFreq expresses target MPU performance levels in terms of MPU
0120 frequency. The OMAP PM interface contains functions for these
0121 specialized cases to convert that input information (OPPs/MPU
0122 frequency) into the form that the underlying power management
0123 implementation needs:
0124
0125 6. `(*pdata->dsp_get_opp_table)(void)`
0126
0127 7. `(*pdata->dsp_set_min_opp)(u8 opp_id)`
0128
0129 8. `(*pdata->dsp_get_opp)(void)`
0130
0131 9. `(*pdata->cpu_get_freq_table)(void)`
0132
0133 10. `(*pdata->cpu_set_freq)(unsigned long f)`
0134
0135 11. `(*pdata->cpu_get_freq)(void)`
0136
0137 Customizing OPP for platform
0138 ============================
0139 Defining CONFIG_PM should enable OPP layer for the silicon
0140 and the registration of OPP table should take place automatically.
0141 However, in special cases, the default OPP table may need to be
0142 tweaked, for e.g.:
0143
0144 * enable default OPPs which are disabled by default, but which
0145 could be enabled on a platform
0146 * Disable an unsupported OPP on the platform
0147 * Define and add a custom opp table entry
0148 in these cases, the board file needs to do additional steps as follows:
0149
0150 arch/arm/mach-omapx/board-xyz.c::
0151
0152 #include "pm.h"
0153 ....
0154 static void __init omap_xyz_init_irq(void)
0155 {
0156 ....
0157 /* Initialize the default table */
0158 omapx_opp_init();
0159 /* Do customization to the defaults */
0160 ....
0161 }
0162
0163 NOTE:
0164 omapx_opp_init will be omap3_opp_init or as required
0165 based on the omap family.