1 /**************************************************************************//**
2  * @file     opa.h
3  * @version  V3.00
4  * @brief    M480 series OPA driver header file
5  *
6  * SPDX-License-Identifier: Apache-2.0
7  * @copyright (C) 2016-2020 Nuvoton Technology Corp. All rights reserved.
8  *****************************************************************************/
9 #ifndef __OPA_H__
10 #define __OPA_H__
11 
12 #ifdef __cplusplus
13 extern "C"
14 {
15 #endif
16 
17 
18 /** @addtogroup Standard_Driver Standard Driver
19   @{
20 */
21 
22 /** @addtogroup OPA_Driver OPA Driver
23   @{
24 */
25 
26 /** @addtogroup OPA_EXPORTED_CONSTANTS OPA Exported Constants
27   @{
28 */
29 #define OPA_CALIBRATION_CLK_1K                        (0UL)                     /*!< OPA calibration clock select 1 KHz  \hideinitializer */
30 #define OPA_CALIBRATION_RV_1_2_AVDD                   (0UL)                     /*!< OPA calibration reference voltage select 1/2 AVDD  \hideinitializer */
31 #define OPA_CALIBRATION_RV_H_L_VCM                    (1UL)                     /*!< OPA calibration reference voltage select from high vcm to low vcm \hideinitializer */
32 
33 /*@}*/ /* end of group OPA_EXPORTED_CONSTANTS */
34 
35 /** @addtogroup OPA_EXPORTED_FUNCTIONS OPA Exported Functions
36   @{
37 */
38 
39 /*---------------------------------------------------------------------------------------------------------*/
40 /* Define OPA functions prototype                                                                         */
41 /*---------------------------------------------------------------------------------------------------------*/
42 __STATIC_INLINE int32_t OPA_Calibration(OPA_T *opa, uint32_t u32OpaNum, uint32_t u32ClockSel, uint32_t u32LevelSel);
43 
44 /**
45   * @brief This macro is used to power on the OPA circuit
46   * @param[in] opa The pointer of the specified OPA module
47   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
48   * @return None
49   * @details This macro will set OPx_EN (x=0, 1) bit of OPACR register to power on the OPA circuit.
50   * @note Remember to enable HIRC clock while power on the OPA circuit.
51   * \hideinitializer
52   */
53 #define OPA_POWER_ON(opa, u32OpaNum) ((opa)->CTL |= (1UL<<(OPA_CTL_OPEN0_Pos+(u32OpaNum))))
54 
55 /**
56   * @brief This macro is used to power down the OPA circuit
57   * @param[in] opa The pointer of the specified OPA module
58   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
59   * @return None
60   * @details This macro will clear OPx_EN (x=0, 1) bit of OPACR register to power down the OPA circuit.
61   * \hideinitializer
62   */
63 #define OPA_POWER_DOWN(opa, u32OpaNum) ((opa)->CTL &= ~(1UL<<(OPA_CTL_OPEN0_Pos+(u32OpaNum))))
64 
65 /**
66   * @brief This macro is used to enable the OPA Schmitt trigger buffer
67   * @param[in] opa The pointer of the specified OPA module
68   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
69   * @return None
70   * @details This macro will set OPSCHx_EN (x=0, 1) bit of OPACR register to enable the OPA Schmitt trigger buffer.
71   * \hideinitializer
72   */
73 #define OPA_ENABLE_SCH_TRIGGER(opa, u32OpaNum) ((opa)->CTL |= (1UL<<(OPA_CTL_OPDOEN0_Pos+(u32OpaNum))))
74 
75 /**
76   * @brief This macro is used to disable the OPA Schmitt trigger buffer
77   * @param[in] opa The pointer of the specified OPA module
78   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
79   * @return None
80   * @details This macro will clear OPSCHx_EN (x=0, 1) bit of OPACR register to disable the OPA Schmitt trigger buffer.
81   * \hideinitializer
82   */
83 #define OPA_DISABLE_SCH_TRIGGER(opa, u32OpaNum) ((opa)->CTL &= ~(1UL<<(OPA_CTL_OPDOEN0_Pos+(u32OpaNum))))
84 
85 /**
86   * @brief This macro is used to enable OPA Schmitt trigger digital output interrupt
87   * @param[in] opa The pointer of the specified OPA module
88   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
89   * @return None
90   * @details This macro will set OPDIEx (x=0, 1) bit of OPACR register to enable the OPA Schmitt trigger digital output interrupt.
91   * \hideinitializer
92   */
93 #define OPA_ENABLE_INT(opa, u32OpaNum) ((opa)->CTL |= (1UL<<(OPA_CTL_OPDOIEN0_Pos+(u32OpaNum))))
94 
95 /**
96   * @brief This macro is used to disable OPA Schmitt trigger digital output interrupt
97   * @param[in] opa The pointer of the specified OPA module
98   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
99   * @return None
100   * @details This macro will clear OPDIEx (x=0, 1) bit of OPACR register to disable the OPA Schmitt trigger digital output interrupt.
101   * \hideinitializer
102   */
103 #define OPA_DISABLE_INT(opa, u32OpaNum) ((opa)->CTL &= ~(1UL<<(OPA_CTL_OPDOIEN0_Pos+(u32OpaNum))))
104 
105 /**
106   * @brief This macro is used to get OPA digital output state
107   * @param[in] opa The pointer of the specified OPA module
108   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
109   * @return  OPA digital output state
110   * @details This macro will return the OPA digital output value.
111   * \hideinitializer
112   */
113 #define OPA_GET_DIGITAL_OUTPUT(opa, u32OpaNum) (((opa)->STATUS & (OPA_STATUS_OPDO0_Msk<<(u32OpaNum)))?1UL:0UL)
114 
115 /**
116   * @brief This macro is used to get OPA interrupt flag
117   * @param[in] opa The pointer of the specified OPA module
118   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
119   * @retval     0 OPA interrupt does not occur.
120   * @retval     1 OPA interrupt occurs.
121   * @details This macro will return the ACMP interrupt flag.
122   * \hideinitializer
123   */
124 #define OPA_GET_INT_FLAG(opa, u32OpaNum) (((opa)->STATUS & (OPA_STATUS_OPDOIF0_Msk<<(u32OpaNum)))?1UL:0UL)
125 
126 /**
127   * @brief This macro is used to clear OPA interrupt flag
128   * @param[in] opa The pointer of the specified OPA module
129   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
130   * @return   None
131   * @details This macro will write 1 to OPDFx (x=0,1) bit of OPASR register to clear interrupt flag.
132   * \hideinitializer
133   */
134 #define OPA_CLR_INT_FLAG(opa, u32OpaNum) ((opa)->STATUS = (OPA_STATUS_OPDOIF0_Msk<<(u32OpaNum)))
135 
136 
137 /**
138   * @brief This function is used to configure and start OPA calibration
139   * @param[in] opa The pointer of the specified OPA module
140   * @param[in] u32OpaNum The OPA number. 0 for OPA0; 1 for OPA1; 2 for OPA2.
141   * @param[in] u32ClockSel Select OPA calibration clock
142   *                 - \ref OPA_CALIBRATION_CLK_1K
143   * @param[in] u32RefVol Select OPA reference voltage
144   *                 - \ref OPA_CALIBRATION_RV_1_2_AVDD
145   *                 - \ref OPA_CALIBRATION_RV_H_L_VCM
146   * @retval      0 PMOS and NMOS calibration successfully.
147   * @retval     -1 only PMOS calibration failed.
148   * @retval     -2 only NMOS calibration failed.
149   * @retval     -3 PMOS and NMOS calibration failed.
150   */
OPA_Calibration(OPA_T * opa,uint32_t u32OpaNum,uint32_t u32ClockSel,uint32_t u32RefVol)151 __STATIC_INLINE int32_t OPA_Calibration(OPA_T *opa,
152                                         uint32_t u32OpaNum,
153                                         uint32_t u32ClockSel,
154                                         uint32_t u32RefVol)
155 {
156     uint32_t u32CALResult;
157     int32_t i32Ret = 0L;
158 
159     (opa)->CALCTL = (((opa)->CALCTL) & ~(OPA_CALCTL_CALCLK0_Msk << (u32OpaNum << 1)));
160     (opa)->CALCTL = (((opa)->CALCTL) & ~(OPA_CALCTL_CALRVS0_Msk << (u32OpaNum))) | (((u32RefVol) << OPA_CALCTL_CALRVS0_Pos) << (u32OpaNum));
161     (opa)->CALCTL |= (OPA_CALCTL_CALTRG0_Msk << (u32OpaNum));
162     while((opa)->CALCTL & (OPA_CALCTL_CALTRG0_Msk << (u32OpaNum))) {}
163 
164     u32CALResult = ((opa)->CALST >> ((u32OpaNum)*4U)) & (OPA_CALST_CALNS0_Msk|OPA_CALST_CALPS0_Msk);
165     if (u32CALResult == 0U)
166     {
167         i32Ret = 0L;
168     }
169     else if (u32CALResult == OPA_CALST_CALNS0_Msk)
170     {
171         i32Ret = -2L;
172     }
173     else if (u32CALResult == OPA_CALST_CALPS0_Msk)
174     {
175         i32Ret = -1L;
176     }
177     else if (u32CALResult == (OPA_CALST_CALNS0_Msk|OPA_CALST_CALPS0_Msk))
178     {
179         i32Ret = -3L;
180     }
181 
182     return i32Ret;
183 }
184 
185 /**
186   * @brief This macro is used to generate asynchronous reset signals to OPA controller
187   * @param    None
188   * @return   None
189   * \hideinitializer
190   */
191 #define OPA_Reset() \
192 do { \
193     SYS->IPRST2 |= SYS_IPRST2_OPARST_Msk; \
194     SYS->IPRST2 &= ~SYS_IPRST2_OPARST_Msk; \
195 } while(0)
196 
197 /*@}*/ /* end of group OPA_EXPORTED_FUNCTIONS */
198 
199 /*@}*/ /* end of group OPA_Driver */
200 
201 /*@}*/ /* end of group Standard_Driver */
202 
203 #ifdef __cplusplus
204 }
205 #endif
206 
207 #endif /* __OPA_H__ */
208 
209 /*** (C) COPYRIGHT 2016 Nuvoton Technology Corp. ***/
210