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 	if (levels)
603 		*levels = regul->voltage_table;
604 }
605 
voltage_to_index(const char * name,uint16_t millivolts)606 static size_t voltage_to_index(const char *name, uint16_t millivolts)
607 {
608 	const struct regul_struct *regul = get_regulator_data(name);
609 	unsigned int i = 0;
610 
611 	assert(regul->voltage_table);
612 	for (i = 0; i < regul->voltage_table_size; i++)
613 		if (regul->voltage_table[i] == millivolts)
614 			return i;
615 
616 	return VOLTAGE_INDEX_INVALID;
617 }
618 
stpmic1_powerctrl_on(void)619 int stpmic1_powerctrl_on(void)
620 {
621 	return stpmic1_register_update(MAIN_CONTROL_REG, PWRCTRL_PIN_VALID,
622 				       PWRCTRL_PIN_VALID);
623 }
624 
stpmic1_switch_off(void)625 int stpmic1_switch_off(void)
626 {
627 	return stpmic1_register_update(MAIN_CONTROL_REG, 1,
628 				       SOFTWARE_SWITCH_OFF_ENABLED);
629 }
630 
stpmic1_regulator_enable(const char * name)631 int stpmic1_regulator_enable(const char *name)
632 {
633 	const struct regul_struct *regul = get_regulator_data(name);
634 
635 	return stpmic1_register_update(regul->control_reg,
636 				       BIT(regul->enable_pos),
637 				       BIT(regul->enable_pos));
638 }
639 
stpmic1_regulator_disable(const char * name)640 int stpmic1_regulator_disable(const char *name)
641 {
642 	const struct regul_struct *regul = get_regulator_data(name);
643 
644 	return stpmic1_register_update(regul->control_reg, 0,
645 				       BIT(regul->enable_pos));
646 }
647 
stpmic1_is_regulator_enabled(const char * name)648 bool stpmic1_is_regulator_enabled(const char *name)
649 {
650 	const struct regul_struct *regul = get_regulator_data(name);
651 	uint8_t val = 0;
652 
653 	if (stpmic1_register_read(regul->control_reg, &val))
654 		panic();
655 
656 	return val & BIT(regul->enable_pos);
657 }
658 
659 /* Voltage can be set for buck<N> or ldo<N> (except ldo4) regulators */
find_plat_mask(const char * name)660 static uint8_t find_plat_mask(const char *name)
661 {
662 	if (!strncmp(name, "buck", 4))
663 		return BUCK_VOLTAGE_MASK;
664 
665 	if (!strncmp(name, "ldo", 3) && strcmp(name, "ldo4"))
666 		return LDO_VOLTAGE_MASK;
667 
668 	return 0;
669 }
670 
stpmic1_regulator_voltage_set(const char * name,uint16_t millivolts)671 int stpmic1_regulator_voltage_set(const char *name, uint16_t millivolts)
672 {
673 	size_t voltage_index = voltage_to_index(name, millivolts);
674 	const struct regul_struct *regul = get_regulator_data(name);
675 	uint8_t mask = 0;
676 
677 	if (voltage_index == VOLTAGE_INDEX_INVALID)
678 		return -1;
679 
680 	mask = find_plat_mask(name);
681 	if (!mask)
682 		return 0;
683 
684 	return stpmic1_register_update(regul->control_reg,
685 				       voltage_index << LDO_BUCK_VOLTAGE_SHIFT,
686 				       mask);
687 }
688 
stpmic1_regulator_mask_reset_set(const char * name)689 int stpmic1_regulator_mask_reset_set(const char *name)
690 {
691 	const struct regul_struct *regul = get_regulator_data(name);
692 
693 	if (regul->control_reg == USB_CONTROL_REG) {
694 		DMSG("No reset for USB control");
695 		return -1;
696 	}
697 
698 	return stpmic1_register_update(regul->mask_reset_reg,
699 				       BIT(regul->mask_reset_pos),
700 				       LDO_BUCK_RESET_MASK <<
701 				       regul->mask_reset_pos);
702 }
703 
stpmic1_bo_enable_cfg(const char * name,struct stpmic1_bo_cfg * cfg)704 int stpmic1_bo_enable_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
705 {
706 	const struct regul_struct *regul = get_regulator_data(name);
707 
708 	cfg->ctrl_reg = regul->control_reg;
709 	cfg->enable_pos = regul->enable_pos;
710 
711 	return 0;
712 }
713 
stpmic1_bo_enable_unpg(struct stpmic1_bo_cfg * cfg)714 int stpmic1_bo_enable_unpg(struct stpmic1_bo_cfg *cfg)
715 {
716 	return stpmic1_register_update(cfg->ctrl_reg,
717 				       BIT(cfg->enable_pos),
718 				       BIT(cfg->enable_pos));
719 }
720 
721 /* 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)722 int stpmic1_bo_voltage_cfg(const char *name, uint16_t min_millivolt,
723 			   struct stpmic1_bo_cfg *cfg)
724 {
725 	size_t min_index = voltage_to_index(name, min_millivolt);
726 	const struct regul_struct *regul = get_regulator_data(name);
727 	uint8_t mask = 0;
728 
729 	if (min_index == VOLTAGE_INDEX_INVALID)
730 		panic();
731 
732 	mask = find_plat_mask(name);
733 	if (!mask)
734 		return 1;
735 
736 	cfg->ctrl_reg = regul->control_reg;
737 	cfg->min_value = min_index << LDO_BUCK_VOLTAGE_SHIFT;
738 	cfg->mask = mask;
739 
740 	return 0;
741 }
742 
stpmic1_bo_voltage_unpg(struct stpmic1_bo_cfg * cfg)743 int stpmic1_bo_voltage_unpg(struct stpmic1_bo_cfg *cfg)
744 {
745 	uint8_t value = 0;
746 
747 	assert(cfg->ctrl_reg);
748 
749 	if (stpmic1_register_read(cfg->ctrl_reg, &value))
750 		return -1;
751 
752 	if ((value & cfg->mask) >= cfg->min_value)
753 		return 0;
754 
755 	return stpmic1_register_update(cfg->ctrl_reg, cfg->min_value,
756 				       cfg->mask);
757 }
758 
stpmic1_bo_pull_down_cfg(const char * name,struct stpmic1_bo_cfg * cfg)759 int stpmic1_bo_pull_down_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
760 {
761 	const struct regul_struct *regul = get_regulator_data(name);
762 
763 	if (!regul->pull_down_reg) {
764 		DMSG("No pull down for regu %s", name);
765 		panic();
766 	}
767 
768 	cfg->pd_reg = regul->pull_down_reg;
769 	cfg->pd_value = BIT(regul->pull_down_pos);
770 	cfg->pd_mask = LDO_BUCK_PULL_DOWN_MASK << regul->pull_down_pos;
771 
772 	return 0;
773 }
774 
stpmic1_bo_pull_down_unpg(struct stpmic1_bo_cfg * cfg)775 int stpmic1_bo_pull_down_unpg(struct stpmic1_bo_cfg *cfg)
776 {
777 	assert(cfg->pd_reg);
778 
779 	return stpmic1_register_update(cfg->pd_reg, cfg->pd_value,
780 				       cfg->pd_mask);
781 }
782 
stpmic1_bo_mask_reset_cfg(const char * name,struct stpmic1_bo_cfg * cfg)783 int stpmic1_bo_mask_reset_cfg(const char *name, struct stpmic1_bo_cfg *cfg)
784 {
785 	const struct regul_struct *regul = get_regulator_data(name);
786 
787 	if (!regul->mask_reset_reg) {
788 		DMSG("No reset mask for regu %s", name);
789 		panic();
790 	}
791 
792 	cfg->mrst_reg = regul->mask_reset_reg;
793 	cfg->mrst_value = BIT(regul->mask_reset_pos);
794 	cfg->mrst_mask = LDO_BUCK_RESET_MASK << regul->mask_reset_pos;
795 
796 	return 0;
797 }
798 
stpmic1_bo_mask_reset_unpg(struct stpmic1_bo_cfg * cfg)799 int stpmic1_bo_mask_reset_unpg(struct stpmic1_bo_cfg *cfg)
800 {
801 	assert(cfg->mrst_reg);
802 
803 	return stpmic1_register_update(cfg->mrst_reg, cfg->mrst_value,
804 				       cfg->mrst_mask);
805 }
806 
stpmic1_regulator_voltage_get(const char * name)807 int stpmic1_regulator_voltage_get(const char *name)
808 {
809 	const struct regul_struct *regul = get_regulator_data(name);
810 	uint8_t value = 0;
811 	uint8_t mask = 0;
812 
813 	mask = find_plat_mask(name);
814 	if (!mask)
815 		return 0;
816 
817 	if (stpmic1_register_read(regul->control_reg, &value))
818 		return -1;
819 
820 	value = (value & mask) >> LDO_BUCK_VOLTAGE_SHIFT;
821 
822 	if (value > regul->voltage_table_size)
823 		return -1;
824 
825 	return regul->voltage_table[value];
826 }
827 
stpmic1_lp_copy_reg(const char * name)828 int stpmic1_lp_copy_reg(const char *name)
829 {
830 	const struct regul_struct *regul = get_regulator_data(name);
831 	uint8_t val = 0;
832 	int status = 0;
833 
834 	if (!regul->low_power_reg)
835 		return -1;
836 
837 	status = stpmic1_register_read(regul->control_reg, &val);
838 	if (status)
839 		return status;
840 
841 	return stpmic1_register_write(regul->low_power_reg, val);
842 }
843 
stpmic1_regu_has_lp_cfg(const char * name)844 bool stpmic1_regu_has_lp_cfg(const char *name)
845 {
846 	return get_regulator_data(name)->low_power_reg;
847 }
848 
stpmic1_lp_cfg(const char * name,struct stpmic1_lp_cfg * cfg)849 int stpmic1_lp_cfg(const char *name, struct stpmic1_lp_cfg *cfg)
850 {
851 	const struct regul_struct *regul = get_regulator_data(name);
852 
853 	if (!regul->low_power_reg)
854 		return -1;
855 
856 	cfg->ctrl_reg = regul->control_reg;
857 	cfg->lp_reg = regul->low_power_reg;
858 
859 	return 0;
860 }
861 
stpmic1_lp_load_unpg(struct stpmic1_lp_cfg * cfg)862 int stpmic1_lp_load_unpg(struct stpmic1_lp_cfg *cfg)
863 {
864 	uint8_t val = 0;
865 	int status = 0;
866 
867 	assert(cfg->lp_reg);
868 
869 	status = stpmic1_register_read(cfg->ctrl_reg, &val);
870 	if (!status)
871 		status = stpmic1_register_write(cfg->lp_reg, val);
872 
873 	return status;
874 }
875 
stpmic1_lp_reg_on_off(const char * name,uint8_t enable)876 int stpmic1_lp_reg_on_off(const char *name, uint8_t enable)
877 {
878 	const struct regul_struct *regul = get_regulator_data(name);
879 
880 	if (!regul->low_power_reg)
881 		return -1;
882 
883 	return stpmic1_register_update(regul->low_power_reg, enable,
884 				       LDO_BUCK_ENABLE_MASK);
885 }
886 
stpmic1_lp_on_off_unpg(struct stpmic1_lp_cfg * cfg,int enable)887 int stpmic1_lp_on_off_unpg(struct stpmic1_lp_cfg *cfg, int enable)
888 {
889 	assert(cfg->lp_reg && (enable == 0 || enable == 1));
890 
891 	return stpmic1_register_update(cfg->lp_reg, enable,
892 				       LDO_BUCK_ENABLE_MASK);
893 }
894 
stpmic1_lp_set_mode(const char * name,uint8_t hplp)895 int stpmic1_lp_set_mode(const char *name, uint8_t hplp)
896 {
897 	const struct regul_struct *regul = get_regulator_data(name);
898 
899 	assert(regul->low_power_reg && (hplp == 0 || hplp == 1));
900 
901 	return stpmic1_register_update(regul->low_power_reg,
902 				       hplp << LDO_BUCK_HPLP_POS,
903 				       BIT(LDO_BUCK_HPLP_POS));
904 }
905 
stpmic1_lp_mode_unpg(struct stpmic1_lp_cfg * cfg,unsigned int mode)906 int stpmic1_lp_mode_unpg(struct stpmic1_lp_cfg *cfg, unsigned int mode)
907 {
908 	assert(cfg->lp_reg && (mode == 0 || mode == 1));
909 	return stpmic1_register_update(cfg->lp_reg,
910 				       mode << LDO_BUCK_HPLP_POS,
911 				       BIT(LDO_BUCK_HPLP_POS));
912 }
913 
stpmic1_lp_set_voltage(const char * name,uint16_t millivolts)914 int stpmic1_lp_set_voltage(const char *name, uint16_t millivolts)
915 {
916 	size_t voltage_index = voltage_to_index(name, millivolts);
917 	const struct regul_struct *regul = get_regulator_data(name);
918 	uint8_t mask = 0;
919 
920 	assert(voltage_index != VOLTAGE_INDEX_INVALID);
921 
922 	mask = find_plat_mask(name);
923 	if (!mask)
924 		return 0;
925 
926 	return stpmic1_register_update(regul->low_power_reg, voltage_index << 2,
927 				       mask);
928 }
929 
930 /* 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)931 int stpmic1_lp_voltage_cfg(const char *name, uint16_t millivolts,
932 			   struct stpmic1_lp_cfg *cfg)
933 
934 {
935 	size_t voltage_index = voltage_to_index(name, millivolts);
936 	uint8_t mask = 0;
937 
938 	mask = find_plat_mask(name);
939 	if (!mask)
940 		return 1;
941 
942 	assert(voltage_index != VOLTAGE_INDEX_INVALID &&
943 	       cfg->lp_reg == get_regulator_data(name)->low_power_reg);
944 
945 	cfg->value = voltage_index << 2;
946 	cfg->mask = mask;
947 
948 	return 0;
949 }
950 
stpmic1_lp_voltage_unpg(struct stpmic1_lp_cfg * cfg)951 int stpmic1_lp_voltage_unpg(struct stpmic1_lp_cfg *cfg)
952 {
953 	assert(cfg->lp_reg);
954 
955 	return stpmic1_register_update(cfg->lp_reg, cfg->value,	cfg->mask);
956 }
957 
stpmic1_register_read(uint8_t register_id,uint8_t * value)958 int stpmic1_register_read(uint8_t register_id,  uint8_t *value)
959 {
960 	struct i2c_handle_s *i2c = pmic_i2c_handle;
961 
962 	return stm32_i2c_read_write_membyte(i2c, pmic_i2c_addr,
963 					    register_id, value,
964 					    false /* !write */);
965 }
966 
stpmic1_register_write(uint8_t register_id,uint8_t value)967 int stpmic1_register_write(uint8_t register_id, uint8_t value)
968 {
969 	struct i2c_handle_s *i2c = pmic_i2c_handle;
970 	uint8_t val = value;
971 
972 	return stm32_i2c_read_write_membyte(i2c, pmic_i2c_addr,
973 					    register_id, &val,
974 					    true /* write */);
975 }
976 
stpmic1_register_update(uint8_t register_id,uint8_t value,uint8_t mask)977 int stpmic1_register_update(uint8_t register_id, uint8_t value, uint8_t mask)
978 {
979 	int status = 0;
980 	uint8_t val = 0;
981 
982 	status = stpmic1_register_read(register_id, &val);
983 	if (status)
984 		return status;
985 
986 	val = (val & ~mask) | (value & mask);
987 
988 	return stpmic1_register_write(register_id, val);
989 }
990 
stpmic1_bind_i2c(struct i2c_handle_s * i2c_handle,uint16_t i2c_addr)991 void stpmic1_bind_i2c(struct i2c_handle_s *i2c_handle, uint16_t i2c_addr)
992 {
993 	pmic_i2c_handle = i2c_handle;
994 	pmic_i2c_addr = i2c_addr;
995 }
996 
stpmic1_dump_regulators(void)997 void stpmic1_dump_regulators(void)
998 {
999 	size_t i = 0;
1000 	char __maybe_unused const *name = NULL;
1001 
1002 	for (i = 0; i < ARRAY_SIZE(regulators_table); i++) {
1003 		if (!regulators_table[i].control_reg)
1004 			continue;
1005 
1006 		name = regulators_table[i].dt_node_name;
1007 		DMSG("PMIC regul %s: %sable, %dmV",
1008 		     name, stpmic1_is_regulator_enabled(name) ? "en" : "dis",
1009 		     stpmic1_regulator_voltage_get(name));
1010 	}
1011 }
1012 
stpmic1_get_version(unsigned long * version)1013 int stpmic1_get_version(unsigned long *version)
1014 {
1015 	uint8_t read_val = 0;
1016 
1017 	if (stpmic1_register_read(VERSION_STATUS_REG, &read_val))
1018 		return -1;
1019 
1020 	*version = read_val;
1021 	return 0;
1022 }
1023