xref: /optee_os/core/drivers/stpmic1.c (revision 8c49825d6ae074d38cec500c80a60194835e1dca)
1 // SPDX-License-Identifier: BSD-3-Clause
2 /*
3  * Copyright (c) 2016-2020, STMicroelectronics - All Rights Reserved
4  */
5 
6 #include <assert.h>
7 #include <drivers/stpmic1.h>
8 #include <drivers/stpmic1_regulator.h>
9 #include <kernel/panic.h>
10 #include <platform_config.h>
11 #include <stdint.h>
12 #include <string.h>
13 #include <trace.h>
14 #include <util.h>
15 
16 #define VOLTAGE_INDEX_INVALID		((unsigned int)~0)
17 
18 struct regul_struct {
19 	const char *dt_node_name;
20 	const uint16_t *voltage_table;
21 	uint8_t voltage_table_size;
22 	uint8_t control_reg;
23 	uint8_t low_power_reg;
24 	uint8_t enable_pos;
25 	uint8_t pull_down_reg;
26 	uint8_t pull_down_pos;
27 	uint8_t mask_reset_reg;
28 	uint8_t mask_reset_pos;
29 };
30 
31 static struct i2c_handle_s *pmic_i2c_handle;
32 static uint16_t pmic_i2c_addr;
33 
34 /* Voltage tables in mV */
35 static const uint16_t buck1_voltage_table[] = {
36 	725,
37 	725,
38 	725,
39 	725,
40 	725,
41 	725,
42 	750,
43 	775,
44 	800,
45 	825,
46 	850,
47 	875,
48 	900,
49 	925,
50 	950,
51 	975,
52 	1000,
53 	1025,
54 	1050,
55 	1075,
56 	1100,
57 	1125,
58 	1150,
59 	1175,
60 	1200,
61 	1225,
62 	1250,
63 	1275,
64 	1300,
65 	1325,
66 	1350,
67 	1375,
68 	1400,
69 	1425,
70 	1450,
71 	1475,
72 	1500,
73 	1500,
74 	1500,
75 	1500,
76 	1500,
77 	1500,
78 	1500,
79 	1500,
80 	1500,
81 	1500,
82 	1500,
83 	1500,
84 	1500,
85 	1500,
86 	1500,
87 	1500,
88 	1500,
89 	1500,
90 	1500,
91 	1500,
92 	1500,
93 	1500,
94 	1500,
95 	1500,
96 	1500,
97 	1500,
98 	1500,
99 	1500,
100 };
101 
102 static const uint16_t buck2_voltage_table[] = {
103 	1000,
104 	1000,
105 	1000,
106 	1000,
107 	1000,
108 	1000,
109 	1000,
110 	1000,
111 	1000,
112 	1000,
113 	1000,
114 	1000,
115 	1000,
116 	1000,
117 	1000,
118 	1000,
119 	1000,
120 	1000,
121 	1050,
122 	1050,
123 	1100,
124 	1100,
125 	1150,
126 	1150,
127 	1200,
128 	1200,
129 	1250,
130 	1250,
131 	1300,
132 	1300,
133 	1350,
134 	1350,
135 	1400,
136 	1400,
137 	1450,
138 	1450,
139 	1500,
140 };
141 
142 static const uint16_t buck3_voltage_table[] = {
143 	1000,
144 	1000,
145 	1000,
146 	1000,
147 	1000,
148 	1000,
149 	1000,
150 	1000,
151 	1000,
152 	1000,
153 	1000,
154 	1000,
155 	1000,
156 	1000,
157 	1000,
158 	1000,
159 	1000,
160 	1000,
161 	1000,
162 	1000,
163 	1100,
164 	1100,
165 	1100,
166 	1100,
167 	1200,
168 	1200,
169 	1200,
170 	1200,
171 	1300,
172 	1300,
173 	1300,
174 	1300,
175 	1400,
176 	1400,
177 	1400,
178 	1400,
179 	1500,
180 	1600,
181 	1700,
182 	1800,
183 	1900,
184 	2000,
185 	2100,
186 	2200,
187 	2300,
188 	2400,
189 	2500,
190 	2600,
191 	2700,
192 	2800,
193 	2900,
194 	3000,
195 	3100,
196 	3200,
197 	3300,
198 	3400,
199 };
200 
201 static const uint16_t buck4_voltage_table[] = {
202 	600,
203 	625,
204 	650,
205 	675,
206 	700,
207 	725,
208 	750,
209 	775,
210 	800,
211 	825,
212 	850,
213 	875,
214 	900,
215 	925,
216 	950,
217 	975,
218 	1000,
219 	1025,
220 	1050,
221 	1075,
222 	1100,
223 	1125,
224 	1150,
225 	1175,
226 	1200,
227 	1225,
228 	1250,
229 	1275,
230 	1300,
231 	1300,
232 	1350,
233 	1350,
234 	1400,
235 	1400,
236 	1450,
237 	1450,
238 	1500,
239 	1600,
240 	1700,
241 	1800,
242 	1900,
243 	2000,
244 	2100,
245 	2200,
246 	2300,
247 	2400,
248 	2500,
249 	2600,
250 	2700,
251 	2800,
252 	2900,
253 	3000,
254 	3100,
255 	3200,
256 	3300,
257 	3400,
258 	3500,
259 	3600,
260 	3700,
261 	3800,
262 	3900,
263 };
264 
265 static const uint16_t ldo1_voltage_table[] = {
266 	1700,
267 	1700,
268 	1700,
269 	1700,
270 	1700,
271 	1700,
272 	1700,
273 	1700,
274 	1700,
275 	1800,
276 	1900,
277 	2000,
278 	2100,
279 	2200,
280 	2300,
281 	2400,
282 	2500,
283 	2600,
284 	2700,
285 	2800,
286 	2900,
287 	3000,
288 	3100,
289 	3200,
290 	3300,
291 };
292 
293 static const uint16_t ldo2_voltage_table[] = {
294 	1700,
295 	1700,
296 	1700,
297 	1700,
298 	1700,
299 	1700,
300 	1700,
301 	1700,
302 	1700,
303 	1800,
304 	1900,
305 	2000,
306 	2100,
307 	2200,
308 	2300,
309 	2400,
310 	2500,
311 	2600,
312 	2700,
313 	2800,
314 	2900,
315 	3000,
316 	3100,
317 	3200,
318 	3300,
319 };
320 
321 static const uint16_t ldo3_voltage_table[] = {
322 	1700,
323 	1700,
324 	1700,
325 	1700,
326 	1700,
327 	1700,
328 	1700,
329 	1700,
330 	1700,
331 	1800,
332 	1900,
333 	2000,
334 	2100,
335 	2200,
336 	2300,
337 	2400,
338 	2500,
339 	2600,
340 	2700,
341 	2800,
342 	2900,
343 	3000,
344 	3100,
345 	3200,
346 	3300,
347 	3300,
348 	3300,
349 	3300,
350 	3300,
351 	3300,
352 	3300,
353 	500,	/* VOUT2/2 (Sink/source mode) */
354 	0xFFFF, /* VREFDDR */
355 };
356 
357 static const uint16_t ldo5_voltage_table[] = {
358 	1700,
359 	1700,
360 	1700,
361 	1700,
362 	1700,
363 	1700,
364 	1700,
365 	1700,
366 	1700,
367 	1800,
368 	1900,
369 	2000,
370 	2100,
371 	2200,
372 	2300,
373 	2400,
374 	2500,
375 	2600,
376 	2700,
377 	2800,
378 	2900,
379 	3000,
380 	3100,
381 	3200,
382 	3300,
383 	3400,
384 	3500,
385 	3600,
386 	3700,
387 	3800,
388 	3900,
389 };
390 
391 static const uint16_t ldo6_voltage_table[] = {
392 	900,
393 	1000,
394 	1100,
395 	1200,
396 	1300,
397 	1400,
398 	1500,
399 	1600,
400 	1700,
401 	1800,
402 	1900,
403 	2000,
404 	2100,
405 	2200,
406 	2300,
407 	2400,
408 	2500,
409 	2600,
410 	2700,
411 	2800,
412 	2900,
413 	3000,
414 	3100,
415 	3200,
416 	3300,
417 };
418 
419 static const uint16_t ldo4_voltage_table[] = {
420 	3300,
421 };
422 
423 static const uint16_t vref_ddr_voltage_table[] = {
424 	3300,
425 };
426 
427 static const uint16_t fixed_5v_voltage_table[] = {
428 	5000,
429 };
430 
431 /* Table of Regulators in PMIC SoC */
432 static const struct regul_struct regulators_table[] = {
433 	{
434 		.dt_node_name	= "buck1",
435 		.voltage_table	= buck1_voltage_table,
436 		.voltage_table_size = ARRAY_SIZE(buck1_voltage_table),
437 		.control_reg	= BUCK1_CONTROL_REG,
438 		.low_power_reg	= BUCK1_PWRCTRL_REG,
439 		.enable_pos	= LDO_BUCK_ENABLE_POS,
440 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
441 		.pull_down_pos	= BUCK1_PULL_DOWN_SHIFT,
442 		.mask_reset_reg = MASK_RESET_BUCK_REG,
443 		.mask_reset_pos = BUCK1_MASK_RESET_SHIFT,
444 	},
445 	{
446 		.dt_node_name	= "buck2",
447 		.voltage_table	= buck2_voltage_table,
448 		.voltage_table_size = ARRAY_SIZE(buck2_voltage_table),
449 		.control_reg	= BUCK2_CONTROL_REG,
450 		.low_power_reg	= BUCK2_PWRCTRL_REG,
451 		.enable_pos	= LDO_BUCK_ENABLE_POS,
452 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
453 		.pull_down_pos	= BUCK2_PULL_DOWN_SHIFT,
454 		.mask_reset_reg = MASK_RESET_BUCK_REG,
455 		.mask_reset_pos = BUCK2_MASK_RESET_SHIFT,
456 	},
457 	{
458 		.dt_node_name	= "buck3",
459 		.voltage_table	= buck3_voltage_table,
460 		.voltage_table_size = ARRAY_SIZE(buck3_voltage_table),
461 		.control_reg	= BUCK3_CONTROL_REG,
462 		.low_power_reg	= BUCK3_PWRCTRL_REG,
463 		.enable_pos	= LDO_BUCK_ENABLE_POS,
464 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
465 		.pull_down_pos	= BUCK3_PULL_DOWN_SHIFT,
466 		.mask_reset_reg = MASK_RESET_BUCK_REG,
467 		.mask_reset_pos = BUCK3_MASK_RESET_SHIFT,
468 	},
469 	{
470 		.dt_node_name	= "buck4",
471 		.voltage_table	= buck4_voltage_table,
472 		.voltage_table_size = ARRAY_SIZE(buck4_voltage_table),
473 		.control_reg	= BUCK4_CONTROL_REG,
474 		.low_power_reg	= BUCK4_PWRCTRL_REG,
475 		.enable_pos	= LDO_BUCK_ENABLE_POS,
476 		.pull_down_reg	= BUCK_PULL_DOWN_REG,
477 		.pull_down_pos	= BUCK4_PULL_DOWN_SHIFT,
478 		.mask_reset_reg = MASK_RESET_BUCK_REG,
479 		.mask_reset_pos = BUCK4_MASK_RESET_SHIFT,
480 	},
481 	{
482 		.dt_node_name	= "ldo1",
483 		.voltage_table	= ldo1_voltage_table,
484 		.voltage_table_size = ARRAY_SIZE(ldo1_voltage_table),
485 		.control_reg	= LDO1_CONTROL_REG,
486 		.low_power_reg	= LDO1_PWRCTRL_REG,
487 		.enable_pos	= LDO_BUCK_ENABLE_POS,
488 		.mask_reset_reg = MASK_RESET_LDO_REG,
489 		.mask_reset_pos = LDO1_MASK_RESET_SHIFT,
490 	},
491 	{
492 		.dt_node_name	= "ldo2",
493 		.voltage_table	= ldo2_voltage_table,
494 		.voltage_table_size = ARRAY_SIZE(ldo2_voltage_table),
495 		.control_reg	= LDO2_CONTROL_REG,
496 		.low_power_reg	= LDO2_PWRCTRL_REG,
497 		.enable_pos	= LDO_BUCK_ENABLE_POS,
498 		.mask_reset_reg = MASK_RESET_LDO_REG,
499 		.mask_reset_pos = LDO2_MASK_RESET_SHIFT,
500 	},
501 	{
502 		.dt_node_name	= "ldo3",
503 		.voltage_table	= ldo3_voltage_table,
504 		.voltage_table_size = ARRAY_SIZE(ldo3_voltage_table),
505 		.control_reg	= LDO3_CONTROL_REG,
506 		.low_power_reg	= LDO3_PWRCTRL_REG,
507 		.enable_pos	= LDO_BUCK_ENABLE_POS,
508 		.mask_reset_reg = MASK_RESET_LDO_REG,
509 		.mask_reset_pos = LDO3_MASK_RESET_SHIFT,
510 	},
511 	{
512 		.dt_node_name	= "ldo4",
513 		.voltage_table	= ldo4_voltage_table,
514 		.voltage_table_size = ARRAY_SIZE(ldo4_voltage_table),
515 		.control_reg	= LDO4_CONTROL_REG,
516 		.low_power_reg	= LDO4_PWRCTRL_REG,
517 		.enable_pos	= LDO_BUCK_ENABLE_POS,
518 		.mask_reset_reg = MASK_RESET_LDO_REG,
519 		.mask_reset_pos = LDO4_MASK_RESET_SHIFT,
520 	},
521 	{
522 		.dt_node_name	= "ldo5",
523 		.voltage_table	= ldo5_voltage_table,
524 		.voltage_table_size = ARRAY_SIZE(ldo5_voltage_table),
525 		.control_reg	= LDO5_CONTROL_REG,
526 		.low_power_reg	= LDO5_PWRCTRL_REG,
527 		.enable_pos	= LDO_BUCK_ENABLE_POS,
528 		.mask_reset_reg = MASK_RESET_LDO_REG,
529 		.mask_reset_pos = LDO5_MASK_RESET_SHIFT,
530 	},
531 	{
532 		.dt_node_name	= "ldo6",
533 		.voltage_table	= ldo6_voltage_table,
534 		.voltage_table_size = ARRAY_SIZE(ldo6_voltage_table),
535 		.control_reg	= LDO6_CONTROL_REG,
536 		.low_power_reg	= LDO6_PWRCTRL_REG,
537 		.enable_pos	= LDO_BUCK_ENABLE_POS,
538 		.mask_reset_reg = MASK_RESET_LDO_REG,
539 		.mask_reset_pos = LDO6_MASK_RESET_SHIFT,
540 	},
541 	{
542 		.dt_node_name	= "vref_ddr",
543 		.voltage_table	= vref_ddr_voltage_table,
544 		.voltage_table_size = ARRAY_SIZE(vref_ddr_voltage_table),
545 		.control_reg	= VREF_DDR_CONTROL_REG,
546 		.low_power_reg	= VREF_DDR_PWRCTRL_REG,
547 		.enable_pos	= LDO_BUCK_ENABLE_POS,
548 		.mask_reset_reg = MASK_RESET_LDO_REG,
549 		.mask_reset_pos = VREF_DDR_MASK_RESET_SHIFT,
550 	},
551 	{
552 		.dt_node_name = "boost",
553 		.voltage_table	= fixed_5v_voltage_table,
554 		.voltage_table_size = ARRAY_SIZE(fixed_5v_voltage_table),
555 		.control_reg	= USB_CONTROL_REG,
556 		.enable_pos	= BOOST_ENABLED_POS,
557 	},
558 	{
559 		.dt_node_name	= "pwr_sw1",
560 		.voltage_table	= fixed_5v_voltage_table,
561 		.voltage_table_size = ARRAY_SIZE(fixed_5v_voltage_table),
562 		.control_reg	= USB_CONTROL_REG,
563 		.enable_pos	= USBSW_OTG_SWITCH_ENABLED_POS,
564 	},
565 	{
566 		.dt_node_name	= "pwr_sw2",
567 		.voltage_table	= fixed_5v_voltage_table,
568 		.voltage_table_size = ARRAY_SIZE(fixed_5v_voltage_table),
569 		.control_reg	= USB_CONTROL_REG,
570 		.enable_pos	= SWIN_SWOUT_ENABLED_POS,
571 	},
572 };
573 
get_regulator_data(const char * name)574 static const struct regul_struct *get_regulator_data(const char *name)
575 {
576 	unsigned int i = 0;
577 
578 	for (i = 0; i < ARRAY_SIZE(regulators_table); i++)
579 		if (strcmp(name, regulators_table[i].dt_node_name) == 0)
580 			return &regulators_table[i];
581 
582 	DMSG("Regulator %s not found", name);
583 	return NULL;
584 }
585 
stpmic1_regulator_is_valid(const char * name)586 bool stpmic1_regulator_is_valid(const char *name)
587 {
588 	return get_regulator_data(name);
589 }
590 
stpmic1_regulator_levels_mv(const char * name,const uint16_t ** levels,size_t * levels_count)591 void stpmic1_regulator_levels_mv(const char *name,
592 				 const uint16_t **levels,
593 				 size_t *levels_count)
594 {
595 	const struct regul_struct *regul = get_regulator_data(name);
596 
597 	assert(regul);
598 
599 	if (levels_count) {
600 		*levels_count = regul->voltage_table_size;
601 
602 		/* Remove last cell 0xFFFF that is not a voltage level */
603 		if (regul->voltage_table == ldo3_voltage_table)
604 			(*levels_count)--;
605 	}
606 
607 	if (levels)
608 		*levels = regul->voltage_table;
609 }
610 
voltage_to_index(const char * name,uint16_t millivolts)611 static size_t voltage_to_index(const char *name, uint16_t millivolts)
612 {
613 	const struct regul_struct *regul = get_regulator_data(name);
614 	unsigned int i = 0;
615 
616 	assert(regul->voltage_table);
617 	for (i = 0; i < regul->voltage_table_size; i++)
618 		if (regul->voltage_table[i] == millivolts)
619 			return i;
620 
621 	return VOLTAGE_INDEX_INVALID;
622 }
623 
stpmic1_powerctrl_on(void)624 int stpmic1_powerctrl_on(void)
625 {
626 	return stpmic1_register_update(MAIN_CONTROL_REG, PWRCTRL_PIN_VALID,
627 				       PWRCTRL_PIN_VALID);
628 }
629 
stpmic1_switch_off(void)630 int stpmic1_switch_off(void)
631 {
632 	return stpmic1_register_update(MAIN_CONTROL_REG, 1,
633 				       SOFTWARE_SWITCH_OFF_ENABLED);
634 }
635 
stpmic1_regulator_enable(const char * name)636 int stpmic1_regulator_enable(const char *name)
637 {
638 	const struct regul_struct *regul = get_regulator_data(name);
639 
640 	return stpmic1_register_update(regul->control_reg,
641 				       BIT(regul->enable_pos),
642 				       BIT(regul->enable_pos));
643 }
644 
stpmic1_regulator_disable(const char * name)645 int stpmic1_regulator_disable(const char *name)
646 {
647 	const struct regul_struct *regul = get_regulator_data(name);
648 
649 	return stpmic1_register_update(regul->control_reg, 0,
650 				       BIT(regul->enable_pos));
651 }
652 
stpmic1_is_regulator_enabled(const char * name)653 bool stpmic1_is_regulator_enabled(const char *name)
654 {
655 	const struct regul_struct *regul = get_regulator_data(name);
656 	uint8_t val = 0;
657 
658 	if (stpmic1_register_read(regul->control_reg, &val))
659 		panic();
660 
661 	return val & BIT(regul->enable_pos);
662 }
663 
664 /* Voltage can be set for buck<N> or ldo<N> (except ldo4) regulators */
find_plat_mask(const char * name)665 static uint8_t find_plat_mask(const char *name)
666 {
667 	if (!strncmp(name, "buck", 4))
668 		return BUCK_VOLTAGE_MASK;
669 
670 	if (!strncmp(name, "ldo", 3) && strcmp(name, "ldo4"))
671 		return LDO_VOLTAGE_MASK;
672 
673 	return 0;
674 }
675 
stpmic1_regulator_voltage_set(const char * name,uint16_t millivolts)676 int stpmic1_regulator_voltage_set(const char *name, uint16_t millivolts)
677 {
678 	size_t voltage_index = voltage_to_index(name, millivolts);
679 	const struct regul_struct *regul = get_regulator_data(name);
680 	uint8_t mask = 0;
681 
682 	if (voltage_index == VOLTAGE_INDEX_INVALID)
683 		return -1;
684 
685 	mask = find_plat_mask(name);
686 	if (!mask)
687 		return 0;
688 
689 	return stpmic1_register_update(regul->control_reg,
690 				       voltage_index << LDO_BUCK_VOLTAGE_SHIFT,
691 				       mask);
692 }
693 
stpmic1_regulator_mask_reset_set(const char * name)694 int stpmic1_regulator_mask_reset_set(const char *name)
695 {
696 	const struct regul_struct *regul = get_regulator_data(name);
697 
698 	if (regul->control_reg == USB_CONTROL_REG) {
699 		DMSG("No reset for USB control");
700 		return -1;
701 	}
702 
703 	return stpmic1_register_update(regul->mask_reset_reg,
704 				       BIT(regul->mask_reset_pos),
705 				       LDO_BUCK_RESET_MASK <<
706 				       regul->mask_reset_pos);
707 }
708 
stpmic1_bo_enable_cfg(const char * name,struct stpmic1_bo_cfg * cfg)709 int stpmic1_bo_enable_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
710 {
711 	const struct regul_struct *regul = get_regulator_data(name);
712 
713 	cfg->ctrl_reg = regul->control_reg;
714 	cfg->enable_pos = regul->enable_pos;
715 
716 	return 0;
717 }
718 
stpmic1_bo_enable_unpg(struct stpmic1_bo_cfg * cfg)719 int stpmic1_bo_enable_unpg(struct stpmic1_bo_cfg *cfg)
720 {
721 	return stpmic1_register_update(cfg->ctrl_reg,
722 				       BIT(cfg->enable_pos),
723 				       BIT(cfg->enable_pos));
724 }
725 
726 /* Returns 1 if no configuration are expected applied at runtime, 0 otherwise */
stpmic1_bo_voltage_cfg(const char * name,uint16_t min_millivolt,struct stpmic1_bo_cfg * cfg)727 int stpmic1_bo_voltage_cfg(const char *name, uint16_t min_millivolt,
728 			   struct stpmic1_bo_cfg *cfg)
729 {
730 	size_t min_index = voltage_to_index(name, min_millivolt);
731 	const struct regul_struct *regul = get_regulator_data(name);
732 	uint8_t mask = 0;
733 
734 	if (min_index == VOLTAGE_INDEX_INVALID)
735 		panic();
736 
737 	mask = find_plat_mask(name);
738 	if (!mask)
739 		return 1;
740 
741 	cfg->ctrl_reg = regul->control_reg;
742 	cfg->min_value = min_index << LDO_BUCK_VOLTAGE_SHIFT;
743 	cfg->mask = mask;
744 
745 	return 0;
746 }
747 
stpmic1_bo_voltage_unpg(struct stpmic1_bo_cfg * cfg)748 int stpmic1_bo_voltage_unpg(struct stpmic1_bo_cfg *cfg)
749 {
750 	uint8_t value = 0;
751 
752 	assert(cfg->ctrl_reg);
753 
754 	if (stpmic1_register_read(cfg->ctrl_reg, &value))
755 		return -1;
756 
757 	if ((value & cfg->mask) >= cfg->min_value)
758 		return 0;
759 
760 	return stpmic1_register_update(cfg->ctrl_reg, cfg->min_value,
761 				       cfg->mask);
762 }
763 
stpmic1_bo_pull_down_cfg(const char * name,struct stpmic1_bo_cfg * cfg)764 int stpmic1_bo_pull_down_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
765 {
766 	const struct regul_struct *regul = get_regulator_data(name);
767 
768 	if (!regul->pull_down_reg) {
769 		DMSG("No pull down for regu %s", name);
770 		panic();
771 	}
772 
773 	cfg->pd_reg = regul->pull_down_reg;
774 	cfg->pd_value = BIT(regul->pull_down_pos);
775 	cfg->pd_mask = LDO_BUCK_PULL_DOWN_MASK << regul->pull_down_pos;
776 
777 	return 0;
778 }
779 
stpmic1_bo_pull_down_unpg(struct stpmic1_bo_cfg * cfg)780 int stpmic1_bo_pull_down_unpg(struct stpmic1_bo_cfg *cfg)
781 {
782 	assert(cfg->pd_reg);
783 
784 	return stpmic1_register_update(cfg->pd_reg, cfg->pd_value,
785 				       cfg->pd_mask);
786 }
787 
stpmic1_bo_mask_reset_cfg(const char * name,struct stpmic1_bo_cfg * cfg)788 int stpmic1_bo_mask_reset_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
789 {
790 	const struct regul_struct *regul = get_regulator_data(name);
791 
792 	if (!regul->mask_reset_reg) {
793 		DMSG("No reset mask for regu %s", name);
794 		panic();
795 	}
796 
797 	cfg->mrst_reg = regul->mask_reset_reg;
798 	cfg->mrst_value = BIT(regul->mask_reset_pos);
799 	cfg->mrst_mask = LDO_BUCK_RESET_MASK << regul->mask_reset_pos;
800 
801 	return 0;
802 }
803 
stpmic1_bo_mask_reset_unpg(struct stpmic1_bo_cfg * cfg)804 int stpmic1_bo_mask_reset_unpg(struct stpmic1_bo_cfg *cfg)
805 {
806 	assert(cfg->mrst_reg);
807 
808 	return stpmic1_register_update(cfg->mrst_reg, cfg->mrst_value,
809 				       cfg->mrst_mask);
810 }
811 
stpmic1_regulator_voltage_get(const char * name)812 int stpmic1_regulator_voltage_get(const char *name)
813 {
814 	const struct regul_struct *regul = get_regulator_data(name);
815 	uint8_t value = 0;
816 	uint8_t mask = 0;
817 
818 	mask = find_plat_mask(name);
819 	if (!mask)
820 		return 0;
821 
822 	if (stpmic1_register_read(regul->control_reg, &value))
823 		return -1;
824 
825 	value = (value & mask) >> LDO_BUCK_VOLTAGE_SHIFT;
826 
827 	if (value > regul->voltage_table_size)
828 		return -1;
829 
830 	return regul->voltage_table[value];
831 }
832 
stpmic1_lp_copy_reg(const char * name)833 int stpmic1_lp_copy_reg(const char *name)
834 {
835 	const struct regul_struct *regul = get_regulator_data(name);
836 	uint8_t val = 0;
837 	int status = 0;
838 
839 	if (!regul->low_power_reg)
840 		return -1;
841 
842 	status = stpmic1_register_read(regul->control_reg, &val);
843 	if (status)
844 		return status;
845 
846 	return stpmic1_register_write(regul->low_power_reg, val);
847 }
848 
stpmic1_regu_has_lp_cfg(const char * name)849 bool stpmic1_regu_has_lp_cfg(const char *name)
850 {
851 	return get_regulator_data(name)->low_power_reg;
852 }
853 
stpmic1_lp_cfg(const char * name,struct stpmic1_lp_cfg * cfg)854 int stpmic1_lp_cfg(const char *name, struct stpmic1_lp_cfg *cfg)
855 {
856 	const struct regul_struct *regul = get_regulator_data(name);
857 
858 	if (!regul->low_power_reg)
859 		return -1;
860 
861 	cfg->ctrl_reg = regul->control_reg;
862 	cfg->lp_reg = regul->low_power_reg;
863 
864 	return 0;
865 }
866 
stpmic1_lp_load_unpg(struct stpmic1_lp_cfg * cfg)867 int stpmic1_lp_load_unpg(struct stpmic1_lp_cfg *cfg)
868 {
869 	uint8_t val = 0;
870 	int status = 0;
871 
872 	assert(cfg->lp_reg);
873 
874 	status = stpmic1_register_read(cfg->ctrl_reg, &val);
875 	if (!status)
876 		status = stpmic1_register_write(cfg->lp_reg, val);
877 
878 	return status;
879 }
880 
stpmic1_lp_reg_on_off(const char * name,uint8_t enable)881 int stpmic1_lp_reg_on_off(const char *name, uint8_t enable)
882 {
883 	const struct regul_struct *regul = get_regulator_data(name);
884 
885 	if (!regul->low_power_reg)
886 		return -1;
887 
888 	return stpmic1_register_update(regul->low_power_reg, enable,
889 				       LDO_BUCK_ENABLE_MASK);
890 }
891 
stpmic1_lp_on_off_unpg(struct stpmic1_lp_cfg * cfg,int enable)892 int stpmic1_lp_on_off_unpg(struct stpmic1_lp_cfg *cfg, int enable)
893 {
894 	assert(cfg->lp_reg && (enable == 0 || enable == 1));
895 
896 	return stpmic1_register_update(cfg->lp_reg, enable,
897 				       LDO_BUCK_ENABLE_MASK);
898 }
899 
stpmic1_lp_set_mode(const char * name,uint8_t hplp)900 int stpmic1_lp_set_mode(const char *name, uint8_t hplp)
901 {
902 	const struct regul_struct *regul = get_regulator_data(name);
903 
904 	assert(regul->low_power_reg && (hplp == 0 || hplp == 1));
905 
906 	return stpmic1_register_update(regul->low_power_reg,
907 				       hplp << LDO_BUCK_HPLP_POS,
908 				       BIT(LDO_BUCK_HPLP_POS));
909 }
910 
stpmic1_lp_mode_unpg(struct stpmic1_lp_cfg * cfg,unsigned int mode)911 int stpmic1_lp_mode_unpg(struct stpmic1_lp_cfg *cfg, unsigned int mode)
912 {
913 	assert(cfg->lp_reg && (mode == 0 || mode == 1));
914 	return stpmic1_register_update(cfg->lp_reg,
915 				       mode << LDO_BUCK_HPLP_POS,
916 				       BIT(LDO_BUCK_HPLP_POS));
917 }
918 
stpmic1_lp_set_voltage(const char * name,uint16_t millivolts)919 int stpmic1_lp_set_voltage(const char *name, uint16_t millivolts)
920 {
921 	size_t voltage_index = voltage_to_index(name, millivolts);
922 	const struct regul_struct *regul = get_regulator_data(name);
923 	uint8_t mask = 0;
924 
925 	assert(voltage_index != VOLTAGE_INDEX_INVALID);
926 
927 	mask = find_plat_mask(name);
928 	if (!mask)
929 		return 0;
930 
931 	return stpmic1_register_update(regul->low_power_reg, voltage_index << 2,
932 				       mask);
933 }
934 
935 /* Returns 1 if no configuration are expected applied at runtime, 0 otherwise */
stpmic1_lp_voltage_cfg(const char * name,uint16_t millivolts,struct stpmic1_lp_cfg * cfg)936 int stpmic1_lp_voltage_cfg(const char *name, uint16_t millivolts,
937 			   struct stpmic1_lp_cfg *cfg)
938 
939 {
940 	size_t voltage_index = voltage_to_index(name, millivolts);
941 	uint8_t mask = 0;
942 
943 	mask = find_plat_mask(name);
944 	if (!mask)
945 		return 1;
946 
947 	assert(voltage_index != VOLTAGE_INDEX_INVALID &&
948 	       cfg->lp_reg == get_regulator_data(name)->low_power_reg);
949 
950 	cfg->value = voltage_index << 2;
951 	cfg->mask = mask;
952 
953 	return 0;
954 }
955 
stpmic1_lp_voltage_unpg(struct stpmic1_lp_cfg * cfg)956 int stpmic1_lp_voltage_unpg(struct stpmic1_lp_cfg *cfg)
957 {
958 	assert(cfg->lp_reg);
959 
960 	return stpmic1_register_update(cfg->lp_reg, cfg->value,	cfg->mask);
961 }
962 
stpmic1_register_read(uint8_t register_id,uint8_t * value)963 int stpmic1_register_read(uint8_t register_id,  uint8_t *value)
964 {
965 	struct i2c_handle_s *i2c = pmic_i2c_handle;
966 
967 	return stm32_i2c_read_write_membyte(i2c, pmic_i2c_addr,
968 					    register_id, value,
969 					    false /* !write */);
970 }
971 
stpmic1_register_write(uint8_t register_id,uint8_t value)972 int stpmic1_register_write(uint8_t register_id, uint8_t value)
973 {
974 	struct i2c_handle_s *i2c = pmic_i2c_handle;
975 	uint8_t val = value;
976 
977 	return stm32_i2c_read_write_membyte(i2c, pmic_i2c_addr,
978 					    register_id, &val,
979 					    true /* write */);
980 }
981 
stpmic1_register_update(uint8_t register_id,uint8_t value,uint8_t mask)982 int stpmic1_register_update(uint8_t register_id, uint8_t value, uint8_t mask)
983 {
984 	int status = 0;
985 	uint8_t val = 0;
986 
987 	status = stpmic1_register_read(register_id, &val);
988 	if (status)
989 		return status;
990 
991 	val = (val & ~mask) | (value & mask);
992 
993 	return stpmic1_register_write(register_id, val);
994 }
995 
stpmic1_bind_i2c(struct i2c_handle_s * i2c_handle,uint16_t i2c_addr)996 void stpmic1_bind_i2c(struct i2c_handle_s *i2c_handle, uint16_t i2c_addr)
997 {
998 	pmic_i2c_handle = i2c_handle;
999 	pmic_i2c_addr = i2c_addr;
1000 }
1001 
stpmic1_dump_regulators(void)1002 void stpmic1_dump_regulators(void)
1003 {
1004 	size_t i = 0;
1005 	char __maybe_unused const *name = NULL;
1006 
1007 	for (i = 0; i < ARRAY_SIZE(regulators_table); i++) {
1008 		if (!regulators_table[i].control_reg)
1009 			continue;
1010 
1011 		name = regulators_table[i].dt_node_name;
1012 		DMSG("PMIC regul %s: %sable, %dmV",
1013 		     name, stpmic1_is_regulator_enabled(name) ? "en" : "dis",
1014 		     stpmic1_regulator_voltage_get(name));
1015 	}
1016 }
1017 
stpmic1_get_version(unsigned long * version)1018 int stpmic1_get_version(unsigned long *version)
1019 {
1020 	uint8_t read_val = 0;
1021 
1022 	if (stpmic1_register_read(VERSION_STATUS_REG, &read_val))
1023 		return -1;
1024 
1025 	*version = read_val;
1026 	return 0;
1027 }
1028