1*868b2d60SZhigang Qin /*
2*868b2d60SZhigang Qin * Copyright (c) 2025, Mediatek Inc. All rights reserved.
3*868b2d60SZhigang Qin * SPDX-License-Identifier: BSD-3-Clause
4*868b2d60SZhigang Qin */
5*868b2d60SZhigang Qin
6*868b2d60SZhigang Qin #include <errno.h>
7*868b2d60SZhigang Qin
8*868b2d60SZhigang Qin #include <common/debug.h>
9*868b2d60SZhigang Qin
10*868b2d60SZhigang Qin #include <drivers/pmic/mt6319_lowpower_reg.h>
11*868b2d60SZhigang Qin #include <drivers/pmic/mt6359p_set_lowpower.h>
12*868b2d60SZhigang Qin #include <drivers/pmic/pmic_swap_api.h>
13*868b2d60SZhigang Qin #include <lib/mtk_init/mtk_init.h>
14*868b2d60SZhigang Qin #include <pmic_wrap_init_common.h>
15*868b2d60SZhigang Qin
16*868b2d60SZhigang Qin #define PMIC_SLVID_BUCK_SET_LP(_chip, _slvid, _name, _user, _en, _mode, _cfg) \
17*868b2d60SZhigang Qin { \
18*868b2d60SZhigang Qin struct spmi_device *sdev = lowpower_sdev[_slvid]; \
19*868b2d60SZhigang Qin if (sdev) {\
20*868b2d60SZhigang Qin pmic_spmi_update_bits(sdev, \
21*868b2d60SZhigang Qin _chip##_RG_BUCK_##_name##_##_user##_OP_CFG_ADDR, \
22*868b2d60SZhigang Qin 1 << _user, \
23*868b2d60SZhigang Qin _cfg ? 1 << _user : 0); \
24*868b2d60SZhigang Qin pmic_spmi_update_bits(sdev, \
25*868b2d60SZhigang Qin _chip##_RG_BUCK_##_name##_##_user##_OP_MODE_ADDR, \
26*868b2d60SZhigang Qin 1 << _user, \
27*868b2d60SZhigang Qin _mode ? 1 << _user : 0); \
28*868b2d60SZhigang Qin pmic_spmi_update_bits(sdev, \
29*868b2d60SZhigang Qin _chip##_RG_BUCK_##_name##_##_user##_OP_EN_ADDR, \
30*868b2d60SZhigang Qin 1 << _user, \
31*868b2d60SZhigang Qin _en ? 1 << _user : 0); \
32*868b2d60SZhigang Qin } \
33*868b2d60SZhigang Qin }
34*868b2d60SZhigang Qin
35*868b2d60SZhigang Qin struct spmi_device *lowpower_sdev[SPMI_MAX_SLAVE_ID];
36*868b2d60SZhigang Qin
37*868b2d60SZhigang Qin static const uint8_t lowpower_slvid_arr[] = {
38*868b2d60SZhigang Qin SPMI_SLAVE_7,
39*868b2d60SZhigang Qin };
40*868b2d60SZhigang Qin
pmic_spmi_update_bits(struct spmi_device * sdev,uint16_t reg,uint8_t mask,uint8_t val)41*868b2d60SZhigang Qin static int pmic_spmi_update_bits(struct spmi_device *sdev, uint16_t reg,
42*868b2d60SZhigang Qin uint8_t mask, uint8_t val)
43*868b2d60SZhigang Qin {
44*868b2d60SZhigang Qin uint8_t orig = 0;
45*868b2d60SZhigang Qin int ret = 0;
46*868b2d60SZhigang Qin
47*868b2d60SZhigang Qin ret = spmi_ext_register_readl(sdev, reg, &orig, 1);
48*868b2d60SZhigang Qin if (ret < 0)
49*868b2d60SZhigang Qin return ret;
50*868b2d60SZhigang Qin orig &= ~mask;
51*868b2d60SZhigang Qin orig |= val & mask;
52*868b2d60SZhigang Qin ret = spmi_ext_register_writel(sdev, reg, &orig, 1);
53*868b2d60SZhigang Qin return ret;
54*868b2d60SZhigang Qin }
55*868b2d60SZhigang Qin
pmic_lowpower_init(void)56*868b2d60SZhigang Qin static int pmic_lowpower_init(void)
57*868b2d60SZhigang Qin {
58*868b2d60SZhigang Qin uint8_t i, slvid;
59*868b2d60SZhigang Qin
60*868b2d60SZhigang Qin for (i = 0; i < ARRAY_SIZE(lowpower_slvid_arr); i++) {
61*868b2d60SZhigang Qin slvid = lowpower_slvid_arr[i];
62*868b2d60SZhigang Qin lowpower_sdev[slvid] = get_spmi_device(SPMI_MASTER_P_1, slvid);
63*868b2d60SZhigang Qin if (!lowpower_sdev[slvid])
64*868b2d60SZhigang Qin return -ENODEV;
65*868b2d60SZhigang Qin }
66*868b2d60SZhigang Qin
67*868b2d60SZhigang Qin PMIC_SLVID_BUCK_SET_LP(MT6319, SPMI_SLAVE_7, VBUCK3, HW0, true, OP_MODE_LP, HW_LP);
68*868b2d60SZhigang Qin
69*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VPROC2, HW0, true, OP_MODE_LP, HW_OFF);
70*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VPROC2, HW2, true, OP_MODE_LP, HW_LP);
71*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VGPU11, HW0, true, OP_MODE_LP, HW_LP);
72*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VGPU11, HW2, true, OP_MODE_LP, HW_LP);
73*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VS1, HW0, true, OP_MODE_LP, HW_LP);
74*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VS1, HW2, true, OP_MODE_LP, HW_LP);
75*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VS2, HW0, true, OP_MODE_LP, HW_LP);
76*868b2d60SZhigang Qin PMIC_BUCK_SET_LP(MT6359P, VS2, HW2, true, OP_MODE_LP, HW_LP);
77*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VRF12, HW0, true, OP_MODE_LP, HW_LP);
78*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VRF12, HW2, true, OP_MODE_LP, HW_LP);
79*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VA12, HW0, true, OP_MODE_LP, HW_LP);
80*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VA12, HW2, true, OP_MODE_LP, HW_LP);
81*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VA09, HW0, true, OP_MODE_LP, HW_LP);
82*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VA09, HW2, true, OP_MODE_LP, HW_LP);
83*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VAUX18, HW0, true, OP_MODE_LP, HW_LP);
84*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VAUX18, HW2, true, OP_MODE_LP, HW_LP);
85*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VXO22, HW0, true, OP_MODE_LP, HW_LP);
86*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VXO22, HW2, true, OP_MODE_LP, HW_LP);
87*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VUSB, HW0, true, OP_MODE_LP, HW_LP);
88*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VUSB, HW2, true, OP_MODE_LP, HW_LP);
89*868b2d60SZhigang Qin PMIC_LDO_SET_LP(MT6359P, VUFS, HW0, true, OP_MODE_LP, HW_LP);
90*868b2d60SZhigang Qin
91*868b2d60SZhigang Qin return 0;
92*868b2d60SZhigang Qin }
93*868b2d60SZhigang Qin
94*868b2d60SZhigang Qin MTK_PLAT_SETUP_0_INIT(pmic_lowpower_init);
95