1 /**
2 ******************************************************************************
3 * @file ald_dac.c
4 * @brief DAC module driver.
5 *
6 * @version V1.0
7 * @date 28 Jun 2019
8 * @author AE Team.
9 * @note
10 * Change Logs:
11 * Date Author Notes
12 * 28 Jun 2019 AE Team The first version
13 *
14 * Copyright (C) Shanghai Eastsoft Microelectronics Co. Ltd. All rights reserved.
15 *
16 * SPDX-License-Identifier: Apache-2.0
17 *
18 * Licensed under the Apache License, Version 2.0 (the License); you may
19 * not use this file except in compliance with the License.
20 * You may obtain a copy of the License at
21 *
22 * www.apache.org/licenses/LICENSE-2.0
23 *
24 * Unless required by applicable law or agreed to in writing, software
25 * distributed under the License is distributed on an AS IS BASIS, WITHOUT
26 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
27 * See the License for the specific language governing permissions and
28 * limitations under the License.
29 **********************************************************************************
30 */
31
32 #include "ald_conf.h"
33
34
35 /** @addtogroup ES32FXXX_ALD
36 * @{
37 */
38
39 /** @defgroup DAC DAC
40 * @brief DAC module driver
41 * @{
42 */
43 #ifdef ALD_DAC
44
45 /** @defgroup DAC_Public_Functions DAC Public Functions
46 * @{
47 */
48 /**
49 * @brief Reset the dac mode.
50 * @param hperh: Pointer to a dac_handle_t structure that contains
51 * the configuration information for the specified DAC module.
52 * @retval Status, see @ref ald_status_t.
53 */
ald_dac_reset(dac_handle_t * hperh)54 ald_status_t ald_dac_reset(dac_handle_t *hperh)
55 {
56 assert_param(IS_DAC_TYPE(hperh->perh));
57
58 hperh->perh->CON = 0;
59 hperh->perh->CH0CTRL = 0;
60 hperh->perh->CH1CTRL = 0;
61 hperh->perh->IES = 0;
62 hperh->perh->IEC = 0xFF;
63 hperh->perh->IFC = 0xFF;
64 hperh->perh->CAL = 0;
65
66 return OK;
67 }
68
69 /**
70 * @brief Initializes the DAC peripheral.
71 * @param hperh: Pointer to a dac_handle_t structure that contains
72 * the configuration information for the specified DAC module.
73 * @retval Status, see @ref ald_status_t.
74 */
ald_dac_init(dac_handle_t * hperh)75 ald_status_t ald_dac_init(dac_handle_t *hperh)
76 {
77 uint32_t tmp;
78
79 assert_param(IS_DAC_TYPE(hperh->perh));
80 assert_param(IS_DAC_CONVERT_TYPE(hperh->init.conv_mode));
81 assert_param(IS_DAC_OUTPUT_TYPE(hperh->init.out_mode));
82 assert_param(IS_DAC_NEG_REFRESH_TYPE(hperh->init.n_ref));
83 assert_param(IS_DAC_POS_REFRESH_TYPE(hperh->init.p_ref));
84 assert_param(IS_DAC_REFRESH_TYPE(hperh->init.refresh));
85 assert_param(IS_DAC_PRESCALE_TYPE(hperh->init.div));
86 assert_param(IS_FUNC_STATE(hperh->init.ch0_reset));
87 assert_param(IS_FUNC_STATE(hperh->init.o_ctrl_pis));
88 assert_param(IS_FUNC_STATE(hperh->init.sine));
89 assert_param(IS_FUNC_STATE(hperh->init.diff));
90
91 __LOCK(hperh);
92 ald_dac_reset(hperh);
93 DAC_CH0_DISABLE();
94 DAC_CH1_DISABLE();
95
96 MODIFY_REG(ADC0->CCR, ADC_CCR_VREFEN_MSK, 1 << ADC_CCR_VREFEN_POS);
97
98 if (hperh->init.p_ref == DAC_POS_REF_VREEFP_BUF || hperh->init.p_ref == DAC_POS_REF_2V)
99 SET_BIT(ADC0->CCR, (ADC_CCR_IREFEN_MSK | ADC_CCR_VRBUFEN_MSK | ADC_CCR_VCMBUFEN_MSK));
100
101 MODIFY_REG(ADC0->CCR, ADC_CCR_VRNSEL_MSK, hperh->init.n_ref << ADC_CCR_VRNSEL_POS);
102 MODIFY_REG(ADC0->CCR, ADC_CCR_VRPSEL_MSK, hperh->init.p_ref << ADC_CCR_VRPSEL_POSS);
103
104 tmp = ((hperh->init.refresh << DAC_CON_RCYCLSEL_POSS) | (hperh->init.div << DAC_CON_PRES_POSS) |
105 (hperh->init.ch0_reset << DAC_CON_CH0PRESRST_POS) | ( hperh->init.o_ctrl_pis << DAC_CON_OUTENPIS_POS) |
106 (hperh->init.out_mode << DAC_CON_OUTMD_POSS) | (hperh->init.conv_mode << DAC_CON_CONVMD_POSS) |
107 (hperh->init.sine << DAC_CON_SINEMD_POS) | (hperh->init.diff << DAC_CON_DIFEN_POS));
108 hperh->perh->CON = tmp;
109
110 /* Automatic calibration */
111 SET_BIT(hperh->perh->CAL, DAC_CAL_SELF_CALEN_MSK);
112 for (tmp = 0; tmp < 1000; ++tmp);
113 CLEAR_BIT(hperh->perh->CAL, DAC_CAL_SELF_CALEN_MSK);
114
115 __UNLOCK(hperh);
116 return OK;
117 }
118
119 /**
120 * @brief Configure dac channel.
121 * @param hperh: Pointer to a dac_handle_t structure that contains
122 * the configuration information for the specified DAC module.
123 * @param config: Pointer to a dac_channel_config_t structure that contains
124 * the configutation information for dac channel.
125 * @param ch: Specifies which dac channel to be config.
126 * @retval Status, see @ref ald_status_t.
127 */
ald_dac_channel_config(dac_handle_t * hperh,dac_channel_config_t * config,dac_channel_t ch)128 ald_status_t ald_dac_channel_config(dac_handle_t *hperh, dac_channel_config_t *config, dac_channel_t ch)
129 {
130 uint32_t tmp;
131
132 if ((hperh == NULL) || (config == NULL))
133 return ERROR;
134
135 assert_param(IS_DAC_TYPE(hperh->perh));
136 assert_param(IS_FUNC_STATE(config->enable));
137 assert_param(IS_DAC_TRIGGER_TYPE(config->trigger));
138 assert_param(IS_FUNC_STATE(config->refresh_en));
139 assert_param(IS_DAC_PISSEL_CH_TYPE(config->pis_ch));
140
141 __LOCK(hperh);
142 tmp = ((config->pis_ch << DAC_CH0CTRL_PISSEL_POSS) | (config->trigger << DAC_CH0CTRL_PISEN_POS) |
143 (config->refresh_en << DAC_CH0CTRL_RCYCLEN_POS) | (config->enable << DAC_CH0CTRL_EN_POS));
144
145 switch (ch) {
146 case DAC_CHANNEL_0:
147 hperh->perh->CH0CTRL = tmp;
148 break;
149
150 case DAC_CHANNEL_1:
151 hperh->perh->CH1CTRL = tmp;
152 break;
153
154 default:
155 break;
156 }
157
158 __UNLOCK(hperh);
159 return OK;
160 }
161
162 /**
163 * @brief Set dac channel output value.
164 * @param hperh: Pointer to a dac_handle_t structure that contains
165 * the configuration information for the specified DAC module.
166 * @param ch: Specifies which dac channel to be set.
167 * @param value: The value be converted,and the valid value is low 12 bit.
168 * @retval None
169 */
ald_dac_output_set(dac_handle_t * hperh,dac_channel_t ch,uint32_t value)170 void ald_dac_output_set(dac_handle_t *hperh, dac_channel_t ch, uint32_t value)
171 {
172 assert_param(IS_DAC_TYPE(hperh->perh));
173 assert_param(IS_DAC_CHANNEL_TYPE(ch));
174
175 switch (ch) {
176 case DAC_CHANNEL_0:
177 hperh->perh->CH0DATA = value;
178 break;
179
180 case DAC_CHANNEL_1:
181 hperh->perh->CH1DATA = value;
182 break;
183
184 case DAC_CHANNEL_COMB:
185 hperh->perh->COMBDATA = value;
186 break;
187
188 default:
189 break;
190 }
191
192 return;
193 }
194
195 /**
196 * @brief Checks whether the specified DAC flag is set or not.
197 * @param hperh: Pointer to a dac_handle_t structure that contains
198 * the configuration information for the specified dac.
199 * @param status: Specifies the flag to check.
200 * @retval The new state.
201 */
ald_dac_get_status(dac_handle_t * hperh,dac_status_t status)202 flag_status_t ald_dac_get_status(dac_handle_t *hperh, dac_status_t status)
203 {
204 assert_param(IS_DAC_TYPE(hperh->perh));
205 assert_param(IS_DAC_STATUS_TYPE(status));
206
207 return hperh->perh->STAT & status ? SET : RESET;
208 }
209
210 /**
211 * @brief Enable or disable the specified interrupt
212 * @param hperh: Pointer to a dac_handle_t structure that contains
213 * the configuration information for the specified DAC.
214 * @param it: Specifies the interrupt type to be enabled or disabled
215 * @arg @ref DAC_IT_CH0 Channel 0 conversion complete interrupt
216 * @arg @ref DAC_IT_CH1 Channel 1 conversion complete interrupt
217 * @arg @ref DAC_IT_CH0_UF Channel 0 data underflow interrupt
218 * @arg @ref DAC_IT_CH1_UF Channel 1 data underflow interrupt
219 * @param state: New state of the specified interrupt.
220 * This parameter can be: ENABLE or DISABLE
221 * @retval Status, see @ref ald_status_t.
222 */
ald_dac_interrupt_config(dac_handle_t * hperh,dac_it_t it,type_func_t state)223 void ald_dac_interrupt_config(dac_handle_t *hperh, dac_it_t it, type_func_t state)
224 {
225 assert_param(IS_DAC_TYPE(hperh->perh));
226 assert_param(IS_DAC_INTERRUPT_TYPE(it));
227 assert_param(IS_FUNC_STATE(state));
228
229 if (state)
230 hperh->perh->IES |= it;
231 else
232 hperh->perh->IEC = it;
233
234 return;
235 }
236
237 /**
238 * @brief Get the status of DAC interrupt source.
239 * @param hperh: Pointer to a dac_handle_t structure that contains
240 * the configuration information for the specified DAC.
241 * @param it: Specifies the DAC interrupt source.
242 * @retval Status:
243 * - 0: RESET
244 * - 1: SET
245 */
ald_dac_get_it_status(dac_handle_t * hperh,dac_it_t it)246 it_status_t ald_dac_get_it_status(dac_handle_t *hperh, dac_it_t it)
247 {
248 assert_param(IS_DAC_TYPE(hperh->perh));
249 assert_param(IS_DAC_INTERRUPT_TYPE(it));
250
251 return hperh->perh->IEV & it ? SET : RESET;
252 }
253
254 /**
255 * @brief Checks whether the specified interrupt has occurred or not.
256 * @param hperh: Pointer to a dac_handle_t structure that contains
257 * the configuration information for the specified DAC.
258 * @param flag: Specifies the interrupt type to check.
259 * @retval The new state.
260 */
ald_dac_get_flag_status(dac_handle_t * hperh,dac_flag_t flag)261 flag_status_t ald_dac_get_flag_status(dac_handle_t *hperh, dac_flag_t flag)
262 {
263 assert_param(IS_DAC_TYPE(hperh->perh));
264 assert_param(IS_DAC_FLAG_TYPE(flag));
265
266 return hperh->perh->RIF & flag ? SET : RESET;
267 }
268
269 /**
270 * @brief Get the status of interrupt flag and interupt source.
271 * @param hperh: Pointer to a dac_handle_t structure that contains
272 * the configuration information for the specified DAC.
273 * @param flag: Specifies the DAC interrupt flag.
274 * @retval Status:
275 * - 0: RESET
276 * - 1: SET
277 */
ald_dac_get_mask_flag_status(dac_handle_t * hperh,dac_flag_t flag)278 flag_status_t ald_dac_get_mask_flag_status(dac_handle_t *hperh, dac_flag_t flag)
279 {
280 assert_param(IS_DAC_TYPE(hperh->perh));
281 assert_param(IS_DAC_FLAG_TYPE(flag));
282
283 return hperh->perh->IFM & flag ? SET : RESET;
284 }
285
286 /**
287 * @brief Clear interrupt state flag
288 * @param hperh: Pointer to a dac_handle_t structure that contains
289 * the configuration information for the specified DAC.
290 * @param flag: Specifies the interrupt type to clear
291 * @retval None
292 */
ald_dac_clear_flag_status(dac_handle_t * hperh,dac_flag_t flag)293 void ald_dac_clear_flag_status(dac_handle_t *hperh, dac_flag_t flag)
294 {
295 assert_param(IS_DAC_TYPE(hperh->perh));
296 assert_param(IS_DAC_FLAG_TYPE(flag));
297
298 hperh->perh->IFC = flag;
299 return;
300 }
301
302 /**
303 * @brief This function handles DAC event interrupt request.
304 * @param hperh: Pointer to a dac_handle_t structure that contains
305 * the configuration information for the specified DAC.
306 * @retval None
307 */
ald_dac_irq_handler(dac_handle_t * hperh)308 void ald_dac_irq_handler(dac_handle_t *hperh)
309 {
310 if (ald_dac_get_mask_flag_status(hperh, DAC_FLAG_CH0)) {
311 ald_dac_clear_flag_status(hperh, DAC_FLAG_CH0);
312
313 if (hperh->cbk)
314 hperh->cbk(hperh, DAC_EVENT_CH0_CPLT);
315 }
316
317 if (ald_dac_get_mask_flag_status(hperh, DAC_FLAG_CH1)) {
318 ald_dac_clear_flag_status(hperh, DAC_FLAG_CH1);
319
320 if (hperh->cbk)
321 hperh->cbk(hperh, DAC_EVENT_CH1_CPLT);
322 }
323
324 if (ald_dac_get_mask_flag_status(hperh, DAC_FLAG_CH0_UF)) {
325 ald_dac_clear_flag_status(hperh, DAC_FLAG_CH0_UF);
326
327 if (hperh->cbk)
328 hperh->cbk(hperh, DAC_EVENT_CH0_UF);
329 }
330
331 if (ald_dac_get_mask_flag_status(hperh, DAC_FLAG_CH1_UF)) {
332 ald_dac_clear_flag_status(hperh, DAC_FLAG_CH1_UF);
333
334 if (hperh->cbk)
335 hperh->cbk(hperh, DAC_EVENT_CH1_UF);
336 }
337
338 return;
339 }
340 /**
341 *@}
342 */
343 #endif /* ALD_DAC */
344 /**
345 *@}
346 */
347 /**
348 *@}
349 */
350