1 /********************************** (C) COPYRIGHT *******************************
2  * File Name          : ch32v10x_pwr.c
3  * Author             : WCH
4  * Version            : V1.0.0
5  * Date               : 2020/04/30
6  * Description        : This file provides all the PWR firmware functions.
7  * Copyright (c) 2021 Nanjing Qinheng Microelectronics Co., Ltd.
8  * SPDX-License-Identifier: Apache-2.0
9  ********************************************************************************/
10 #include "ch32v10x_pwr.h"
11 #include "ch32v10x_rcc.h"
12 
13 /* PWR registers bit mask */
14 /* CTLR register bit mask */
15 #define CTLR_DS_MASK     ((uint32_t)0xFFFFFFFC)
16 #define CTLR_PLS_MASK    ((uint32_t)0xFFFFFF1F)
17 
18 /*********************************************************************
19  * @fn      PWR_DeInit
20  *
21  * @brief   Deinitializes the PWR peripheral registers to their default
22  *        reset values.
23  *
24  * @return  none
25  */
PWR_DeInit(void)26 void PWR_DeInit(void)
27 {
28     RCC_APB1PeriphResetCmd(RCC_APB1Periph_PWR, ENABLE);
29     RCC_APB1PeriphResetCmd(RCC_APB1Periph_PWR, DISABLE);
30 }
31 
32 /*********************************************************************
33  * @fn      PWR_BackupAccessCmd
34  *
35  * @brief   Enables or disables access to the RTC and backup registers.
36  *
37  * @param   NewState - new state of the access to the RTC and backup registers,
38  *            This parameter can be: ENABLE or DISABLE.
39  *
40  * @return  none
41  */
PWR_BackupAccessCmd(FunctionalState NewState)42 void PWR_BackupAccessCmd(FunctionalState NewState)
43 {
44     if(NewState)
45     {
46         PWR->CTLR |= (1 << 8);
47     }
48     else
49     {
50         PWR->CTLR &= ~(1 << 8);
51     }
52 }
53 
54 /*********************************************************************
55  * @fn      PWR_PVDCmd
56  *
57  * @brief   Enables or disables the Power Voltage Detector(PVD).
58  *
59  * @param   NewState - new state of the PVD(ENABLE or DISABLE).
60  *
61  * @return  none
62  */
PWR_PVDCmd(FunctionalState NewState)63 void PWR_PVDCmd(FunctionalState NewState)
64 {
65     if(NewState)
66     {
67         PWR->CTLR |= (1 << 4);
68     }
69     else
70     {
71         PWR->CTLR &= ~(1 << 4);
72     }
73 }
74 
75 /*********************************************************************
76  * @fn      PWR_PVDLevelConfig
77  *
78  * @brief   Configures the voltage threshold detected by the Power Voltage
79  *        Detector(PVD).
80  *
81  * @param   PWR_PVDLevel - specifies the PVD detection level
82  *            PWR_PVDLevel_2V2 - PVD detection level set to 2.2V
83  *            PWR_PVDLevel_2V3 - PVD detection level set to 2.3V
84  *            PWR_PVDLevel_2V4 - PVD detection level set to 2.4V
85  *            PWR_PVDLevel_2V5 - PVD detection level set to 2.5V
86  *            PWR_PVDLevel_2V6 - PVD detection level set to 2.6V
87  *            PWR_PVDLevel_2V7 - PVD detection level set to 2.7V
88  *            PWR_PVDLevel_2V8 - PVD detection level set to 2.8V
89  *            PWR_PVDLevel_2V9 - PVD detection level set to 2.9V
90  *
91  * @return  none
92  */
PWR_PVDLevelConfig(uint32_t PWR_PVDLevel)93 void PWR_PVDLevelConfig(uint32_t PWR_PVDLevel)
94 {
95     uint32_t tmpreg = 0;
96     tmpreg = PWR->CTLR;
97     tmpreg &= CTLR_PLS_MASK;
98     tmpreg |= PWR_PVDLevel;
99     PWR->CTLR = tmpreg;
100 }
101 
102 /*********************************************************************
103  * @fn      PWR_WakeUpPinCmd
104  *
105  * @brief   Enables or disables the WakeUp Pin functionality.
106  *
107  * @param   NewState - new state of the WakeUp Pin functionality
108  *        (ENABLE or DISABLE).
109  *
110  * @return  none
111  */
PWR_WakeUpPinCmd(FunctionalState NewState)112 void PWR_WakeUpPinCmd(FunctionalState NewState)
113 {
114     if(NewState)
115     {
116         PWR->CSR |= (1 << 8);
117     }
118     else
119     {
120         PWR->CSR &= ~(1 << 8);
121     }
122 }
123 
124 /*********************************************************************
125  * @fn      PWR_EnterSTOPMode
126  *
127  * @brief   Enters STOP mode.
128  *
129  * @param   PWR_Regulator - specifies the regulator state in STOP mode.
130  *            PWR_Regulator_ON - STOP mode with regulator ON
131  *            PWR_Regulator_LowPower - STOP mode with regulator in low power mode
132  *          PWR_STOPEntry - specifies if STOP mode in entered with WFI or WFE instruction.
133  *            PWR_STOPEntry_WFI - enter STOP mode with WFI instruction
134  *            PWR_STOPEntry_WFE - enter STOP mode with WFE instruction
135  *
136  * @return  none
137  */
PWR_EnterSTOPMode(uint32_t PWR_Regulator,uint8_t PWR_STOPEntry)138 void PWR_EnterSTOPMode(uint32_t PWR_Regulator, uint8_t PWR_STOPEntry)
139 {
140     uint32_t tmpreg = 0;
141     tmpreg = PWR->CTLR;
142     tmpreg &= CTLR_DS_MASK;
143     tmpreg |= PWR_Regulator;
144     PWR->CTLR = tmpreg;
145 
146     NVIC->SCTLR |= (1 << 2);
147 
148     if(PWR_STOPEntry == PWR_STOPEntry_WFI)
149     {
150         __WFI();
151     }
152     else
153     {
154         __WFE();
155     }
156 
157     NVIC->SCTLR &= ~(1 << 2);
158 }
159 
160 /*********************************************************************
161  * @fn      PWR_EnterSTANDBYMode
162  *
163  * @brief   Enters STANDBY mode.
164  *
165  * @return  none
166  */
PWR_EnterSTANDBYMode(void)167 void PWR_EnterSTANDBYMode(void)
168 {
169     PWR->CTLR |= PWR_CTLR_CWUF;
170     PWR->CTLR |= PWR_CTLR_PDDS;
171     NVIC->SCTLR |= (1 << 2);
172 
173     __WFI();
174 }
175 
176 /*********************************************************************
177  * @fn      PWR_GetFlagStatus
178  *
179  * @brief   Checks whether the specified PWR flag is set or not.
180  *
181  * @param   PWR_FLAG - specifies the flag to check.
182  *            PWR_FLAG_WU - Wake Up flag
183  *            PWR_FLAG_SB - StandBy flag
184  *            PWR_FLAG_PVDO - PVD Output
185  *
186  * @return  The new state of PWR_FLAG (SET or RESET).
187  */
PWR_GetFlagStatus(uint32_t PWR_FLAG)188 FlagStatus PWR_GetFlagStatus(uint32_t PWR_FLAG)
189 {
190     FlagStatus bitstatus = RESET;
191 
192     if((PWR->CSR & PWR_FLAG) != (uint32_t)RESET)
193     {
194         bitstatus = SET;
195     }
196     else
197     {
198         bitstatus = RESET;
199     }
200     return bitstatus;
201 }
202 
203 /*********************************************************************
204  * @fn      PWR_ClearFlag
205  *
206  * @brief   Clears the PWR's pending flags.
207  *
208  * @param   PWR_FLAG - specifies the flag to clear.
209  *            PWR_FLAG_WU - Wake Up flag
210  *            PWR_FLAG_SB - StandBy flag
211  *
212  * @return  none
213  */
PWR_ClearFlag(uint32_t PWR_FLAG)214 void PWR_ClearFlag(uint32_t PWR_FLAG)
215 {
216     PWR->CTLR |= PWR_FLAG << 2;
217 }
218