1 /* SPDX-License-Identifier: BSD-2-Clause */ 2 /* 3 * Copyright (c) 2023, STMicroelectronics 4 */ 5 #ifndef DRIVERS_REGULATOR_H 6 #define DRIVERS_REGULATOR_H 7 8 #include <assert.h> 9 #include <bitstring.h> 10 #include <kernel/mutex.h> 11 #include <sys/queue.h> 12 #include <tee_api_types.h> 13 #include <stdbool.h> 14 #include <stdint.h> 15 #include <util.h> 16 17 /* Regulator property flags: related to device tree binding properties */ 18 19 /* Regulator should never be disabled. DT property: regulator-always-on */ 20 #define REGULATOR_ALWAYS_ON BIT(0) 21 /* Enables pull down mode. DT property: regulator-pull-down */ 22 #define REGULATOR_PULL_DOWN BIT(1) 23 24 #define REGULATOR_FLAGS_MASK (REGULATOR_ALWAYS_ON | REGULATOR_PULL_DOWN) 25 26 struct regulator_ops; 27 28 /* 29 * struct regu_dt_desc - Regulator description passed to regulator_dt_register() 30 * @priv: Regulator driver private data 31 * @name: Regulator string name for debug purpose 32 * @supply_name: Regulator supply name for node property *-supply or NULL 33 * @ops: Operation handlers for the regulator 34 * @regulator: Pointer to preallocated regulator or NULL if none 35 */ 36 struct regu_dt_desc { 37 void *priv; 38 char *name; 39 const char *supply_name; 40 const struct regulator_ops *ops; 41 struct regulator *regulator; 42 }; 43 44 /* 45 * Defines the format of struct voltages::entries 46 * 47 * If regulator_voltages::type is VOLTAGE_TYPE_FULL_LIST, then 48 * regulator_voltages@entries stores regulator_voltages::num_levels cells, 49 * listing supported voltage levels in uV from lowest to highest value. 50 * 51 * If regulator_voltages::type is VOLTAGE_TYPE_INCREMENT, then 52 * regulator_voltages::entries stores 3 cells: min level, max level and 53 * level increment step, all in uV. When so, regulator_voltages::num_levels 54 * is meaningless. 55 */ 56 enum voltage_type { 57 VOLTAGE_TYPE_INVALID = 0, 58 VOLTAGE_TYPE_FULL_LIST, /* extensive list in uV */ 59 VOLTAGE_TYPE_INCREMENT /* min, max, increment (in uV) */ 60 }; 61 62 /* 63 * struct regulator_voltages - Voltage levels description 64 * @type: Type of level description 65 * @num_levels: Number of cells of @entries when @type is VOLTAGE_TYPE_FULL_LIST 66 * @entries: Voltage level information in uV 67 * 68 */ 69 struct regulator_voltages { 70 enum voltage_type type; 71 size_t num_levels; 72 int entries[]; 73 }; 74 75 /* 76 * struct regulator - A regulator instance 77 * @ops: Operation handlers for the regulator 78 * @supply: Regulator supply reference or NULL if none 79 * @priv: Regulator driver private data 80 * @name: Regulator string name for debug purpose or NULL 81 * @min_uv: Min possible voltage level in microvolt (uV) 82 * @max_uv: Max possible voltage level in microvolt (uV) 83 * @cur_uv: Current voltage level in microvolt (uV) 84 * @flags: REGULATOR_* property flags 85 * @refcount: Regulator enable request reference counter 86 * @lock: Mutex for concurrent access protection 87 * @voltages_fallback: Default supported voltage range description 88 * @link: Link in initialized regulator list 89 */ 90 struct regulator { 91 /* Fields initialized by caller of regulator_register() */ 92 const struct regulator_ops *ops; 93 struct regulator *supply; 94 void *priv; 95 char *name; 96 int min_uv; 97 int max_uv; 98 /* Fields internal to regulator framework */ 99 int cur_uv; 100 unsigned int flags; 101 unsigned int refcount; 102 struct mutex lock; /* Concurrent access protection */ 103 struct voltages_fallback { 104 struct regulator_voltages desc; 105 int levels[3]; 106 } voltages_fallback; 107 size_t levels_count_fallback; 108 SLIST_ENTRY(regulator) link; 109 }; 110 111 /* 112 * struct regulator_ops - Regulator operation handlers 113 * 114 * @set_state: Enable or disable a regulator 115 * @get_state: Get regulator effective state 116 * @set_voltage: Set voltage level in microvolt (uV) 117 * @get_voltage: Get current voltage in microvolt (uV) 118 * @supported_voltages: Get supported levels description 119 * @supplied_init: Optional, finalize initialization once supply is ready 120 */ 121 struct regulator_ops { 122 TEE_Result (*set_state)(struct regulator *r, bool enabled); 123 TEE_Result (*get_state)(struct regulator *r, bool *enabled); 124 TEE_Result (*set_voltage)(struct regulator *r, int level_uv); 125 TEE_Result (*get_voltage)(struct regulator *r, int *level_uv); 126 TEE_Result (*supported_voltages)(struct regulator *r, 127 struct regulator_voltages **voltages); 128 TEE_Result (*supplied_init)(struct regulator *r, const void *fdt, 129 int node); 130 }; 131 132 #ifdef CFG_DRIVERS_REGULATOR 133 /* 134 * regulator_enable() - Enable regulator 135 * @regulator: Regulator reference 136 */ 137 TEE_Result regulator_enable(struct regulator *regulator); 138 139 /* 140 * regulator_disable() - Disable regulator 141 * @regulator: Regulator reference 142 */ 143 TEE_Result regulator_disable(struct regulator *regulator); 144 145 /* 146 * regulator_is_enabled() - Return whether or not regulator is currently enabled 147 * despite its refcount value. 148 * @regulator: Regulator reference 149 */ 150 bool regulator_is_enabled(struct regulator *regulator); 151 152 /* 153 * regulator_set_voltage() - Set regulator to target level in microvolt 154 * @regulator: Regulator reference 155 * @level_uv: Level in microvolt 156 */ 157 TEE_Result regulator_set_voltage(struct regulator *regulator, int level_uv); 158 159 /* 160 * regulator_register() - Register and initialize a regulator 161 * @regulator: Regulator reference 162 */ 163 TEE_Result regulator_register(struct regulator *regulator); 164 165 /* Print registered regulators and their state to the output console */ 166 void regulator_print_state(const char *message); 167 #else 168 static inline TEE_Result regulator_enable(struct regulator *regulator __unused) 169 { 170 return TEE_ERROR_NOT_SUPPORTED; 171 } 172 173 static inline TEE_Result regulator_disable(struct regulator *regulator __unused) 174 { 175 return TEE_ERROR_NOT_SUPPORTED; 176 } 177 178 static inline bool regulator_is_enabled(struct regulator *regulator __unused) 179 { 180 return false; 181 } 182 183 static inline TEE_Result regulator_set_voltage(struct regulator *regul __unused, 184 int level_mv __unused) 185 { 186 return TEE_ERROR_NOT_SUPPORTED; 187 } 188 189 static inline TEE_Result regulator_init(struct regulator *regulator __unused) 190 { 191 return TEE_ERROR_NOT_SUPPORTED; 192 } 193 194 static inline void regulator_print_state(const char *message __unused) 195 { 196 } 197 #endif /*CFG_DRIVERS_REGULATOR*/ 198 199 #if defined(CFG_DRIVERS_REGULATOR) && defined(CFG_DT) 200 /* 201 * regulator_dt_get_supply() - Get a regulator supply from name and DT node 202 * @fdt: FDT to work on 203 * @node: DT node of the regulator consumer 204 * @supply_name: Name of the supply in DT property xxx-supply 205 * @regulator: Output regulator upon success 206 * 207 * Upon success, this function provides the pointer to regulator 208 * defined by DT binding property @name-supply phandle reference. 209 * 210 * This function returns TEE_ERROR_DEFER_DRIVER_INIT if supply exists but is 211 * not yet initialized. 212 */ 213 TEE_Result regulator_dt_get_supply(const void *fdt, int node, 214 const char *supply_name, 215 struct regulator **regulator); 216 217 /* 218 * regulator_dt_register() - Register a regulator to related to a DT node 219 * @fdt: FDT to work on 220 * @node: DT node of the regulator exposed by regulator driver 221 * @provider_node: Node where xxx-supply property is found or -1 if no supply. 222 * @desc: Description of the regulator to register 223 * 224 * This function registers and initializes a regulator instance once its supply 225 * if found, if any. Regulators registered with this function can be found by 226 * their consumer drivers using API function regulator_dt_get_supply() or like. 227 * 228 * Return TEE_SUCCESS in case of success 229 * Return TEE_ERROR_OUT_OF_MEMORY if failed on memory allocation 230 * Return any other TEE_Result compliant code in case of error 231 */ 232 TEE_Result regulator_dt_register(const void *fdt, int node, int provider_node, 233 const struct regu_dt_desc *desc); 234 #else 235 static inline TEE_Result regulator_dt_get_supply(const void *fdt __unused, 236 int node __unused, 237 const char *supply __unused, 238 struct regulator **r __unused) 239 { 240 return TEE_ERROR_NOT_SUPPORTED; 241 } 242 243 static inline TEE_Result 244 regulator_dt_register(const void *fdt __unused, int node __unused, 245 int provider_node __unused, 246 const struct regu_dt_desc *d __unused) 247 { 248 return TEE_ERROR_NOT_SUPPORTED; 249 } 250 #endif /* CFG_DRIVERS_REGULATOR && CFG_DT */ 251 252 /* 253 * regulator_name() - Return regulator name or NULL 254 * @regulator: Regulator reference 255 */ 256 static inline const char *regulator_name(struct regulator *regulator) 257 { 258 return regulator->name; 259 } 260 261 /* 262 * regulator_is_always_on() - Return the state of REGULATOR_ALWAYS_ON flag 263 * @regulator: Regulator reference 264 */ 265 static inline bool regulator_is_always_on(struct regulator *regulator) 266 { 267 return regulator->flags & REGULATOR_ALWAYS_ON; 268 } 269 270 /* 271 * regulator_set_min_voltage() - Set regulator to its min level 272 * @regulator: Regulator reference 273 */ 274 static inline TEE_Result regulator_set_min_voltage(struct regulator *regulator) 275 { 276 return regulator_set_voltage(regulator, regulator->min_uv); 277 } 278 279 /* 280 * regulator_get_voltage() - Get regulator current level in microvolt 281 * @regulator: Regulator reference 282 */ 283 static inline int regulator_get_voltage(struct regulator *regulator) 284 { 285 return regulator->cur_uv; 286 } 287 288 /* 289 * regulator_get_range() - Get regulator min and/or max support levels 290 * @regulator: Regulator reference 291 * @min_mv: Output reference to min level in microvolt (uV) or NULL 292 * @max_mv: Output reference to max level in microvolt (uV) or NULL 293 */ 294 static inline void regulator_get_range(struct regulator *regulator, int *min_uv, 295 int *max_uv) 296 { 297 assert(regulator); 298 if (min_uv) 299 *min_uv = regulator->min_uv; 300 if (max_uv) 301 *max_uv = regulator->max_uv; 302 } 303 304 /* 305 * regulator_supported_voltages() - Get regulator supported levels in microvolt 306 * @regulator: Regulator reference 307 * @voltages: Output description supported voltage levels 308 */ 309 TEE_Result regulator_supported_voltages(struct regulator *regulator, 310 struct regulator_voltages **voltages); 311 #endif /* DRIVERS_REGULATOR_H */ 312