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