1 /*
2  * Copyright 2021 ~ 2022 NXP
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  */
7 
8 #include "fsl_pf5020.h"
9 
10 /*******************************************************************************
11  * Definitions
12  ******************************************************************************/
13 #define PF5020_REGULATOR_PG_EN_MASK  (0x1U)
14 #define PF5020_REGULATOR_PG_EN_SHIFT (0U)
15 #define PF5020_REGULATOR_PG_EN(x) \
16     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_PG_EN_SHIFT)) & PF5020_REGULATOR_PG_EN_MASK)
17 
18 #define PF5020_REGULATOR_WDBYPASS_MASK  (0x2U)
19 #define PF5020_REGULATOR_WDBYPASS_SHIFT (1U)
20 #define PF5020_REGULATOR_WDBYPASS(x) \
21     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_WDBYPASS_SHIFT)) & PF5020_REGULATOR_WDBYPASS_MASK)
22 
23 #define PF5020_REGULATOR_ILIM_BYPASS_MASK  (0x20U)
24 #define PF5020_REGULATOR_ILIM_BYPASS_SHIFT (5U)
25 #define PF5020_REGULATOR_ILIM_BYPASS(x) \
26     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_ILIM_BYPASS_SHIFT)) & PF5020_REGULATOR_ILIM_BYPASS_MASK)
27 
28 #define PF5020_REGULATOR_OV_BYPASS_MASK  (0x40U)
29 #define PF5020_REGULATOR_OV_BYPASS_SHIFT (6U)
30 #define PF5020_REGULATOR_OV_BYPASS(x) \
31     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_OV_BYPASS_SHIFT)) & PF5020_REGULATOR_OV_BYPASS_MASK)
32 
33 #define PF5020_REGULATOR_UV_BYPASS_MASK  (0x80U)
34 #define PF5020_REGULATOR_UV_BYPASS_SHIFT (7U)
35 #define PF5020_REGULATOR_UV_BYPASS(x) \
36     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_UV_BYPASS_SHIFT)) & PF5020_REGULATOR_UV_BYPASS_MASK)
37 
38 #define PF5020_REGULATOR_FLT_REN_MASK  (0x80U)
39 #define PF5020_REGULATOR_FLT_REN_SHIFT (7U)
40 #define PF5020_REGULATOR_FLT_REN(x) \
41     (((uint8_t)(((uint8_t)(x)) << PF5020_REGULATOR_FLT_REN_SHIFT)) & PF5020_REGULATOR_FLT_REN_MASK)
42 
43 #define PF5020_BUCK_REGULATOR_RUN_MODE_MASK  (0x3U)
44 #define PF5020_BUCK_REGULATOR_RUN_MODE_SHIFT (0U)
45 #define PF5020_BUCK_REGULATOR_RUN_MODE(x) \
46     (((uint8_t)(((uint8_t)(x)) << PF5020_BUCK_REGULATOR_RUN_MODE_SHIFT)) & PF5020_BUCK_REGULATOR_RUN_MODE_MASK)
47 
48 #define PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK  (0xCU)
49 #define PF5020_BUCK_REGULATOR_STANDBY_MODE_SHIFT (2U)
50 #define PF5020_BUCK_REGULATOR_STANDBY_MODE(x) \
51     (((uint8_t)(((uint8_t)(x)) << PF5020_BUCK_REGULATOR_STANDBY_MODE_SHIFT)) & PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK)
52 
53 #define PF5020_BUCK_REGULATOR_ILIM_MASK  (0x18U)
54 #define PF5020_BUCK_REGULATOR_ILIM_SHIFT (3U)
55 #define PF5020_BUCK_REGULATOR_ILIM(x) \
56     (((uint8_t)(((uint8_t)(x)) << PF5020_BUCK_REGULATOR_ILIM_SHIFT)) & PF5020_BUCK_REGULATOR_ILIM_MASK)
57 
58 #define PF5020_BUCK_REGULATOR_PDGPR_MASK  (0x30U)
59 #define PF5020_BUCK_REGULATOR_PDGPR_SHIFT (4U)
60 #define PF5020_BUCK_REGULATOR_PDGPR(x) \
61     (((uint8_t)(((uint8_t)(x)) << PF5020_BUCK_REGULATOR_PDGPR_SHIFT)) & PF5020_BUCK_REGULATOR_PDGPR_MASK)
62 
63 #define PF5020_BUCK_REGULATOR_PHASE_MASK  (0x7U)
64 #define PF5020_BUCK_REGULATOR_PHASE_SHIFT (0U)
65 #define PF5020_BUCK_REGULATOR_PHASE(x) \
66     (((uint8_t)(((uint8_t)(x)) << PF5020_BUCK_REGULATOR_PHASE_SHIFT)) & PF5020_BUCK_REGULATOR_PHASE_MASK)
67 
68 #define PF5020_SW2_CONFIG2_VTTEN_MASK  (0x40U)
69 #define PF5020_SW2_CONFIG2_VTTEN_SHIFT (6U)
70 #define PF5020_SW2_CONFIG2_VTTEN(x) \
71     (((uint8_t)(((uint8_t)(x)) << PF5020_SW2_CONFIG2_VTTEN_SHIFT)) & PF5020_SW2_CONFIG2_VTTEN_MASK)
72 
73 #define PF5020_LDO1_CONFIG2_STBY_EN_MASK  (0x1U)
74 #define PF5020_LDO1_CONFIG2_STBY_EN_SHIFT (0U)
75 #define PF5020_LDO1_CONFIG2_STBY_EN(x) \
76     (((uint8_t)(((uint8_t)(x)) << PF5020_LDO1_CONFIG2_STBY_EN_SHIFT)) & PF5020_LDO1_CONFIG2_STBY_EN_MASK)
77 
78 #define PF5020_LDO1_CONFIG2_RUN_EN_MASK  (0x2U)
79 #define PF5020_LDO1_CONFIG2_RUN_EN_SHIFT (1U)
80 #define PF5020_LDO1_CONFIG2_RUN_EN(x) \
81     (((uint8_t)(((uint8_t)(x)) << PF5020_LDO1_CONFIG2_RUN_EN_SHIFT)) & PF5020_LDO1_CONFIG2_RUN_EN_MASK)
82 
83 #define PF5020_LDO1_CONFIG2_LDO1_PDGRP_MASK  (0x60U)
84 #define PF5020_LDO1_CONFIG2_LDO1_PDGRP_SHIFT (5U)
85 #define PF5020_LDO1_CONFIG2_LDO1_PDGRP(x) \
86     (((uint8_t)(((uint8_t)(x)) << PF5020_LDO1_CONFIG2_LDO1_PDGRP_SHIFT)) & PF5020_LDO1_CONFIG2_LDO1_PDGRP_MASK)
87 
88 #define PF5020_CTRL1_WD_STBY_EN_MASK  (0x4U)
89 #define PF5020_CTRL1_WD_STBY_EN_SHIFT (2U)
90 #define PF5020_CTRL1_WD_STBY_EN(x) \
91     (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL1_WD_STBY_EN_SHIFT)) & PF5020_CTRL1_WD_STBY_EN_MASK)
92 
93 #define PF5020_CTRL1_WD_EN_MASK  (0x8U)
94 #define PF5020_CTRL1_WD_EN_SHIFT (3U)
95 #define PF5020_CTRL1_WD_EN(x)    (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL1_WD_EN_SHIFT)) & PF5020_CTRL1_WD_EN_MASK)
96 
97 #define PF5020_CTRL1_TMP_MON_EN_MASK  (0x10U)
98 #define PF5020_CTRL1_TMP_MON_EN_SHIFT (4U)
99 #define PF5020_CTRL1_TMP_MON_EN(x) \
100     (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL1_TMP_MON_EN_SHIFT)) & PF5020_CTRL1_TMP_MON_EN_MASK)
101 
102 #define PF5020_CTRL2_TMP_MON_AON_MASK  (0x10U)
103 #define PF5020_CTRL2_TMP_MON_AON_SHIFT (4U)
104 #define PF5020_CTRL2_TMP_MON_AON(x) \
105     (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL2_TMP_MON_AON_SHIFT)) & PF5020_CTRL2_TMP_MON_AON_MASK)
106 
107 #define PF5020_CTRL3_PMIC_OFF_MASK  (0x2U)
108 #define PF5020_CTRL3_PMIC_OFF_SHIFT (1U)
109 #define PF5020_CTRL3_PMIC_OFF(x) \
110     (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL3_PMIC_OFF_SHIFT)) & PF5020_CTRL3_PMIC_OFF_MASK)
111 
112 #define PF5020_CTRL3_UV_DB_MASK  (0x30U)
113 #define PF5020_CTRL3_UV_DB_SHIFT (4U)
114 #define PF5020_CTRL3_UV_DB(x)    (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL3_UV_DB_SHIFT)) & PF5020_CTRL3_UV_DB_MASK)
115 
116 #define PF5020_CTRL3_OV_DB_MASK  (0xC0U)
117 #define PF5020_CTRL3_OV_DB_SHIFT (6U)
118 #define PF5020_CTRL3_OV_DB(x)    (((uint8_t)(((uint8_t)(x)) << PF5020_CTRL3_OV_DB_SHIFT)) & PF5020_CTRL3_OV_DB_MASK)
119 
120 #define PF5020_AMUX_AMUX_SEL_MASK  (0x1FU)
121 #define PF5020_AMUX_MAUX_SEL_SHIFT (0U)
122 #define PF5020_AMUX_MAUX_SEL(x)    (((uint8_t)(((uint8_t)(x)) << PF5020_AMUX_MAUX_SEL_SHIFT)) & PF5020_AMUX_AMUX_SEL_MASK)
123 
124 #define PF5020_AMUX_AMUX_EN_MASK  (0x20U)
125 #define PF5020_AMUX_AMUX_EN_SHIFT (5U)
126 #define PF5020_AMUX_AMUX_EN(x)    (((uint8_t)(((uint8_t)(x)) << PF5020_AMUX_AMUX_EN_SHIFT)) & PF5020_AMUX_AMUX_EN_MASK)
127 
128 #define PF5020_VMONEN1_SW1VMON_EN_MASK  (0x1U)
129 #define PF5020_VMONEN1_SW1VMON_EN_SHIFT (0U)
130 #define PF5020_VMONEN1_SW1VMON_EN(x) \
131     (((uint8_t)(((uint8_t)(x)) << PF5020_VMONEN1_SW1VMON_EN_SHIFT)) & PF5020_VMONEN1_SW1VMON_EN_MASK)
132 
133 #define PF5020_VMONEN1_SW2VMON_EN_MASK  (0x2U)
134 #define PF5020_VMONEN1_SW2VMON_EN_SHIFT (1U)
135 #define PF5020_VMONEN1_SW2VMON_EN(x) \
136     (((uint8_t)(((uint8_t)(x)) << PF5020_VMONEN1_SW2VMON_EN_SHIFT)) & PF5020_VMONEN1_SW2VMON_EN_MASK)
137 
138 #define PF5020_VMONEN1_SWND1VMON_EN_MASK  (0x40U)
139 #define PF5020_VMONEN1_SWND1VMON_EN_SHIFT (6U)
140 #define PF5020_VMONEN1_SWND1VMON_EN(x) \
141     (((uint8_t)(((uint8_t)(x)) << PF5020_VMONEN1_SWND1VMON_EN_SHIFT)) & PF5020_VMONEN1_SWND1VMON_EN_MASK)
142 
143 #define PF5020_VMONEN2_LDO1VMON_EN_MASK  (0x1U)
144 #define PF5020_VMONEN2_LDO1VMON_EN_SHIFT (0U)
145 #define PF5020_VMONEN2_LDO1VMON_EN(x) \
146     (((uint8_t)(((uint8_t)(x)) << PF5020_VMONEN2_LDO1VMON_EN_SHIFT)) & PF5020_VMONEN2_LDO1VMON_EN_MASK)
147 
148 #define PF5020_PWRUP_CTRL_RESETBMCU_PDGRP_MASK  (0xCU)
149 #define PF5020_PWRUP_CTRL_RESETBMCU_PDGRP_SHIFT (2U)
150 #define PF5020_PWRUP_CTRL_RESETBMCU_PDGRP(x) \
151     (((uint8_t)(((uint8_t)(x)) << PF5020_PWRUP_CTRL_RESETBMCU_PDGRP_SHIFT)) & PF5020_PWRUP_CTRL_RESETBMCU_PDGRP_MASK)
152 
153 #define PF5020_PWRUP_CTRL_PGOOD_PDGRP_MASK  (0x30U)
154 #define PF5020_PWRUP_CTRL_PGOOD_PDGRP_SHIFT (4U)
155 #define PF5020_PWRUP_CTRL_PGOOD_PDGRP(x) \
156     (((uint8_t)(((uint8_t)(x)) << PF5020_PWRUP_CTRL_PGOOD_PDGRP_SHIFT)) & PF5020_PWRUP_CTRL_PGOOD_PDGRP_MASK)
157 
158 #define PF5020_PWRUP_CTRL_PWRDWN_MODE_MASK  (0x40U)
159 #define PF5020_PWRUP_CTRL_PWRDWN_MODE_SHIFT (6U)
160 #define PF5020_PWRUP_CTRL_PWRDWN_MODE(x) \
161     (((uint8_t)(((uint8_t)(x)) << PF5020_PWRUP_CTRL_PWRDWN_MODE_SHIFT)) & PF5020_PWRUP_CTRL_PWRDWN_MODE_MASK)
162 
163 /*******************************************************************************
164  * Prototypes
165  ******************************************************************************/
166 static status_t PF5020_SetRegulatorCommonConfig(pf5020_handle_t *handle,
167                                                 pf5020_regulator_name_t regulatorName,
168                                                 bool enableUVBypass,
169                                                 bool enableOVBypass,
170                                                 bool enableWatchdogBypass,
171                                                 bool enablePGMonitor,
172                                                 bool faultReEnabled,
173                                                 bool enableILIMBypass);
174 
175 static status_t PF5020_MaskInterrupts(pf5020_handle_t *handle, uint64_t interruptMask, bool enableMask);
176 
177 /*******************************************************************************
178  * Variables
179  ******************************************************************************/
180 
181 /*******************************************************************************
182  * Code
183  ******************************************************************************/
PF5020_SetRegulatorCommonConfig(pf5020_handle_t * handle,pf5020_regulator_name_t regulatorName,bool enableUVBypass,bool enableOVBypass,bool enableWatchdogBypass,bool enablePGMonitor,bool faultReEnabled,bool enableILIMBypass)184 static status_t PF5020_SetRegulatorCommonConfig(pf5020_handle_t *handle,
185                                                 pf5020_regulator_name_t regulatorName,
186                                                 bool enableUVBypass,
187                                                 bool enableOVBypass,
188                                                 bool enableWatchdogBypass,
189                                                 bool enablePGMonitor,
190                                                 bool faultReEnabled,
191                                                 bool enableILIMBypass)
192 {
193     assert(handle);
194 
195     uint8_t regAddrShift;
196     uint8_t tmp8;
197     status_t status = kStatus_Success;
198 
199     /* Calculate register address shift based on regulator name. */
200     if (regulatorName == kPF5020_RegulatorLdo1)
201     {
202         regAddrShift = ((uint8_t)regulatorName - 1U) * 8U + 7U;
203     }
204     else
205     {
206         regAddrShift = (uint8_t)regulatorName * 8U;
207     }
208 
209     tmp8 = PF5020_REGULATOR_PG_EN(enablePGMonitor) | PF5020_REGULATOR_WDBYPASS(enableWatchdogBypass) |
210            PF5020_REGULATOR_ILIM_BYPASS(enableILIMBypass) | PF5020_REGULATOR_OV_BYPASS(enableOVBypass) |
211            PF5020_REGULATOR_UV_BYPASS(enableUVBypass);
212 
213     status = PF5020_ModifyReg(handle, PF5020_SW2_CONFIG1 + regAddrShift, 0xE3U, tmp8);
214 
215     if (status == kStatus_Success)
216     {
217         status = PF5020_ModifyReg(handle, PF5020_SW1_CONFIG2 + regAddrShift, 0x80U,
218                                   PF5020_REGULATOR_FLT_REN(faultReEnabled));
219     }
220 
221     return status;
222 }
223 
PF5020_MaskInterrupts(pf5020_handle_t * handle,uint64_t interruptMask,bool enableMask)224 static status_t PF5020_MaskInterrupts(pf5020_handle_t *handle, uint64_t interruptMask, bool enableMask)
225 {
226     static const uint8_t maskRegArray[] = PF5020_INT_MASK_ARRAY;
227     uint8_t maskReg;
228     uint8_t regIndex;
229     uint64_t tmp64;
230     uint8_t maskRegValue;
231     status_t status = kStatus_Success;
232 
233     for (regIndex = 0U; regIndex < 7U; regIndex++)
234     {
235         /* Get each interrupt mask register's value. */
236         tmp64 = interruptMask & (0xFFULL << (regIndex * 8U));
237 
238         if (tmp64 != 0ULL)
239         {
240             if ((tmp64 & (uint64_t)kPF5020_ILIM_Ldo1IlimInterrupt) != 0ULL)
241             {
242                 tmp64 &= (uint64_t)(~kPF5020_ILIM_Ldo1IlimInterrupt);
243                 status = PF5020_WriteReg(handle, PF5020_LDO_ILIM_MASK, enableMask ? 0U : 1U);
244             }
245             if ((tmp64 & (uint64_t)kPF5020_UV_Ldo1UvInterrupt) != 0ULL)
246             {
247                 tmp64 &= (uint64_t)(~kPF5020_UV_Ldo1UvInterrupt);
248                 status = PF5020_WriteReg(handle, PF5020_LDO_UV_MASK, enableMask ? 0U : 1U);
249             }
250 
251             if ((tmp64 & (uint64_t)kPF5020_OV_Ldo1OvInterrupt) != 0UL)
252             {
253                 tmp64 &= (uint64_t)(~kPF5020_OV_Ldo1OvInterrupt);
254                 status = PF5020_WriteReg(handle, PF5020_LDO_OV_MASK, enableMask ? 0U : 1U);
255             }
256             if (status == kStatus_Success)
257             {
258                 maskRegValue = (uint8_t)((tmp64 >> (regIndex * 8U)) & 0xFFU);
259                 maskReg      = maskRegArray[regIndex];
260                 status = PF5020_ModifyReg(handle, maskReg, maskRegValue, enableMask ? (~maskRegValue) : maskRegValue);
261             }
262         }
263     }
264 
265     return status;
266 }
267 
268 /*!
269  * brief Write to PF5020 register via I2C.
270  *
271  * param handle The pointer to pf5020_handle_t.
272  * param regAddr The address of register to write.
273  * param val The value to be write.
274  *
275  * retval #kStatus_Success The transaction was started successfully.
276  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
277  *      transaction is already in progress.
278  */
PF5020_WriteReg(pf5020_handle_t * handle,uint8_t regAddr,uint8_t val)279 status_t PF5020_WriteReg(pf5020_handle_t *handle, uint8_t regAddr, uint8_t val)
280 {
281     assert(handle);
282     assert(handle->I2C_SendFunc);
283 
284     return handle->I2C_SendFunc(handle->slaveAddress, regAddr, 1U, &val, 1U);
285 }
286 
287 /*!
288  * brief Read value from PF5020 register via I2C.
289  *
290  * param handle The pointer to pf5020_handle_t.
291  * param regAddr The address of register to write.
292  * param val Pointer store return value.
293  *
294  * retval #kStatus_Success The transaction was started successfully.
295  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
296  *      transaction is already in progress.
297  */
PF5020_ReadReg(pf5020_handle_t * handle,uint8_t regAddr,uint8_t * val)298 status_t PF5020_ReadReg(pf5020_handle_t *handle, uint8_t regAddr, uint8_t *val)
299 {
300     assert(handle);
301     assert(handle->I2C_ReceiveFunc);
302 
303     return handle->I2C_ReceiveFunc(handle->slaveAddress, regAddr, 1U, val, 1U);
304 }
305 
306 /*!
307  * brief Read and modify the register value
308  *
309  * param handle The pointer to pf5020_handle_t structure.
310  * param regAddr The address of register.
311  * param mask The mask of register bit to be modified.
312  * param val The value to be set.
313  *
314  * retval #kStatus_Success The transaction was started successfully.
315  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
316  *      transaction is already in progress.
317  */
PF5020_ModifyReg(pf5020_handle_t * handle,uint8_t regAddr,uint8_t mask,uint8_t val)318 status_t PF5020_ModifyReg(pf5020_handle_t *handle, uint8_t regAddr, uint8_t mask, uint8_t val)
319 {
320     assert(handle);
321 
322     status_t status = kStatus_Success;
323     uint8_t tmp8;
324 
325     status = PF5020_ReadReg(handle, regAddr, &tmp8);
326 
327     if (status == kStatus_Success)
328     {
329         tmp8 &= (uint8_t)~mask;
330         tmp8 |= (val & mask);
331         status = PF5020_WriteReg(handle, regAddr, tmp8);
332     }
333 
334     return status;
335 }
336 
337 /*!
338  * brief Dump the value of continuous registers.
339  *
340  * param handle The pointer to pf5020_handle_t structure.
341  * param regAddr The address of start register.
342  * param buffer The buffer to store the dumped registers' value.
343  * param length The length of the continuous registers to be dumped.
344  *
345  * retval #kStatus_Success The transaction was started successfully.
346  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
347  *      transaction is already in progress.
348  */
PF5020_DumpReg(pf5020_handle_t * handle,uint8_t regAddr,uint8_t * buffer,uint8_t length)349 status_t PF5020_DumpReg(pf5020_handle_t *handle, uint8_t regAddr, uint8_t *buffer, uint8_t length)
350 {
351     assert(handle);
352     assert(handle->I2C_ReceiveFunc);
353 
354     uint8_t i       = 0U;
355     status_t status = kStatus_Success;
356 
357     for (i = 0U; i < length; i++)
358     {
359         status = PF5020_ReadReg(handle, regAddr++, buffer++);
360         if (status != kStatus_Success)
361         {
362             /* In case of fail to read register. */
363             break;
364         }
365     }
366 
367     return status;
368 }
369 
370 /*!
371  * brief Get default initialize configuration.
372  *
373  * code
374  *   config->I2C_SendFunc = NULL;
375  *   config->I2C_ReceiveFunc = NULL;
376  *   config->slaveAddress = 0x08U;
377  * endcode
378  * param config The pointer to pf5020_config_t structure.
379  */
PF5020_GetDefaultConfig(pf5020_config_t * config)380 void PF5020_GetDefaultConfig(pf5020_config_t *config)
381 {
382     assert(config);
383 
384     config->I2C_SendFunc    = NULL;
385     config->I2C_ReceiveFunc = NULL;
386     /* In default, the slave address of PF5020 is 0x08. */
387     config->slaveAddress = 0x08U;
388 }
389 
390 /*!
391  * brief Initialize runtime handle.
392  *
393  * param handle The pointer to pf5020_handle_t structure.
394  * param config The pointer to pf5020_config_t structure.
395  */
PF5020_CreateHandle(pf5020_handle_t * handle,const pf5020_config_t * config)396 void PF5020_CreateHandle(pf5020_handle_t *handle, const pf5020_config_t *config)
397 {
398     assert(handle);
399     assert(config);
400 
401     handle->I2C_SendFunc    = config->I2C_SendFunc;
402     handle->I2C_ReceiveFunc = config->I2C_ReceiveFunc;
403     handle->slaveAddress    = config->slaveAddress;
404 }
405 
406 /*!
407  * brief Set power up sequencer time base.
408  *
409  * param handle The pointer to pf5020_handle_t structure.
410  * param timeBase The time base value to set, please refer pf5020_sequencer_time_base_t for details.
411  *
412  * retval #kStatus_Success The transaction was started successfully.
413  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
414  *      transaction is already in progress.
415  */
PF5020_SetSequencerTimeBase(pf5020_handle_t * handle,pf5020_sequencer_time_base_t timeBase)416 status_t PF5020_SetSequencerTimeBase(pf5020_handle_t *handle, pf5020_sequencer_time_base_t timeBase)
417 {
418     assert(handle);
419 
420     return PF5020_ModifyReg(handle, PF5020_PWRUP_CTRL, 0x3U, (uint8_t)timeBase & 0x3U);
421 }
422 
423 /*!
424  * brief Set power up sequence, when transitioning from standby state to run state, the power up sequencer is activated
425  * only if any of the regulators is re-enabled during this transition.
426  *
427  * param handle The pointer to pf5020_handle_t structure.
428  * param powerUpSeq The pointer to pf5020_power_up_sequence_t structure.
429  * retval #kStatus_Success The transaction was started successfully.
430  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
431  *      transaction is already in progress.
432  */
PF5020_SetPowerUpSequence(pf5020_handle_t * handle,pf5020_power_up_sequence_t * powerUpSeq)433 status_t PF5020_SetPowerUpSequence(pf5020_handle_t *handle, pf5020_power_up_sequence_t *powerUpSeq)
434 {
435     assert(handle);
436     assert(powerUpSeq);
437 
438     static const uint8_t seqReqArray[] = PF5020_SEQ_REG_ARRAY;
439     uint8_t tmp8;
440     uint8_t i;
441     status_t status;
442 
443     for (i = 0U; i < 6U; i++)
444     {
445         status = PF5020_ReadReg(handle, seqReqArray[i], &tmp8);
446         /* if the sequence order to set is same as register value, it is no need to set register again. */
447         if ((tmp8 != *((uint8_t *)powerUpSeq + i)) && (status == kStatus_Success))
448         {
449             status = PF5020_WriteReg(handle, seqReqArray[i], *((uint8_t *)powerUpSeq + i));
450         }
451 
452         if (status != kStatus_Success)
453         {
454             break;
455         }
456     }
457 
458     return status;
459 }
460 
461 /*!
462  * brief Set power down mode, sequential mode or group mode.
463  *
464  * param handle The pointer to pf5020_handle_t structure.
465  * param powerDownMode The power down mode to set, please refer to pf5020_power_down_mode_t.
466  * retval #kStatus_Success The transaction was started successfully.
467  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
468  *      transaction is already in progress.
469  */
PF5020_SetPowerDownMode(pf5020_handle_t * handle,pf5020_power_down_mode_t powerDownMode)470 status_t PF5020_SetPowerDownMode(pf5020_handle_t *handle, pf5020_power_down_mode_t powerDownMode)
471 {
472     assert(handle);
473 
474     return PF5020_ModifyReg(handle, PF5020_PWRUP_CTRL, PF5020_PWRUP_CTRL_PWRDWN_MODE_MASK,
475                             PF5020_PWRUP_CTRL_PWRDWN_MODE(powerDownMode));
476 }
477 
478 /*!
479  * brief Set power down groups that each internal module placed to.
480  *
481  * param handle The pointer to pf5020_handle_t structure.
482  * param groupConfig Pointer to the pf5020_power_down_group_config_t structure.
483  * retval #kStatus_Success The transaction was started successfully.
484  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
485  *      transaction is already in progress.
486  */
PF5020_SetPowerDownGroups(pf5020_handle_t * handle,const pf5020_power_down_group_config_t * groupConfig)487 status_t PF5020_SetPowerDownGroups(pf5020_handle_t *handle, const pf5020_power_down_group_config_t *groupConfig)
488 {
489     assert(handle);
490     assert(groupConfig);
491 
492     status_t status;
493 
494     status = PF5020_ModifyReg(handle, PF5020_PWRUP_CTRL,
495                               PF5020_PWRUP_CTRL_PGOOD_PDGRP_MASK | PF5020_PWRUP_CTRL_RESETBMCU_PDGRP_MASK,
496                               PF5020_PWRUP_CTRL_RESETBMCU_PDGRP(groupConfig->resetBMCUGroup) |
497                                   PF5020_PWRUP_CTRL_PGOOD_PDGRP(groupConfig->pGoodGroup));
498 
499     if (status == kStatus_Success)
500     {
501         status = PF5020_ModifyReg(handle, PF5020_SW1_MODE, PF5020_BUCK_REGULATOR_PDGPR_MASK,
502                                   PF5020_BUCK_REGULATOR_PDGPR(groupConfig->sw1Group));
503     }
504     if (status == kStatus_Success)
505     {
506         status = PF5020_ModifyReg(handle, PF5020_SW2_MODE1, PF5020_BUCK_REGULATOR_PDGPR_MASK,
507                                   PF5020_BUCK_REGULATOR_PDGPR(groupConfig->sw2Group));
508     }
509     if (status == kStatus_Success)
510     {
511         status = PF5020_ModifyReg(handle, PF5020_SWND1_MODE1, PF5020_BUCK_REGULATOR_PDGPR_MASK,
512                                   PF5020_BUCK_REGULATOR_PDGPR(groupConfig->swnd1Group));
513     }
514     if (status == kStatus_Success)
515     {
516         status = PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG2, PF5020_LDO1_CONFIG2_LDO1_PDGRP_MASK,
517                                   PF5020_LDO1_CONFIG2_LDO1_PDGRP(groupConfig->ldo1Group));
518     }
519 
520     return status;
521 }
522 
523 /*!
524  * brief Set selected power down group's delay.
525  *
526  * param handle The pointer to pf5020_handle_t structure.
527  * param group The selected power down group, please refer to pf5020_power_down_group_t for details.
528  * param delay The delay value to be set, please refer to pf5020_power_down_delay_t for details.
529  * retval #kStatus_Success The transaction was started successfully.
530  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
531  *      transaction is already in progress.
532  */
PF5020_SetPowerDownGroupDelay(pf5020_handle_t * handle,pf5020_power_down_group_t group,pf5020_power_down_delay_t delay)533 status_t PF5020_SetPowerDownGroupDelay(pf5020_handle_t *handle,
534                                        pf5020_power_down_group_t group,
535                                        pf5020_power_down_delay_t delay)
536 {
537     assert(handle);
538 
539     return PF5020_ModifyReg(handle, PF5020_PWRDN_DLY1, (0x3U << (2U * (3U - (uint8_t)group))),
540                             (uint8_t)delay << (2U * (3U - (uint8_t)group)));
541 }
542 
543 /*!
544  * brief Set delay to disable the regulators after RESETBMCU is asserted.
545  *
546  * param handle The pointer to pf5020_handle_t structure.
547  * param delay The delay value, please refer to pf5020_resetBMCU_delay_t.
548  * retval #kStatus_Success The transaction was started successfully.
549  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
550  *      transaction is already in progress.
551  */
PF5020_SetResetBMcuPinDelay(pf5020_handle_t * handle,pf5020_resetBMCU_delay_t delay)552 status_t PF5020_SetResetBMcuPinDelay(pf5020_handle_t *handle, pf5020_resetBMCU_delay_t delay)
553 {
554     assert(handle);
555 
556     return PF5020_WriteReg(handle, PF5020_PWRDN_DLY2, (uint8_t)delay);
557 }
558 
559 /*!
560  * brief Turn off PF5020 PMIC.
561  *
562  * param handle The pointer to pf5020_handle_t structure.
563  * retval #kStatus_Success The transaction was started successfully.
564  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
565  *      transaction is already in progress.
566  */
PF5020_TurnOffPMIC(pf5020_handle_t * handle)567 status_t PF5020_TurnOffPMIC(pf5020_handle_t *handle)
568 {
569     assert(handle);
570 
571     return PF5020_ModifyReg(handle, PF5020_CTRL3, PF5020_CTRL3_PMIC_OFF_MASK, PF5020_CTRL3_PMIC_OFF_MASK);
572 }
573 
574 /*!
575  * brief Configure internal high speed clock.
576  *
577  * param handle The pointer to pf5020_handle_t structure.
578  * param config The pointer to pf5020_high_speed_clk_config_t structure.
579  * retval #kStatus_Success The transaction was started successfully.
580  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
581  *      transaction is already in progress.
582  */
PF5020_CLK_ConfigHighSpeedClock(pf5020_handle_t * handle,const pf5020_high_speed_clk_config_t * config)583 status_t PF5020_CLK_ConfigHighSpeedClock(pf5020_handle_t *handle, const pf5020_high_speed_clk_config_t *config)
584 {
585     assert(handle);
586     assert(config);
587 
588     uint8_t tmp8;
589 
590     tmp8 = ((uint8_t)(config->clkFreq) | ((uint8_t)(config->enableSS) << 5U) | ((uint8_t)(config->ssRange) << 4U));
591     return PF5020_ModifyReg(handle, PF5020_FREQ_CTRL, 0x3FU, tmp8);
592 }
593 
594 /*!
595  * brief Enable/disable clock sync out.
596  *
597  * param handle The pointer to pf5020_handle_t structure.
598  * param enable Used to enable/disable sync output.
599  * retval #kStatus_Success The transaction was started successfully.
600  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
601  *      transaction is already in progress.
602  */
PF5020_CLK_EnableSyncOut(pf5020_handle_t * handle,bool enable)603 status_t PF5020_CLK_EnableSyncOut(pf5020_handle_t *handle, bool enable)
604 {
605     return PF5020_ModifyReg(handle, PF5020_FREQ_CTRL, 0x80U, enable ? 0x80U : 0U);
606 }
607 
608 /*!
609  * brief Set VSNS LDO output voltage.
610  *
611  * param handle The pointer to pf5020_handle_t structure.
612  * param voltage The output voltage of VSNVS, please refer to pf5020_vsnvs_ldo_output_voltage_t.
613  * retval #kStatus_Success The transaction was started successfully.
614  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
615  *      transaction is already in progress.
616  */
PF5020_SetVsnvsLdoOutputVoltage(pf5020_handle_t * handle,pf5020_vsnvs_ldo_output_voltage_t voltage)617 status_t PF5020_SetVsnvsLdoOutputVoltage(pf5020_handle_t *handle, pf5020_vsnvs_ldo_output_voltage_t voltage)
618 {
619     assert(handle);
620 
621     return PF5020_WriteReg(handle, PF5020_VSNVS_CONFIG1, (uint8_t)voltage);
622 }
623 
624 /* SW1 Buck Regulator Control APIs. */
625 /*!
626  * brief Set SW1 Buck regulator global configuration.
627  *
628  * param handle The pointer to pf5020_handle_t structure.
629  * param config The pointer to pf5020_sw1_regulator_config_t structure.
630  * retval #kStatus_Success The transaction was started successfully.
631  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
632  *      transaction is already in progress.
633  */
PF5020_SW1_SetGlobalConfig(pf5020_handle_t * handle,const pf5020_sw1_regulator_config_t * config)634 status_t PF5020_SW1_SetGlobalConfig(pf5020_handle_t *handle, const pf5020_sw1_regulator_config_t *config)
635 {
636     assert(handle);
637     assert(config);
638 
639     status_t status;
640     uint8_t value         = 0U;
641     uint8_t mask          = 0U;
642     bool enableILIMBypass = true;
643 
644     /* Set SW1 DVS Ramp. */
645     status = PF5020_ModifyReg(handle, PF5020_SW_RAMP, 0x7U, (uint8_t)(config->sw1DvsRamp));
646 
647     if (status == kStatus_Success)
648     {
649         /* Set SW1 output voltage in run state. */
650         status = PF5020_WriteReg(handle, PF5020_SW1_RUN_VOLT, config->sw1RunOutputVolt);
651     }
652     if (status == kStatus_Success)
653     {
654         /* Set SW1 output voltage in standby state. */
655         status = PF5020_WriteReg(handle, PF5020_SW1_STBY_VOLT, config->sw1StandbyOutputVolt);
656     }
657 
658     if (status == kStatus_Success)
659     {
660         /* Update operate mode in run/standby state. */
661         status = PF5020_ModifyReg(handle, PF5020_SW1_MODE,
662                                   PF5020_BUCK_REGULATOR_RUN_MODE_MASK | PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK,
663                                   PF5020_BUCK_REGULATOR_RUN_MODE(config->sw1RunOperateMode) |
664                                       PF5020_BUCK_REGULATOR_STANDBY_MODE(config->sw1StandbyOperateMode));
665     }
666     if (status == kStatus_Success)
667     {
668         if (config->sw1CurrentLimit != kPF5020_BuckRegulatorCurrentLimitBypass)
669         {
670             enableILIMBypass = false;
671             value |= PF5020_BUCK_REGULATOR_ILIM(config->sw1CurrentLimit);
672             mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
673         }
674 
675         status = PF5020_SetRegulatorCommonConfig(
676             handle, kPF5020_BuckRegulatorSw1, config->sw1EnableUVBypass, config->sw1EnableOVBypass,
677             config->sw1EnableWatchdogBypass, config->sw1EnablePGMonitor, config->sw1FaultReEnabled, enableILIMBypass);
678 
679         if (status == kStatus_Success)
680         {
681             value |= PF5020_BUCK_REGULATOR_PHASE(config->sw1PhaseShift);
682             mask |= PF5020_BUCK_REGULATOR_PHASE_MASK;
683             /* Set SW1 Config2 register, this register can be used to set current limitation value and phase shift.  */
684             status = PF5020_ModifyReg(handle, PF5020_SW1_CONFIG2, mask, value);
685         }
686     }
687 
688     return status;
689 }
690 
691 /*!
692  * brief Set DVS Ramp for SW1 buck regulator.
693  *
694  * param handle The pointer to pf5020_handle_t structure.
695  * param dvsRamp The DVS ramp value to set, please refer to pf5020_type1_buck_regulator_dvs_ramp_t for details.
696  * retval #kStatus_Success The transaction was started successfully.
697  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
698  *      transaction is already in progress.
699  */
PF5020_SW1_SetDvsRamp(pf5020_handle_t * handle,pf5020_type1_buck_regulator_dvs_ramp_t dvsRamp)700 status_t PF5020_SW1_SetDvsRamp(pf5020_handle_t *handle, pf5020_type1_buck_regulator_dvs_ramp_t dvsRamp)
701 {
702     assert(handle);
703 
704     return PF5020_ModifyReg(handle, PF5020_SW_RAMP, 0x3U, (uint8_t)dvsRamp);
705 }
706 
707 /*!
708  * brief Set SW1 regulator's output voltage and operate mode in run state.
709  *
710  * param handle The pointer to pf5020_handle_t structure.
711  * param runOutputVolt The output voltage of SW1 in run state.
712  * param runOperateMode The operate mode of SW1 in run state.
713  * retval #kStatus_Success The transaction was started successfully.
714  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
715  *      transaction is already in progress.
716  */
PF5020_SW1_SetRunStateOption(pf5020_handle_t * handle,uint8_t runOutputVolt,pf5020_buck_regulator_operate_mode_t runOperateMode)717 status_t PF5020_SW1_SetRunStateOption(pf5020_handle_t *handle,
718                                       uint8_t runOutputVolt,
719                                       pf5020_buck_regulator_operate_mode_t runOperateMode)
720 {
721     assert(handle);
722 
723     uint8_t sw1RunMode;
724     uint8_t sw1RunVolt;
725     status_t status = kStatus_Success;
726 
727     (void)PF5020_ReadReg(handle, PF5020_SW1_MODE, &sw1RunMode);
728     sw1RunMode &= PF5020_BUCK_REGULATOR_RUN_MODE_MASK;
729     sw1RunMode = sw1RunMode >> PF5020_BUCK_REGULATOR_RUN_MODE_SHIFT;
730     (void)PF5020_ReadReg(handle, PF5020_SW1_RUN_VOLT, &sw1RunVolt);
731 
732     if (sw1RunVolt != runOutputVolt)
733     {
734         status = PF5020_WriteReg(handle, PF5020_SW1_RUN_VOLT, runOutputVolt);
735     }
736     if ((sw1RunMode != (uint8_t)runOperateMode) && (status == kStatus_Success))
737     {
738         status = PF5020_ModifyReg(handle, PF5020_SW1_MODE, PF5020_BUCK_REGULATOR_RUN_MODE_MASK,
739                                   PF5020_BUCK_REGULATOR_RUN_MODE(runOperateMode));
740     }
741 
742     return status;
743 }
744 
745 /*!
746  * brief Set SW1 regulator's output voltage and operate mode in standby state.
747  *
748  * param handle The pointer to pf5020_handle_t structure.
749  * param standbyOutputVolt The output voltage of SW1 in standby state.
750  * param standbyOperateMode The operate mode of SW1 in standby state.
751  * retval #kStatus_Success The transaction was started successfully.
752  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
753  *      transaction is already in progress.
754  */
PF5020_SW1_SetStandbyStateOption(pf5020_handle_t * handle,uint8_t standbyOutputVolt,pf5020_buck_regulator_operate_mode_t standbyOperateMode)755 status_t PF5020_SW1_SetStandbyStateOption(pf5020_handle_t *handle,
756                                           uint8_t standbyOutputVolt,
757                                           pf5020_buck_regulator_operate_mode_t standbyOperateMode)
758 {
759     assert(handle);
760 
761     uint8_t sw1StandbyMode;
762     uint8_t sw1StandbyVolt;
763     status_t status = kStatus_Success;
764 
765     (void)PF5020_ReadReg(handle, PF5020_SW1_MODE, &sw1StandbyMode);
766     sw1StandbyMode &= PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK;
767     sw1StandbyMode = sw1StandbyMode >> PF5020_BUCK_REGULATOR_STANDBY_MODE_SHIFT;
768 
769     (void)PF5020_ReadReg(handle, PF5020_SW1_STBY_VOLT, &sw1StandbyVolt);
770 
771     if (sw1StandbyVolt != standbyOutputVolt)
772     {
773         status = PF5020_WriteReg(handle, PF5020_SW1_STBY_VOLT, standbyOutputVolt);
774     }
775 
776     if ((sw1StandbyMode != (uint8_t)standbyOperateMode) && (status == kStatus_Success))
777     {
778         status = PF5020_ModifyReg(handle, PF5020_SW1_MODE, PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK,
779                                   PF5020_BUCK_REGULATOR_STANDBY_MODE(standbyOperateMode));
780     }
781 
782     return status;
783 }
784 
785 /*!
786  * brief Set SW1 regulator fault detection related options.
787  *
788  * param handle The pointer to pf5020_handle_t structure.
789  * param currentLimit SW1 buck regulator current limitation value, please refer to
790  *                      pf5020_buck_regulator_current_limit_t for details.
791  * param enableUVBypass Enable/disable UV bypass.
792  * param enableOVBypass Enable/disable OV bypass.
793  * param faultReEnabled Used to control whether return to sw1 regulator previous state if fault condition is cleared.
794  * retval #kStatus_Success The transaction was started successfully.
795  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
796  *      transaction is already in progress.
797  */
PF5020_SW1_SetFaultDetection(pf5020_handle_t * handle,pf5020_buck_regulator_current_limit_t currentLimit,bool enableUVBypass,bool enableOVBypass,bool faultReEnabled)798 status_t PF5020_SW1_SetFaultDetection(pf5020_handle_t *handle,
799                                       pf5020_buck_regulator_current_limit_t currentLimit,
800                                       bool enableUVBypass,
801                                       bool enableOVBypass,
802                                       bool faultReEnabled)
803 {
804     assert(handle);
805 
806     status_t status;
807     bool enableILIMBypass   = false;
808     uint8_t sw1Config2Mask  = 0U;
809     uint8_t sw1Config2Value = 0U;
810 
811     if (currentLimit == kPF5020_BuckRegulatorCurrentLimitBypass)
812     {
813         enableILIMBypass = true;
814     }
815     else
816     {
817         sw1Config2Mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
818         sw1Config2Value |= PF5020_BUCK_REGULATOR_ILIM(currentLimit);
819     }
820 
821     sw1Config2Mask |= PF5020_REGULATOR_FLT_REN_MASK;
822     sw1Config2Value |= PF5020_REGULATOR_FLT_REN(faultReEnabled);
823     status = PF5020_ModifyReg(handle, PF5020_SW1_CONFIG2, sw1Config2Mask, sw1Config2Value);
824 
825     if (status == kStatus_Success)
826     {
827         status = PF5020_ModifyReg(
828             handle, PF5020_SW1_CONFIG1,
829             PF5020_REGULATOR_ILIM_BYPASS_MASK | PF5020_REGULATOR_OV_BYPASS_MASK | PF5020_REGULATOR_UV_BYPASS_MASK,
830             PF5020_REGULATOR_ILIM_BYPASS(enableILIMBypass) | PF5020_REGULATOR_OV_BYPASS(enableOVBypass) |
831                 PF5020_REGULATOR_UV_BYPASS(enableUVBypass));
832     }
833 
834     return status;
835 }
836 
837 /*!
838  * brief Set SW1 regulator phase shift value.
839  *
840  * param handle The pointer to pf5020_handle_t structure.
841  * param phaseShift SW1 buck regulator phase shift value, please refer to pf5020_buck_regulator_phase_shift_t
842  *                   for details.
843  * retval #kStatus_Success The transaction was started successfully.
844  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
845  *      transaction is already in progress.
846  */
PF5020_SW1_SetPhaseShift(pf5020_handle_t * handle,pf5020_buck_regulator_phase_shift_t phaseShift)847 status_t PF5020_SW1_SetPhaseShift(pf5020_handle_t *handle, pf5020_buck_regulator_phase_shift_t phaseShift)
848 {
849     assert(handle);
850 
851     status_t status = kStatus_Success;
852     uint8_t sw1Phase;
853 
854     (void)PF5020_ReadReg(handle, PF5020_SW1_CONFIG2, &sw1Phase);
855     sw1Phase &= PF5020_BUCK_REGULATOR_PHASE_MASK;
856     sw1Phase = sw1Phase >> PF5020_BUCK_REGULATOR_PHASE_SHIFT;
857 
858     if (sw1Phase != (uint8_t)phaseShift)
859     {
860         status = PF5020_ModifyReg(handle, PF5020_SW1_CONFIG2, PF5020_BUCK_REGULATOR_PHASE_MASK,
861                                   PF5020_BUCK_REGULATOR_PHASE(phaseShift));
862     }
863 
864     return status;
865 }
866 
867 /*!
868  * brief Enable/disable PG monitor for SW1 regulator.
869  *
870  * param handle The pointer to pf5020_handle_t structure.
871  * param enable Enable/disable PG monitor.
872  * retval #kStatus_Success The transaction was started successfully.
873  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
874  *      transaction is already in progress.
875  */
PF5020_SW1_EnablePGMonitor(pf5020_handle_t * handle,bool enable)876 status_t PF5020_SW1_EnablePGMonitor(pf5020_handle_t *handle, bool enable)
877 {
878     assert(handle);
879 
880     return PF5020_ModifyReg(handle, PF5020_SW1_CONFIG1, PF5020_REGULATOR_PG_EN_MASK, PF5020_REGULATOR_PG_EN(enable));
881 }
882 
883 /*!
884  * brief Enable/disable watchdog bypass for SW1 regulator.
885  *
886  * param handle The pointer to pf5020_handle_t structure.
887  * param enable Enable/disable watchdog bypass.
888  * retval #kStatus_Success The transaction was started successfully.
889  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
890  *      transaction is already in progress.
891  */
PF5020_SW1_EnableWatchDogBypass(pf5020_handle_t * handle,bool enable)892 status_t PF5020_SW1_EnableWatchDogBypass(pf5020_handle_t *handle, bool enable)
893 {
894     assert(handle);
895 
896     return PF5020_ModifyReg(handle, PF5020_SW1_CONFIG1, PF5020_REGULATOR_WDBYPASS_MASK,
897                             PF5020_REGULATOR_WDBYPASS(enable));
898 }
899 
900 /*!
901  * brief Set SW2 Buck regulator global configuration.
902  *
903  * param handle The pointer to pf5020_handle_t structure.
904  * param config The pointer to pf5020_sw2_regulator_config_t structure.
905  * retval #kStatus_Success The transaction was started successfully.
906  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
907  *      transaction is already in progress.
908  */
PF5020_SW2_SetGlobalConfig(pf5020_handle_t * handle,const pf5020_sw2_regulator_config_t * config)909 status_t PF5020_SW2_SetGlobalConfig(pf5020_handle_t *handle, const pf5020_sw2_regulator_config_t *config)
910 {
911     assert(handle);
912     assert(config);
913 
914     status_t status;
915     uint8_t value         = 0U;
916     uint8_t mask          = 0U;
917     bool enableILIMBypass = true;
918 
919     /* Set SW2 DVS Ramp. */
920     status = PF5020_ModifyReg(handle, PF5020_SW_RAMP, 0xCU, ((uint8_t)config->sw2DvsRamp) << 2U);
921 
922     if (status == kStatus_Success)
923     {
924         /* Set SW2 output voltage in run state. */
925         status = PF5020_WriteReg(handle, PF5020_SW2_RUN_VOLT, config->sw2RunOutputVolt);
926     }
927     if (status == kStatus_Success)
928     {
929         /* Set SW2 output voltage in standby state. */
930         status = PF5020_WriteReg(handle, PF5020_SW2_STBY_VOLT, config->sw2StandbyOutputVolt);
931     }
932 
933     if (status == kStatus_Success)
934     {
935         /* Update SW2 operate mode in run/standby state. */
936         status = PF5020_ModifyReg(handle, PF5020_SW2_MODE1,
937                                   PF5020_BUCK_REGULATOR_RUN_MODE_MASK | PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK,
938                                   PF5020_BUCK_REGULATOR_RUN_MODE(config->sw2RunOperateMode) |
939                                       PF5020_BUCK_REGULATOR_STANDBY_MODE(config->sw2StandbyOperateMode));
940     }
941     if (status == kStatus_Success)
942     {
943         if (config->sw2CurrentLimit != kPF5020_BuckRegulatorCurrentLimitBypass)
944         {
945             enableILIMBypass = false;
946             value |= PF5020_BUCK_REGULATOR_ILIM(config->sw2CurrentLimit);
947             mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
948         }
949         status = PF5020_SetRegulatorCommonConfig(
950             handle, kPF5020_BuckRegulatorSw2, config->sw2EnableUVBypass, config->sw2EnableOVBypass,
951             config->sw2EnableWatchdogBypass, config->sw2EnablePGMonitor, config->sw2FaultReEnabled, enableILIMBypass);
952 
953         if (status == kStatus_Success)
954         {
955             value |= PF5020_BUCK_REGULATOR_PHASE(config->sw2PhaseShift) |
956                      PF5020_SW2_CONFIG2_VTTEN(config->sw2EnableVTTOperation);
957             mask |= PF5020_BUCK_REGULATOR_PHASE_MASK | PF5020_SW2_CONFIG2_VTTEN_MASK;
958             /* Update SW2 CONFIG2 register, this register can be used to set current limitation and phase shift. */
959             status = PF5020_ModifyReg(handle, PF5020_SW2_CONFIG2, mask, value);
960         }
961     }
962 
963     return status;
964 }
965 
966 /*!
967  * brief Set DVS Ramp for SW2 buck regulator.
968  *
969  * param handle The pointer to pf5020_handle_t structure.
970  * param dvsRamp The DVS ramp value to set, please refer to pf5020_type1_buck_regulator_dvs_ramp_t for details.
971  * retval #kStatus_Success The transaction was started successfully.
972  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
973  *      transaction is already in progress.
974  */
PF5020_SW2_SetDvsRamp(pf5020_handle_t * handle,pf5020_type1_buck_regulator_dvs_ramp_t dvsRamp)975 status_t PF5020_SW2_SetDvsRamp(pf5020_handle_t *handle, pf5020_type1_buck_regulator_dvs_ramp_t dvsRamp)
976 {
977     assert(handle);
978 
979     return PF5020_ModifyReg(handle, PF5020_SW_RAMP, 0xCU, ((uint8_t)dvsRamp << 2U));
980 }
981 
982 /*!
983  * brief Set SW2 regulator's output voltage and operate mode in run state.
984  *
985  * param handle The pointer to pf5020_handle_t structure.
986  * param runOutputVolt The output voltage of SW2 in run state.
987  * param runOperateMode The operate mode of SW2 in run state.
988  * retval #kStatus_Success The transaction was started successfully.
989  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
990  *      transaction is already in progress.
991  */
PF5020_SW2_SetRunStateOption(pf5020_handle_t * handle,uint8_t runOutputVolt,pf5020_buck_regulator_operate_mode_t runOperateMode)992 status_t PF5020_SW2_SetRunStateOption(pf5020_handle_t *handle,
993                                       uint8_t runOutputVolt,
994                                       pf5020_buck_regulator_operate_mode_t runOperateMode)
995 {
996     assert(handle);
997 
998     uint8_t sw2RunMode;
999     uint8_t sw2RunVolt;
1000     status_t status = kStatus_Success;
1001 
1002     (void)PF5020_ReadReg(handle, PF5020_SW2_MODE1, &sw2RunMode);
1003     sw2RunMode &= PF5020_BUCK_REGULATOR_RUN_MODE_MASK;
1004     sw2RunMode = sw2RunMode >> PF5020_BUCK_REGULATOR_RUN_MODE_SHIFT;
1005     (void)PF5020_ReadReg(handle, PF5020_SW2_RUN_VOLT, &sw2RunVolt);
1006 
1007     if (sw2RunVolt != runOutputVolt)
1008     {
1009         status = PF5020_WriteReg(handle, PF5020_SW2_RUN_VOLT, runOutputVolt);
1010     }
1011     if ((sw2RunMode != (uint8_t)runOperateMode) && (status == kStatus_Success))
1012     {
1013         status = PF5020_ModifyReg(handle, PF5020_SW2_MODE1, PF5020_BUCK_REGULATOR_RUN_MODE_MASK,
1014                                   PF5020_BUCK_REGULATOR_RUN_MODE(runOperateMode));
1015     }
1016 
1017     return status;
1018 }
1019 
1020 /*!
1021  * brief Set SW2 regulator's output voltage and operate mode in standby state.
1022  *
1023  * param handle The pointer to pf5020_handle_t structure.
1024  * param standbyOutputVolt The output voltage of SW2 in standby state.
1025  * param standbyOperateMode The operate mode of SW2 in standby state.
1026  * retval #kStatus_Success The transaction was started successfully.
1027  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1028  *      transaction is already in progress.
1029  */
PF5020_SW2_SetStandbyStateOption(pf5020_handle_t * handle,uint8_t standbyOutputVolt,pf5020_buck_regulator_operate_mode_t standbyOperateMode)1030 status_t PF5020_SW2_SetStandbyStateOption(pf5020_handle_t *handle,
1031                                           uint8_t standbyOutputVolt,
1032                                           pf5020_buck_regulator_operate_mode_t standbyOperateMode)
1033 {
1034     assert(handle);
1035 
1036     uint8_t sw2StandbyMode;
1037     uint8_t sw2StandbyVolt;
1038     status_t status = kStatus_Success;
1039 
1040     (void)PF5020_ReadReg(handle, PF5020_SW2_MODE1, &sw2StandbyMode);
1041     sw2StandbyMode &= PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK;
1042     sw2StandbyVolt = sw2StandbyMode >> PF5020_BUCK_REGULATOR_STANDBY_MODE_SHIFT;
1043 
1044     (void)PF5020_ReadReg(handle, PF5020_SW2_STBY_VOLT, &sw2StandbyVolt);
1045 
1046     if (sw2StandbyVolt != standbyOutputVolt)
1047     {
1048         status = PF5020_WriteReg(handle, PF5020_SW2_STBY_VOLT, standbyOutputVolt);
1049     }
1050 
1051     if ((sw2StandbyMode != (uint8_t)standbyOperateMode) && (status == kStatus_Success))
1052     {
1053         status = PF5020_ModifyReg(handle, PF5020_SW2_MODE1, PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK,
1054                                   PF5020_BUCK_REGULATOR_STANDBY_MODE(standbyOperateMode));
1055     }
1056 
1057     return status;
1058 }
1059 
1060 /*!
1061  * brief Set SW2 regulator phase shift value.
1062  *
1063  * param handle The pointer to pf5020_handle_t structure.
1064  * param phaseShift SW2 buck regulator phase shift value, please refer to pf5020_buck_regulator_phase_shift_t
1065  *                   for details.
1066  * retval #kStatus_Success The transaction was started successfully.
1067  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1068  *      transaction is already in progress.
1069  */
PF5020_SW2_SetPhaseShift(pf5020_handle_t * handle,pf5020_buck_regulator_phase_shift_t phaseShift)1070 status_t PF5020_SW2_SetPhaseShift(pf5020_handle_t *handle, pf5020_buck_regulator_phase_shift_t phaseShift)
1071 {
1072     assert(handle);
1073 
1074     status_t status = kStatus_Success;
1075     uint8_t sw2Phase;
1076 
1077     (void)PF5020_ReadReg(handle, PF5020_SW2_CONFIG2, &sw2Phase);
1078     sw2Phase &= PF5020_BUCK_REGULATOR_PHASE_MASK;
1079     sw2Phase = sw2Phase >> PF5020_BUCK_REGULATOR_PHASE_SHIFT;
1080 
1081     if (sw2Phase != (uint8_t)phaseShift)
1082     {
1083         status = PF5020_ModifyReg(handle, PF5020_SW2_CONFIG2, PF5020_BUCK_REGULATOR_PHASE_MASK,
1084                                   PF5020_BUCK_REGULATOR_PHASE(phaseShift));
1085     }
1086 
1087     return status;
1088 }
1089 
1090 /*!
1091  * brief Enable/disable SW2 VTT operateion.
1092  *
1093  * param handle The pointer to pf5020_handle_t structure.
1094  * param enable Used to enable/disable VTT operation.
1095  * retval #kStatus_Success The transaction was started successfully.
1096  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1097  *      transaction is already in progress.
1098  */
PF5020_SW2_EnableVTTOperation(pf5020_handle_t * handle,bool enable)1099 status_t PF5020_SW2_EnableVTTOperation(pf5020_handle_t *handle, bool enable)
1100 {
1101     return PF5020_ModifyReg(handle, PF5020_SW2_CONFIG2, PF5020_SW2_CONFIG2_VTTEN_MASK,
1102                             PF5020_SW2_CONFIG2_VTTEN(enable));
1103 }
1104 
1105 /*!
1106  * brief Set SW2 regulator fault detection related options.
1107  *
1108  * param handle The pointer to pf5020_handle_t structure.
1109  * param currentLimit SW2 buck regulator current limitation value, please refer to
1110  *                      pf5020_buck_regulator_current_limit_t for details.
1111  * param enableUVBypass Enable/disable UV bypass.
1112  * param enableOVBypass Enable/disable OV bypass.
1113  * param faultReEnabled Used to control whether return to sw1 regulator previous state if fault condition is cleared.
1114  * retval #kStatus_Success The transaction was started successfully.
1115  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1116  *      transaction is already in progress.
1117  */
PF5020_SW2_SetFaultDetection(pf5020_handle_t * handle,pf5020_buck_regulator_current_limit_t currentLimit,bool enableUVBypass,bool enableOVBypass,bool faultReEnabled)1118 status_t PF5020_SW2_SetFaultDetection(pf5020_handle_t *handle,
1119                                       pf5020_buck_regulator_current_limit_t currentLimit,
1120                                       bool enableUVBypass,
1121                                       bool enableOVBypass,
1122                                       bool faultReEnabled)
1123 {
1124     assert(handle);
1125 
1126     status_t status;
1127     bool enableILIMBypass   = false;
1128     uint8_t sw2Config2Mask  = 0U;
1129     uint8_t sw2Config2Value = 0U;
1130 
1131     if (currentLimit == kPF5020_BuckRegulatorCurrentLimitBypass)
1132     {
1133         enableILIMBypass = true;
1134     }
1135     else
1136     {
1137         sw2Config2Mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
1138         sw2Config2Value |= PF5020_BUCK_REGULATOR_ILIM(currentLimit);
1139     }
1140 
1141     sw2Config2Mask |= PF5020_REGULATOR_FLT_REN_MASK;
1142     sw2Config2Value |= PF5020_REGULATOR_FLT_REN(faultReEnabled);
1143     status = PF5020_ModifyReg(handle, PF5020_SW1_CONFIG2, sw2Config2Mask, sw2Config2Value);
1144 
1145     if (status == kStatus_Success)
1146     {
1147         status = PF5020_ModifyReg(
1148             handle, PF5020_SW1_CONFIG1,
1149             PF5020_REGULATOR_ILIM_BYPASS_MASK | PF5020_REGULATOR_OV_BYPASS_MASK | PF5020_REGULATOR_UV_BYPASS_MASK,
1150             PF5020_REGULATOR_ILIM_BYPASS(enableILIMBypass) | PF5020_REGULATOR_OV_BYPASS(enableOVBypass) |
1151                 PF5020_REGULATOR_UV_BYPASS(enableUVBypass));
1152     }
1153 
1154     return status;
1155 }
1156 
1157 /*!
1158  * brief Enable/disable PG monitor for SW2 regulator.
1159  *
1160  * param handle The pointer to pf5020_handle_t structure.
1161  * param enable Enable/disable PG monitor.
1162  * retval #kStatus_Success The transaction was started successfully.
1163  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1164  *      transaction is already in progress.
1165  */
PF5020_SW2_EnablePGMonitor(pf5020_handle_t * handle,bool enable)1166 status_t PF5020_SW2_EnablePGMonitor(pf5020_handle_t *handle, bool enable)
1167 {
1168     return PF5020_ModifyReg(handle, PF5020_SW2_CONFIG1, PF5020_REGULATOR_PG_EN_MASK, PF5020_REGULATOR_PG_EN(enable));
1169 }
1170 
1171 /*!
1172  * brief Enable/disable watchdog bypass for SW2 regulator.
1173  *
1174  * param handle The pointer to pf5020_handle_t structure.
1175  * param enable Enable/disable watchdog bypass.
1176  * retval #kStatus_Success The transaction was started successfully.
1177  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1178  *      transaction is already in progress.
1179  */
PF5020_SW2_EnableWatchDogBypass(pf5020_handle_t * handle,bool enable)1180 status_t PF5020_SW2_EnableWatchDogBypass(pf5020_handle_t *handle, bool enable)
1181 {
1182     return PF5020_ModifyReg(handle, PF5020_SW2_CONFIG1, PF5020_REGULATOR_WDBYPASS_MASK,
1183                             PF5020_REGULATOR_WDBYPASS(enable));
1184 }
1185 
1186 /*!
1187  * brief Set SWND1 Buck regulator global configuration.
1188  *
1189  * param handle The pointer to pf5020_handle_t structure.
1190  * param config The pointer to pf5020_swnd1_regulator_config_t structure.
1191  * retval #kStatus_Success The transaction was started successfully.
1192  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1193  *      transaction is already in progress.
1194  */
PF5020_SWND1_SetGlobalConfig(pf5020_handle_t * handle,const pf5020_swnd1_regulator_config_t * config)1195 status_t PF5020_SWND1_SetGlobalConfig(pf5020_handle_t *handle, const pf5020_swnd1_regulator_config_t *config)
1196 {
1197     assert(handle);
1198     assert(config);
1199 
1200     status_t status       = kStatus_Success;
1201     uint8_t value         = 0U;
1202     uint8_t mask          = 0U;
1203     bool enableILIMBypass = true;
1204 
1205     /* Set output voltage in run/standby state. */
1206     status = PF5020_WriteReg(handle, PF5020_SWND1_RUN_VOLT, (uint8_t)(config->swnd1OutputVolt));
1207 
1208     if (status == kStatus_Success)
1209     {
1210         /* Set SWND1 operate mode in run/standby state. */
1211         status = PF5020_ModifyReg(handle, PF5020_SWND1_MODE1,
1212                                   PF5020_BUCK_REGULATOR_RUN_MODE_MASK | PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK,
1213                                   PF5020_BUCK_REGULATOR_RUN_MODE(config->swnd1RunOperateMode) |
1214                                       PF5020_BUCK_REGULATOR_STANDBY_MODE(config->swnd1StandbyOperateMode));
1215     }
1216 
1217     if (status == kStatus_Success)
1218     {
1219         if (config->swnd1CurrentLimit != kPF5020_BuckRegulatorCurrentLimitBypass)
1220         {
1221             enableILIMBypass = false;
1222             value |= PF5020_BUCK_REGULATOR_ILIM(config->swnd1CurrentLimit);
1223             mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
1224         }
1225         status = PF5020_SetRegulatorCommonConfig(handle, kPF5020_BuckRegulatorSwnd1, config->swnd1EnableUVBypass,
1226                                                  config->swnd1EnableOVBypass, config->swnd1EnableWatchdogBypass,
1227                                                  config->swnd1EnablePGMonitor, config->swnd1FaultReEnabled,
1228                                                  enableILIMBypass);
1229 
1230         if (status == kStatus_Success)
1231         {
1232             value |= PF5020_BUCK_REGULATOR_PHASE(config->swnd1PhaseShift);
1233             mask |= PF5020_BUCK_REGULATOR_PHASE_MASK;
1234             /* Update SWND1 CONFIG2 register, this register can be used to set current limitation and phase shift. */
1235             status = PF5020_ModifyReg(handle, PF5020_SWND1_CONFIG2, mask, value);
1236         }
1237     }
1238 
1239     return status;
1240 }
1241 
1242 /*!
1243  * brief Set run/standby output voltage for SWND1 regulator.
1244  *
1245  * param handle The pointer to pf5020_handle_t structure.
1246  * param outputVolt The output voltage of SWND1 regulator in run/standby state,
1247  *                  please refer to pf5020_swnd1_output_voltage_t for details.
1248  * retval #kStatus_Success The transaction was started successfully.
1249  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1250  *      transaction is already in progress.
1251  */
PF5020_SWND1_SetOutputVoltage(pf5020_handle_t * handle,pf5020_swnd1_output_voltage_t outputVolt)1252 status_t PF5020_SWND1_SetOutputVoltage(pf5020_handle_t *handle, pf5020_swnd1_output_voltage_t outputVolt)
1253 {
1254     assert(handle);
1255 
1256     uint8_t swnd1Volt;
1257     status_t status = kStatus_Success;
1258 
1259     (void)PF5020_ReadReg(handle, PF5020_SWND1_RUN_VOLT, &swnd1Volt);
1260 
1261     if (swnd1Volt != (uint8_t)outputVolt)
1262     {
1263         status = PF5020_WriteReg(handle, PF5020_SWND1_RUN_VOLT, (uint8_t)outputVolt);
1264     }
1265 
1266     return status;
1267 }
1268 
1269 /*!
1270  * brief Set SWND1 regulator's operate mode in run and standby state.
1271  *
1272  * param handle The pointer to pf5020_handle_t structure.
1273  * param runOperateMode The operate mode of SWND1 in run state, please refer to pf5020_buck_regulator_operate_mode_t.
1274  * param standbyOperateMode The operate mode of SWND1 in standby state, please refer to
1275  * pf5020_buck_regulator_operate_mode_t. retval #kStatus_Success The transaction was started successfully. retval
1276  * #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking transaction is already in
1277  * progress.
1278  */
PF5020_SWND1_SetOperateMode(pf5020_handle_t * handle,pf5020_buck_regulator_operate_mode_t runOperateMode,pf5020_buck_regulator_operate_mode_t standbyOperateMode)1279 status_t PF5020_SWND1_SetOperateMode(pf5020_handle_t *handle,
1280                                      pf5020_buck_regulator_operate_mode_t runOperateMode,
1281                                      pf5020_buck_regulator_operate_mode_t standbyOperateMode)
1282 {
1283     assert(handle);
1284 
1285     uint8_t tmp8;
1286     uint8_t swnd1RunMode;
1287     uint8_t swnd1StandbyMode;
1288     status_t status;
1289 
1290     (void)PF5020_ReadReg(handle, PF5020_SWND1_MODE1, &tmp8);
1291 
1292     swnd1RunMode     = (tmp8 & PF5020_BUCK_REGULATOR_RUN_MODE_MASK);
1293     swnd1StandbyMode = ((tmp8 & PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK) >> PF5020_BUCK_REGULATOR_STANDBY_MODE_SHIFT);
1294 
1295     if (swnd1RunMode != (uint8_t)runOperateMode)
1296     {
1297         tmp8 = ((tmp8 & (uint8_t)(~PF5020_BUCK_REGULATOR_RUN_MODE_MASK)) | PF5020_BUCK_REGULATOR_RUN_MODE(runOperateMode));
1298     }
1299 
1300     if (swnd1StandbyMode != (uint8_t)standbyOperateMode)
1301     {
1302         tmp8 = ((tmp8 & (uint8_t)(~PF5020_BUCK_REGULATOR_STANDBY_MODE_MASK)) |
1303                PF5020_BUCK_REGULATOR_STANDBY_MODE(standbyOperateMode));
1304     }
1305 
1306     status = PF5020_WriteReg(handle, PF5020_SWND1_MODE1, tmp8);
1307 
1308     return status;
1309 }
1310 
1311 /*!
1312  * brief Set SWND1 regulator phase shift value.
1313  *
1314  * param handle The pointer to pf5020_handle_t structure.
1315  * param phaseShift SWND1 buck regulator phase shift value, please refer to pf5020_buck_regulator_phase_shift_t
1316  *                   for details.
1317  * retval #kStatus_Success The transaction was started successfully.
1318  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1319  *      transaction is already in progress.
1320  */
PF5020_SWND1_SetPhaseShift(pf5020_handle_t * handle,pf5020_buck_regulator_phase_shift_t phaseShift)1321 status_t PF5020_SWND1_SetPhaseShift(pf5020_handle_t *handle, pf5020_buck_regulator_phase_shift_t phaseShift)
1322 {
1323     assert(handle);
1324 
1325     status_t status = kStatus_Success;
1326     uint8_t swnd1Phase;
1327 
1328     (void)PF5020_ReadReg(handle, PF5020_SWND1_CONFIG2, &swnd1Phase);
1329     swnd1Phase &= PF5020_BUCK_REGULATOR_PHASE_MASK;
1330     swnd1Phase = swnd1Phase >> PF5020_BUCK_REGULATOR_PHASE_SHIFT;
1331 
1332     if (swnd1Phase != (uint8_t)phaseShift)
1333     {
1334         status = PF5020_ModifyReg(handle, PF5020_SWND1_CONFIG2, PF5020_BUCK_REGULATOR_PHASE_MASK,
1335                                   PF5020_BUCK_REGULATOR_PHASE(phaseShift));
1336     }
1337 
1338     return status;
1339 }
1340 
1341 /*!
1342  * brief Set SWND1 regulator fault detection related options.
1343  *
1344  * param handle The pointer to pf5020_handle_t structure.
1345  * param currentLimit SWND1 buck regulator current limitation value, please refer to
1346  *                      pf5020_buck_regulator_current_limit_t for details.
1347  * param enableUVBypass Enable/disable UV bypass.
1348  * param enableOVBypass Enable/disable OV bypass.
1349  * param faultReEnabled Used to control whether return to sw1 regulator previous state if fault condition is cleared.
1350  * retval #kStatus_Success The transaction was started successfully.
1351  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1352  *      transaction is already in progress.
1353  */
PF5020_SWND1_SetFaultDetection(pf5020_handle_t * handle,pf5020_buck_regulator_current_limit_t currentLimit,bool enableUVBypass,bool enableOVBypass,bool faultReEnabled)1354 status_t PF5020_SWND1_SetFaultDetection(pf5020_handle_t *handle,
1355                                         pf5020_buck_regulator_current_limit_t currentLimit,
1356                                         bool enableUVBypass,
1357                                         bool enableOVBypass,
1358                                         bool faultReEnabled)
1359 {
1360     assert(handle);
1361 
1362     status_t status;
1363     bool enableILIMBypass     = false;
1364     uint8_t swnd1Config2Mask  = 0U;
1365     uint8_t swnd1Config2Value = 0U;
1366 
1367     if (currentLimit == kPF5020_BuckRegulatorCurrentLimitBypass)
1368     {
1369         enableILIMBypass = true;
1370     }
1371     else
1372     {
1373         swnd1Config2Mask |= PF5020_BUCK_REGULATOR_ILIM_MASK;
1374         swnd1Config2Value |= PF5020_BUCK_REGULATOR_ILIM(currentLimit);
1375     }
1376 
1377     swnd1Config2Mask |= PF5020_REGULATOR_FLT_REN_MASK;
1378     swnd1Config2Value |= PF5020_REGULATOR_FLT_REN(faultReEnabled);
1379     status = PF5020_ModifyReg(handle, PF5020_SWND1_CONFIG2, swnd1Config2Mask, swnd1Config2Value);
1380 
1381     if (status == kStatus_Success)
1382     {
1383         status = PF5020_ModifyReg(
1384             handle, PF5020_SWND1_CONFIG1,
1385             PF5020_REGULATOR_ILIM_BYPASS_MASK | PF5020_REGULATOR_OV_BYPASS_MASK | PF5020_REGULATOR_UV_BYPASS_MASK,
1386             PF5020_REGULATOR_ILIM_BYPASS(enableILIMBypass) | PF5020_REGULATOR_OV_BYPASS(enableOVBypass) |
1387                 PF5020_REGULATOR_UV_BYPASS(enableUVBypass));
1388     }
1389 
1390     return status;
1391 }
1392 
1393 /*!
1394  * brief Enable/disable PG monitor for SWND1 regulator.
1395  *
1396  * param handle The pointer to pf5020_handle_t structure.
1397  * param enable Enable/disable PG monitor.
1398  * retval #kStatus_Success The transaction was started successfully.
1399  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1400  *      transaction is already in progress.
1401  */
PF5020_SWND1_EnablePGMonitor(pf5020_handle_t * handle,bool enable)1402 status_t PF5020_SWND1_EnablePGMonitor(pf5020_handle_t *handle, bool enable)
1403 {
1404     assert(handle);
1405 
1406     return PF5020_ModifyReg(handle, PF5020_SWND1_CONFIG1, PF5020_REGULATOR_PG_EN_MASK, PF5020_REGULATOR_PG_EN(enable));
1407 }
1408 
1409 /*!
1410  * brief Enable/disable watchdog bypass for SW1 regulator.
1411  *
1412  * param handle The pointer to pf5020_handle_t structure.
1413  * param enable Enable/disable watchdog bypass.
1414  * retval #kStatus_Success The transaction was started successfully.
1415  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1416  *      transaction is already in progress.
1417  */
PF5020_SWND1_EnableWatchDogBypass(pf5020_handle_t * handle,bool enable)1418 status_t PF5020_SWND1_EnableWatchDogBypass(pf5020_handle_t *handle, bool enable)
1419 {
1420     assert(handle);
1421 
1422     return PF5020_ModifyReg(handle, PF5020_SWND1_CONFIG1, PF5020_REGULATOR_WDBYPASS_MASK,
1423                             PF5020_REGULATOR_WDBYPASS(enable));
1424 }
1425 
1426 /*!
1427  * brief Set LDO1 global configuration.
1428  *
1429  * param handle The pointer to pf5020_handle_t structure.
1430  * param config The pointer to pf5020_ldo1_regulator_config structure.
1431  * retval #kStatus_Success The transaction was started successfully.
1432  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1433  *      transaction is already in progress.
1434  */
PF5020_LDO1_SetGlobalConfig(pf5020_handle_t * handle,const pf5020_ldo1_regulator_config * config)1435 status_t PF5020_LDO1_SetGlobalConfig(pf5020_handle_t *handle, const pf5020_ldo1_regulator_config *config)
1436 {
1437     assert(handle);
1438     assert(config);
1439 
1440     status_t status = kStatus_Success;
1441 
1442     /* Set LDO1 output voltage in run state. */
1443     status = PF5020_WriteReg(handle, PF5020_LDO1_RUN_VOLT, (uint8_t)(config->ldo1RunOutputVolt));
1444 
1445     if (status == kStatus_Success)
1446     {
1447         /* Set LDO1 output voltage in standby state. */
1448         status = PF5020_WriteReg(handle, PF5020_LDO1_STBY_VOLT, (uint8_t)(config->ldo1StandbyOutputVolt));
1449     }
1450 
1451     if (status == kStatus_Success)
1452     {
1453         status = PF5020_ModifyReg(
1454             handle, PF5020_LDO1_CONFIG2, PF5020_LDO1_CONFIG2_RUN_EN_MASK | PF5020_LDO1_CONFIG2_STBY_EN_MASK,
1455             PF5020_LDO1_CONFIG2_STBY_EN(config->ldo1StandbyEnable) | PF5020_LDO1_CONFIG2_RUN_EN(config->ldo1RunEnable));
1456     }
1457 
1458     if (status == kStatus_Success)
1459     {
1460         status = PF5020_SetRegulatorCommonConfig(handle, kPF5020_RegulatorLdo1, config->ldo1EnableUVBypass,
1461                                                  config->ldo1EnableOVBypass, config->ldo1EnableWatchdogBypass,
1462                                                  config->ldo1EnablePGMonitor, config->ldo1FaultReEnabled,
1463                                                  config->ldo1EnableILIMBypass);
1464     }
1465 
1466     return status;
1467 }
1468 
1469 /*!
1470  * brief Set LDO1 regulator's output voltage and operate mode in run state.
1471  *
1472  * param handle The pointer to pf5020_handle_t structure.
1473  * param runEnable Enable/disable LDO1 in run state.
1474  * param runOuputVolt The output voltage of LDO1 in run state, please refer to pf5020_ldo1_output_voltage_t.
1475  * retval #kStatus_Success The transaction was started successfully.
1476  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1477  *      transaction is already in progress.
1478  */
PF5020_LDO1_SetRunStateOption(pf5020_handle_t * handle,bool runEnable,pf5020_ldo1_output_voltage_t runOuputVolt)1479 status_t PF5020_LDO1_SetRunStateOption(pf5020_handle_t *handle,
1480                                        bool runEnable,
1481                                        pf5020_ldo1_output_voltage_t runOuputVolt)
1482 {
1483     assert(handle);
1484 
1485     status_t status;
1486 
1487     if (runEnable)
1488     {
1489         status = PF5020_WriteReg(handle, PF5020_LDO1_RUN_VOLT, (uint8_t)runOuputVolt);
1490     }
1491     else
1492     {
1493         status = PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG2, PF5020_LDO1_CONFIG2_RUN_EN_MASK,
1494                                   PF5020_LDO1_CONFIG2_RUN_EN(runEnable));
1495     }
1496 
1497     return status;
1498 }
1499 
1500 /*!
1501  * brief Set LDO1 regulator's output voltage and operate mode in standby state.
1502  *
1503  * param handle The pointer to pf5020_handle_t structure.
1504  * param standbyEnable Enable/disable LDO1 in standby state.
1505  * param standbyOuputVolt The output voltage of LDO1 in standby state, please refer to pf5020_ldo1_output_voltage_t.
1506  * retval #kStatus_Success The transaction was started successfully.
1507  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1508  *      transaction is already in progress.
1509  */
PF5020_LDO1_SetStandbyStateOption(pf5020_handle_t * handle,bool standbyEnable,pf5020_ldo1_output_voltage_t standbyOuputVolt)1510 status_t PF5020_LDO1_SetStandbyStateOption(pf5020_handle_t *handle,
1511                                            bool standbyEnable,
1512                                            pf5020_ldo1_output_voltage_t standbyOuputVolt)
1513 {
1514     assert(handle);
1515 
1516     status_t status;
1517 
1518     if (standbyEnable)
1519     {
1520         status = PF5020_WriteReg(handle, PF5020_LDO1_STBY_VOLT, (uint8_t)standbyOuputVolt);
1521     }
1522     else
1523     {
1524         status = PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG2, PF5020_LDO1_CONFIG2_STBY_EN_MASK,
1525                                   PF5020_LDO1_CONFIG2_STBY_EN(standbyEnable));
1526     }
1527 
1528     return status;
1529 }
1530 
1531 /*!
1532  * brief Set SWND1 regulator fault detection related options.
1533  *
1534  * param handle The pointer to pf5020_handle_t structure.
1535  * param enableILIMBypass Enable/disable ILIM bypass.
1536  * param enableUVBypass Enable/disable UV bypass.
1537  * param enableOVBypass Enable/disable OV bypass.
1538  * param faultReEnabled Used to control whether return to ldos1 regulator previous state if fault condition is cleared.
1539  * retval #kStatus_Success The transaction was started successfully.
1540  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1541  *      transaction is already in progress.
1542  */
PF5020_LDO1_SetFaultDetection(pf5020_handle_t * handle,bool enableILIMBypass,bool enableUVBypass,bool enableOVBypass,bool faultReEnabled)1543 status_t PF5020_LDO1_SetFaultDetection(
1544     pf5020_handle_t *handle, bool enableILIMBypass, bool enableUVBypass, bool enableOVBypass, bool faultReEnabled)
1545 {
1546     assert(handle);
1547 
1548     status_t status;
1549 
1550     status = PF5020_ModifyReg(
1551         handle, PF5020_LDO1_CONFIG1,
1552         PF5020_REGULATOR_ILIM_BYPASS_MASK | PF5020_REGULATOR_OV_BYPASS_MASK | PF5020_REGULATOR_UV_BYPASS_MASK,
1553         PF5020_REGULATOR_ILIM_BYPASS(enableILIMBypass) | PF5020_REGULATOR_OV_BYPASS(enableOVBypass) |
1554             PF5020_REGULATOR_UV_BYPASS(enableUVBypass));
1555 
1556     if (status == kStatus_Success)
1557     {
1558         status = PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG2, PF5020_REGULATOR_FLT_REN_MASK,
1559                                   PF5020_REGULATOR_FLT_REN(faultReEnabled));
1560     }
1561 
1562     return status;
1563 }
1564 
1565 /*!
1566  * brief Enable/disable PG monitor for LDO1 regulator.
1567  *
1568  * param handle The pointer to pf5020_handle_t structure.
1569  * param enable Enable/disable PG monitor.
1570  * retval #kStatus_Success The transaction was started successfully.
1571  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1572  *      transaction is already in progress.
1573  */
PF5020_LDO1_EnablePGMonitor(pf5020_handle_t * handle,bool enable)1574 status_t PF5020_LDO1_EnablePGMonitor(pf5020_handle_t *handle, bool enable)
1575 {
1576     assert(handle);
1577 
1578     return PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG1, PF5020_REGULATOR_PG_EN_MASK, PF5020_REGULATOR_PG_EN(enable));
1579 }
1580 
1581 /*!
1582  * brief Enable/disable watchdog bypass for LDO1 regulator.
1583  *
1584  * param handle The pointer to pf5020_handle_t structure.
1585  * param enable Enable/disable watchdog bypass.
1586  * retval #kStatus_Success The transaction was started successfully.
1587  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1588  *      transaction is already in progress.
1589  */
PF5020_LDO1_EnableWatchDogBypass(pf5020_handle_t * handle,bool enable)1590 status_t PF5020_LDO1_EnableWatchDogBypass(pf5020_handle_t *handle, bool enable)
1591 {
1592     assert(handle);
1593 
1594     return PF5020_ModifyReg(handle, PF5020_LDO1_CONFIG1, PF5020_REGULATOR_WDBYPASS_MASK,
1595                             PF5020_REGULATOR_WDBYPASS(enable));
1596 }
1597 
1598 /*!
1599  * brief Set voltage monitor debounce time.
1600  *
1601  * param handle The pointer to pf5020_handle_t structure.
1602  * param uvDebounceTime UV monitor debounce time, please refer to pf5020_uv_debounce_time_t.
1603  * param ovDebounceTime OV monitor debounce time, please refer to pf5020_ov_debounce_time_t.
1604  * retval #kStatus_Success The transaction was started successfully.
1605  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1606  *      transaction is already in progress.
1607  */
PF5020_SetVoltageMonitorDebounceTime(pf5020_handle_t * handle,pf5020_uv_debounce_time_t uvDebounceTime,pf5020_ov_debounce_time_t ovDebounceTime)1608 status_t PF5020_SetVoltageMonitorDebounceTime(pf5020_handle_t *handle,
1609                                               pf5020_uv_debounce_time_t uvDebounceTime,
1610                                               pf5020_ov_debounce_time_t ovDebounceTime)
1611 {
1612     assert(handle);
1613 
1614     return PF5020_ModifyReg(handle, PF5020_CTRL3, PF5020_CTRL3_UV_DB_MASK | PF5020_CTRL3_OV_DB_MASK,
1615                             PF5020_CTRL3_UV_DB(uvDebounceTime) | PF5020_CTRL3_OV_DB(ovDebounceTime));
1616 }
1617 
1618 /*!
1619  * brief Enable/disable selected regulator's voltage monitor.
1620  *
1621  * param handle The pointer to pf5020_handle_t structure.
1622  * param name The regulator to be set.
1623  * param enable Enable/disable voltage monitor.
1624  * retval #kStatus_Success The transaction was started successfully.
1625  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1626  *      transaction is already in progress.
1627  */
PF5020_EnableVoltageMonitor(pf5020_handle_t * handle,pf5020_regulator_name_t name,bool enable)1628 status_t PF5020_EnableVoltageMonitor(pf5020_handle_t *handle, pf5020_regulator_name_t name, bool enable)
1629 {
1630     assert(handle);
1631 
1632     status_t status = kStatus_Success;
1633 
1634     switch (name)
1635     {
1636         case kPF5020_BuckRegulatorSw1:
1637         {
1638             status = PF5020_ModifyReg(handle, PF5020_VMONEN1, PF5020_VMONEN1_SW1VMON_EN_MASK,
1639                                       PF5020_VMONEN1_SW1VMON_EN(enable));
1640             break;
1641         }
1642         case kPF5020_BuckRegulatorSw2:
1643         {
1644             status = PF5020_ModifyReg(handle, PF5020_VMONEN1, PF5020_VMONEN1_SW2VMON_EN_MASK,
1645                                       PF5020_VMONEN1_SW2VMON_EN(enable));
1646             break;
1647         }
1648         case kPF5020_BuckRegulatorSwnd1:
1649         {
1650             status = PF5020_ModifyReg(handle, PF5020_VMONEN1, PF5020_VMONEN1_SWND1VMON_EN_MASK,
1651                                       PF5020_VMONEN1_SWND1VMON_EN(enable));
1652             break;
1653         }
1654         case kPF5020_RegulatorLdo1:
1655         {
1656             status = PF5020_ModifyReg(handle, PF5020_VMONEN2, PF5020_VMONEN2_LDO1VMON_EN_MASK,
1657                                       PF5020_VMONEN2_LDO1VMON_EN(enable));
1658             break;
1659         }
1660         default:
1661         {
1662             assert(false);
1663             break;
1664         }
1665     }
1666 
1667     return status;
1668 }
1669 
1670 /*!
1671  * brief Set fault counter maximum value.
1672  *
1673  * param handle Pointer to the pf5020_handle_t structure.
1674  * param maxValue Ranges from 0 to 15.
1675  * retval #kStatus_Success The transaction was started successfully.
1676  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1677  *      transaction is already in progress.
1678  */
PF5020_SetFaultCounterMaxValue(pf5020_handle_t * handle,uint8_t maxValue)1679 status_t PF5020_SetFaultCounterMaxValue(pf5020_handle_t *handle, uint8_t maxValue)
1680 {
1681     assert(handle);
1682 
1683     return PF5020_ModifyReg(handle, PF5020_FAULT_COUNTER, 0xF0U, ((maxValue << 4U) & 0xF0U));
1684 }
1685 
1686 /*!
1687  * brief Get fault counter current value.
1688  *
1689  * param handle The pointer to pf5020_handle_t structure.
1690  * retval #kStatus_Success The transaction was started successfully.
1691  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1692  *      transaction is already in progress.
1693  */
PF5020_GetFaultCounterCurrentValue(pf5020_handle_t * handle)1694 uint8_t PF5020_GetFaultCounterCurrentValue(pf5020_handle_t *handle)
1695 {
1696     assert(handle);
1697 
1698     uint8_t tmp8;
1699 
1700     (void)PF5020_ReadReg(handle, PF5020_FAULT_COUNTER, &tmp8);
1701     tmp8 = tmp8 & 0x0FU;
1702 
1703     return tmp8;
1704 }
1705 
1706 /*!
1707  * brief Set the expire value of the fault timer, when a regulator experiences a fault event, a fault timer will start.
1708  *
1709  * param handle Pointer to the pf5020_handle_t structure.
1710  * param expireValue The expire value of fault timer, ranges from 0 to 11, the actual expire time = 2 ^ expireValue.
1711  *
1712  * retval #kStatus_Success The transaction was started successfully.
1713  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1714  *      transaction is already in progress.
1715  */
PF5020_SetFaultTimerExpireValue(pf5020_handle_t * handle,uint8_t expireValue)1716 status_t PF5020_SetFaultTimerExpireValue(pf5020_handle_t *handle, uint8_t expireValue)
1717 {
1718     assert(handle);
1719 
1720     return PF5020_ModifyReg(handle, PF5020_FAULT_TIMERS, 0x0FU, (expireValue & 0x0FU));
1721 }
1722 
1723 /*!
1724  * brief Set reset behaviour asserted by WDI.
1725  *
1726  * param handle The pointer to pf5020_handle_t structure.
1727  * param wdiMode Used to control the WDI asserted performs a hard WD reset or soft WD reset.
1728  * retval #kStatus_Success The transaction was started successfully.
1729  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1730  *      transaction is already in progress.
1731  */
PF5020_WDOG_SetWDIMode(pf5020_handle_t * handle,pf5020_wdi_mode_t wdiMode)1732 status_t PF5020_WDOG_SetWDIMode(pf5020_handle_t *handle, pf5020_wdi_mode_t wdiMode)
1733 {
1734     assert(handle);
1735 
1736     return PF5020_ModifyReg(handle, PF5020_CTRL1, 0x20U, (((uint8_t)wdiMode << 5U) & 0x20U));
1737 }
1738 
1739 /*!
1740  * brief Enable/disable WDI watchdog event in standby state.
1741  *
1742  * param handle The pointer to pf5020_handle_t structure.
1743  * param enable Used to control whether generate a watchdog event in standby mode if the WDI is asserted.
1744  * retval #kStatus_Success The transaction was started successfully.
1745  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1746  *      transaction is already in progress.
1747  */
PF5020_WDOG_EnableWDIStanby(pf5020_handle_t * handle,bool enable)1748 status_t PF5020_WDOG_EnableWDIStanby(pf5020_handle_t *handle, bool enable)
1749 {
1750     assert(handle);
1751 
1752     return PF5020_ModifyReg(handle, PF5020_CTRL1, 0x2U, (((uint8_t)enable << 1U) & 0x2U));
1753 }
1754 
1755 /*!
1756  * brief Configure internal watchdog timer.
1757  *
1758  * param handle The pointer to pf5020_handle_t structure.
1759  * param config Pointer to pf5020_wdog_internal_timer_config_t structure.
1760  * retval #kStatus_Success The transaction was started successfully.
1761  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1762  *      transaction is already in progress.
1763  */
PF5020_WDOG_ConfigInternalTimer(pf5020_handle_t * handle,const pf5020_wdog_internal_timer_config_t * config)1764 status_t PF5020_WDOG_ConfigInternalTimer(pf5020_handle_t *handle, const pf5020_wdog_internal_timer_config_t *config)
1765 {
1766     assert(handle);
1767     assert(config);
1768 
1769     status_t status;
1770 
1771     status = PF5020_WriteReg(handle, PF5020_WD_CONFIG, config->timerDuration);
1772 
1773     if (status == kStatus_Success)
1774     {
1775         status = PF5020_ModifyReg(handle, PF5020_WD_EXPIRE, 0x70U, ((config->cyclicCounterMaxVale << 4U) & 0x70U));
1776     }
1777 
1778     if (status == kStatus_Success)
1779     {
1780         status = PF5020_ModifyReg(handle, PF5020_CTRL1, PF5020_CTRL1_WD_EN_MASK | PF5020_CTRL1_WD_STBY_EN_MASK,
1781                                   PF5020_CTRL1_WD_STBY_EN(config->enableStandby) | PF5020_CTRL1_WD_EN(config->enable));
1782     }
1783 
1784     return status;
1785 }
1786 
1787 /*!
1788  * brief Get cyclic counter current value.
1789  *
1790  * param handle The pointer to pf5020_handle_t structure.
1791  * return Current cyclic counter value.
1792  */
PF5020_WDOG_GetCyclicCounterValue(pf5020_handle_t * handle)1793 uint8_t PF5020_WDOG_GetCyclicCounterValue(pf5020_handle_t *handle)
1794 {
1795     assert(handle);
1796 
1797     uint8_t tmp8;
1798 
1799     (void)PF5020_ReadReg(handle, PF5020_WD_EXPIRE, &tmp8);
1800     tmp8 &= 0x7U;
1801 
1802     return tmp8;
1803 }
1804 
1805 /*!
1806  * brief Refresh internal watchdog timer.
1807  *
1808  * param handle The pointer to pf5020_handle_t structure.
1809  * retval #kStatus_Success The transaction was started successfully.
1810  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1811  *      transaction is already in progress.
1812  */
PF5020_WDOG_RefreshInternalTimer(pf5020_handle_t * handle)1813 status_t PF5020_WDOG_RefreshInternalTimer(pf5020_handle_t *handle)
1814 {
1815     assert(handle);
1816 
1817     return PF5020_WriteReg(handle, PF5020_WD_CLEAR, 0x1U);
1818 }
1819 
1820 /*!
1821  * brief Set watchdog event counter maximum value.
1822  *
1823  * param handle The pointer to pf5020_handle_t structure.
1824  * param maxValue The maximum value of watchdog event counter.
1825  * retval #kStatus_Success The transaction was started successfully.
1826  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1827  *      transaction is already in progress.
1828  */
PF5020_WDOG_SetWDEventCounterMaxValue(pf5020_handle_t * handle,uint8_t maxValue)1829 status_t PF5020_WDOG_SetWDEventCounterMaxValue(pf5020_handle_t *handle, uint8_t maxValue)
1830 {
1831     assert(handle);
1832 
1833     return PF5020_ModifyReg(handle, PF5020_WD_COUNTER, 0xF0U, ((maxValue << 4U) & 0xF0U));
1834 }
1835 
1836 /*!
1837  * brief Get watchdog event counter current value.
1838  *
1839  * param handle The pointer to pf5020_handle_t structure.
1840  * return Watch dog event counter current value.
1841  */
PF5020_WDOG_GetWDEventCounterCurrentValue(pf5020_handle_t * handle)1842 uint8_t PF5020_WDOG_GetWDEventCounterCurrentValue(pf5020_handle_t *handle)
1843 {
1844     assert(handle);
1845 
1846     uint8_t tmp8;
1847 
1848     (void)PF5020_ReadReg(handle, PF5020_WD_COUNTER, &tmp8);
1849     tmp8 &= 0xFU;
1850 
1851     return tmp8;
1852 }
1853 
1854 /*!
1855  * brief Configure internal thermal monitor.
1856  *
1857  * param handle The pointer to pf5020_handle_t structure.
1858  * param enable Enable/disable temperature sensor circuit.
1859  * param mode Used to set temperature sensor operate mode, please refer to pf5020_temp_sensor_operate_mode_t.
1860  * retval #kStatus_Success The transaction was started successfully.
1861  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1862  *      transaction is already in progress.
1863  */
PF5020_TMP_SetThermalMonitorConfig(pf5020_handle_t * handle,bool enable,pf5020_temp_sensor_operate_mode_t mode)1864 status_t PF5020_TMP_SetThermalMonitorConfig(pf5020_handle_t *handle,
1865                                             bool enable,
1866                                             pf5020_temp_sensor_operate_mode_t mode)
1867 {
1868     assert(handle);
1869 
1870     status_t status;
1871 
1872     status = PF5020_ModifyReg(handle, PF5020_CTRL1, PF5020_CTRL1_TMP_MON_EN_MASK, PF5020_CTRL1_TMP_MON_EN(enable));
1873 
1874     if (status == kStatus_Success)
1875     {
1876         status = PF5020_ModifyReg(handle, PF5020_CTRL2, PF5020_CTRL2_TMP_MON_AON_MASK, PF5020_CTRL2_TMP_MON_AON(mode));
1877     }
1878 
1879     return status;
1880 }
1881 
1882 /*!
1883  * brief Configure analog multiplexer.
1884  *
1885  * param handle The pointer to pf5020_handle_t structure.
1886  * param enable Enable/disable analog multiplexer.
1887  * param amuxSel Used to select amux output, please refer to pf5020_amux_selection_t
1888  * retval #kStatus_Success The transaction was started successfully.
1889  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1890  *      transaction is already in progress.
1891  */
PF5020_AMUX_SetAnalogMuxConfig(pf5020_handle_t * handle,bool enable,pf5020_amux_selection_t amuxSel)1892 status_t PF5020_AMUX_SetAnalogMuxConfig(pf5020_handle_t *handle, bool enable, pf5020_amux_selection_t amuxSel)
1893 {
1894     assert(handle);
1895 
1896     return PF5020_ModifyReg(handle, PF5020_AMUX, PF5020_AMUX_AMUX_SEL_MASK | PF5020_AMUX_AMUX_EN_MASK,
1897                             PF5020_AMUX_MAUX_SEL(amuxSel) | PF5020_AMUX_AMUX_EN(enable));
1898 }
1899 
1900 /*!
1901  * brief Enable interrupts.
1902  *
1903  * param handle The pointer to pf5020_handle_t structure.
1904  * param interruptMask The mask of interrupts to clear, should be the OR'ed value of pf5020_interrupt_t.
1905  * retval #kStatus_Success The transaction was started successfully.
1906  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1907  *      transaction is already in progress.
1908  */
PF5020_EnableInterrupts(pf5020_handle_t * handle,uint64_t interruptMask)1909 status_t PF5020_EnableInterrupts(pf5020_handle_t *handle, uint64_t interruptMask)
1910 {
1911     assert(handle);
1912 
1913     return PF5020_MaskInterrupts(handle, interruptMask, true);
1914 }
1915 
1916 /*!
1917  * brief Disable Interrupts.
1918  *
1919  * param handle The pointer to pf5020_handle_t structure.
1920  * param interruptMask The mask of interrupts to clear, should be the OR'ed value of pf5020_interrupt_t.
1921  * retval #kStatus_Success The transaction was started successfully.
1922  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1923  *      transaction is already in progress.
1924  */
PF5020_DisableInterrupts(pf5020_handle_t * handle,uint64_t interruptMask)1925 status_t PF5020_DisableInterrupts(pf5020_handle_t *handle, uint64_t interruptMask)
1926 {
1927     assert(handle);
1928 
1929     return PF5020_MaskInterrupts(handle, interruptMask, false);
1930 }
1931 
1932 /*!
1933  * brief Get latched interrupts.
1934  *
1935  * param handle The pointer to pf5020_handle_t structure.
1936  * param interrptLatched Pointer to store the latched interrupt value.
1937  * retval #kStatus_Success The transaction was started successfully.
1938  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
1939  *      transaction is already in progress.
1940  */
PF5020_GetInterruptLatchStatus(pf5020_handle_t * handle,uint64_t * interrptLatched)1941 status_t PF5020_GetInterruptLatchStatus(pf5020_handle_t *handle, uint64_t *interrptLatched)
1942 {
1943     assert(handle);
1944 
1945     static const uint8_t latchRegArray[] = PF5020_INT_LATCH_ARRAY;
1946     uint8_t sysIntStatus;
1947     status_t status;
1948     uint8_t i;
1949     uint8_t tmp8;
1950 
1951     /* Get first level interrupt latch value, if the bit in SYS_INT register is set, it means related second level
1952      * interrupts are latched in second level interrupt register.
1953      */
1954     status = PF5020_ReadReg(handle, PF5020_SYS_INT, &sysIntStatus);
1955 
1956     if (status == kStatus_Success)
1957     {
1958         for (i = 0U; i < 7U; i++)
1959         {
1960             /* If first level interrupt is set, then read related second level interrupt latch register. */
1961             if ((sysIntStatus & (1U << i)) != 0U)
1962             {
1963                 status = PF5020_ReadReg(handle, latchRegArray[i], &tmp8);
1964                 *interrptLatched |= ((uint64_t)tmp8 << (i * 8U));
1965 
1966                 if ((i == 3U) && (status == kStatus_Success))
1967                 {
1968                     status = PF5020_ReadReg(handle, PF5020_LDO_ILIM_INT, &tmp8);
1969                     if ((status == kStatus_Success) && (tmp8 != 0U))
1970                     {
1971                         *interrptLatched |= (uint64_t)kPF5020_ILIM_Ldo1IlimInterrupt;
1972                     }
1973                 }
1974 
1975                 if ((i == 4U) && (status == kStatus_Success))
1976                 {
1977                     status = PF5020_ReadReg(handle, PF5020_LDO_UV_INT, &tmp8);
1978                     if ((tmp8 != 0U) && (status == kStatus_Success))
1979                     {
1980                         *interrptLatched |= (uint64_t)kPF5020_UV_Ldo1UvInterrupt;
1981                     }
1982                 }
1983 
1984                 if ((i == 5U) && (status == kStatus_Success))
1985                 {
1986                     status = PF5020_ReadReg(handle, PF5020_LDO_OV_INT, &tmp8);
1987                     if ((tmp8 != 0U) && (status == kStatus_Success))
1988                     {
1989                         *interrptLatched |= (uint64_t)kPF5020_OV_Ldo1OvInterrupt;
1990                     }
1991                 }
1992             }
1993         }
1994     }
1995 
1996     return status;
1997 }
1998 
1999 /*!
2000  * brief Clear latched interrupts.
2001  *
2002  * param handle The pointer to pf5020_handle_t structure.
2003  * param interruptMask The mask of interrupts to clear, should be the OR'ed value of pf5020_interrupt_t.
2004  * retval #kStatus_Success The transaction was started successfully.
2005  * retval #kStatus_LPI2C_Busy Either another master is currently utilizing the bus, or a non-blocking
2006  *      transaction is already in progress.
2007  */
PF5020_ClearInterruptStatus(pf5020_handle_t * handle,uint64_t interruptMask)2008 status_t PF5020_ClearInterruptStatus(pf5020_handle_t *handle, uint64_t interruptMask)
2009 {
2010     assert(handle);
2011 
2012     static const uint8_t latchRegArray[] = PF5020_INT_LATCH_ARRAY;
2013     status_t status;
2014     uint8_t sysIntStatus;
2015     uint8_t i;
2016     uint8_t tmp8;
2017     uint64_t tmp64;
2018 
2019     /* Read SYS_INT register, it provides information about the interrupt register that originated the interrupt event.
2020      */
2021     status = PF5020_ReadReg(handle, PF5020_SYS_INT, &sysIntStatus);
2022 
2023     for (i = 0U; i < 7U; i++)
2024     {
2025         if ((sysIntStatus & (1U << i)) != 0U)
2026         {
2027             tmp64 = interruptMask & (0xFFULL << (8ULL * i));
2028             if ((tmp64 & (uint64_t)kPF5020_ILIM_Ldo1IlimInterrupt) != 0ULL)
2029             {
2030                 status = PF5020_WriteReg(handle, PF5020_LDO_ILIM_INT, 1U);
2031                 tmp64 &= (uint64_t)~kPF5020_ILIM_Ldo1IlimInterrupt;
2032             }
2033 
2034             if ((tmp64 & (uint64_t)kPF5020_UV_Ldo1UvInterrupt) != 0ULL)
2035             {
2036                 status = PF5020_WriteReg(handle, PF5020_LDO_UV_INT, 1U);
2037                 tmp64 &= (uint64_t)~kPF5020_UV_Ldo1UvInterrupt;
2038             }
2039 
2040             if ((tmp64 & (uint64_t)kPF5020_OV_Ldo1OvInterrupt) != 0ULL)
2041             {
2042                 status = PF5020_WriteReg(handle, PF5020_LDO_OV_INT, 1U);
2043                 tmp64 &= (uint64_t)~kPF5020_OV_Ldo1OvInterrupt;
2044             }
2045 
2046             tmp8 = (uint8_t)(tmp64 >> (8ULL * i)) & (0xFFU);
2047 
2048             if (status == kStatus_Success)
2049             {
2050                 status = PF5020_WriteReg(handle, latchRegArray[i], tmp8);
2051             }
2052         }
2053     }
2054 
2055     return status;
2056 }
2057