1 /*!
2 \file gd32f4xx_adc.c
3 \brief ADC driver
4
5 \version 2016-08-15, V1.0.0, firmware for GD32F4xx
6 \version 2018-12-12, V2.0.0, firmware for GD32F4xx
7 \version 2020-09-30, V2.1.0, firmware for GD32F4xx
8 \version 2022-03-09, V3.0.0, firmware for GD32F4xx
9 */
10
11 /*
12 Copyright (c) 2022, GigaDevice Semiconductor Inc.
13
14 Redistribution and use in source and binary forms, with or without modification,
15 are permitted provided that the following conditions are met:
16
17 1. Redistributions of source code must retain the above copyright notice, this
18 list of conditions and the following disclaimer.
19 2. Redistributions in binary form must reproduce the above copyright notice,
20 this list of conditions and the following disclaimer in the documentation
21 and/or other materials provided with the distribution.
22 3. Neither the name of the copyright holder nor the names of its contributors
23 may be used to endorse or promote products derived from this software without
24 specific prior written permission.
25
26 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
27 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
28 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
29 IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
30 INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
31 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
32 PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
33 WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
34 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
35 OF SUCH DAMAGE.
36 */
37
38 #include "gd32f4xx_adc.h"
39
40 #define REGULAR_TRIGGER_MODE ((uint32_t)28U)
41 #define INSERTED_TRIGGER_MODE ((uint32_t)20U)
42 /* discontinuous mode macro*/
43 #define ADC_CHANNEL_LENGTH_SUBTRACT_ONE ((uint8_t)1U)
44
45 /* ADC regular channel macro */
46 #define ADC_REGULAR_CHANNEL_RANK_SIX ((uint8_t)6U)
47 #define ADC_REGULAR_CHANNEL_RANK_TWELVE ((uint8_t)12U)
48 #define ADC_REGULAR_CHANNEL_RANK_SIXTEEN ((uint8_t)16U)
49 #define ADC_REGULAR_CHANNEL_RANK_LENGTH ((uint8_t)5U)
50
51 /* ADC sampling time macro */
52 #define ADC_CHANNEL_SAMPLE_TEN ((uint8_t)10U)
53 #define ADC_CHANNEL_SAMPLE_EIGHTEEN ((uint8_t)18U)
54 #define ADC_CHANNEL_SAMPLE_LENGTH ((uint8_t)3U)
55
56 /* ADC inserted channel macro */
57 #define ADC_INSERTED_CHANNEL_RANK_LENGTH ((uint8_t)5U)
58 #define ADC_INSERTED_CHANNEL_SHIFT_LENGTH ((uint8_t)15U)
59
60 /* ADC inserted channel offset macro */
61 #define ADC_OFFSET_LENGTH ((uint8_t)3U)
62 #define ADC_OFFSET_SHIFT_LENGTH ((uint8_t)4U)
63
64 /*!
65 \brief reset ADC
66 \param[in] none
67 \param[out] none
68 \retval none
69 */
adc_deinit(void)70 void adc_deinit(void)
71 {
72 rcu_periph_reset_enable(RCU_ADCRST);
73 rcu_periph_reset_disable(RCU_ADCRST);
74 }
75
76 /*!
77 \brief configure the ADC clock for all the ADCs
78 \param[in] prescaler: configure ADCs prescaler ratio
79 only one parameter can be selected which is shown as below:
80 \arg ADC_ADCCK_PCLK2_DIV2: PCLK2 div2
81 \arg ADC_ADCCK_PCLK2_DIV4: PCLK2 div4
82 \arg ADC_ADCCK_PCLK2_DIV6: PCLK2 div6
83 \arg ADC_ADCCK_PCLK2_DIV8: PCLK2 div8
84 \arg ADC_ADCCK_HCLK_DIV5: HCLK div5
85 \arg ADC_ADCCK_HCLK_DIV6: HCLK div6
86 \arg ADC_ADCCK_HCLK_DIV10: HCLK div10
87 \arg ADC_ADCCK_HCLK_DIV20: HCLK div20
88 \param[out] none
89 \retval none
90 */
adc_clock_config(uint32_t prescaler)91 void adc_clock_config(uint32_t prescaler)
92 {
93 ADC_SYNCCTL &= ~((uint32_t)ADC_SYNCCTL_ADCCK);
94 ADC_SYNCCTL |= (uint32_t) prescaler;
95 }
96
97 /*!
98 \brief enable or disable ADC special function
99 \param[in] adc_periph: ADCx,x=0,1,2
100 \param[in] function: the function to config
101 only one parameter can be selected which is shown as below:
102 \arg ADC_SCAN_MODE: scan mode select
103 \arg ADC_INSERTED_CHANNEL_AUTO: inserted channel group convert automatically
104 \arg ADC_CONTINUOUS_MODE: continuous mode select
105 \param[in] newvalue: ENABLE or DISABLE
106 \param[out] none
107 \retval none
108 */
adc_special_function_config(uint32_t adc_periph,uint32_t function,ControlStatus newvalue)109 void adc_special_function_config(uint32_t adc_periph, uint32_t function, ControlStatus newvalue)
110 {
111 if(newvalue) {
112 if(0U != (function & ADC_SCAN_MODE)) {
113 /* enable scan mode */
114 ADC_CTL0(adc_periph) |= ADC_SCAN_MODE;
115 }
116 if(0U != (function & ADC_INSERTED_CHANNEL_AUTO)) {
117 /* enable inserted channel group convert automatically */
118 ADC_CTL0(adc_periph) |= ADC_INSERTED_CHANNEL_AUTO;
119 }
120 if(0U != (function & ADC_CONTINUOUS_MODE)) {
121 /* enable continuous mode */
122 ADC_CTL1(adc_periph) |= ADC_CONTINUOUS_MODE;
123 }
124 } else {
125 if(0U != (function & ADC_SCAN_MODE)) {
126 /* disable scan mode */
127 ADC_CTL0(adc_periph) &= ~ADC_SCAN_MODE;
128 }
129 if(0U != (function & ADC_INSERTED_CHANNEL_AUTO)) {
130 /* disable inserted channel group convert automatically */
131 ADC_CTL0(adc_periph) &= ~ADC_INSERTED_CHANNEL_AUTO;
132 }
133 if(0U != (function & ADC_CONTINUOUS_MODE)) {
134 /* disable continuous mode */
135 ADC_CTL1(adc_periph) &= ~ADC_CONTINUOUS_MODE;
136 }
137 }
138 }
139
140 /*!
141 \brief configure ADC data alignment
142 \param[in] adc_periph: ADCx,x=0,1,2
143 \param[in] data_alignment: data alignment select
144 only one parameter can be selected which is shown as below:
145 \arg ADC_DATAALIGN_RIGHT: LSB alignment
146 \arg ADC_DATAALIGN_LEFT: MSB alignment
147 \param[out] none
148 \retval none
149 */
adc_data_alignment_config(uint32_t adc_periph,uint32_t data_alignment)150 void adc_data_alignment_config(uint32_t adc_periph, uint32_t data_alignment)
151 {
152 if(ADC_DATAALIGN_RIGHT != data_alignment) {
153 /* MSB alignment */
154 ADC_CTL1(adc_periph) |= ADC_CTL1_DAL;
155 } else {
156 /* LSB alignment */
157 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_DAL);
158 }
159 }
160
161 /*!
162 \brief enable ADC interface
163 \param[in] adc_periph: ADCx,x=0,1,2
164 \param[out] none
165 \retval none
166 */
adc_enable(uint32_t adc_periph)167 void adc_enable(uint32_t adc_periph)
168 {
169 if(RESET == (ADC_CTL1(adc_periph) & ADC_CTL1_ADCON)) {
170 /* enable ADC */
171 ADC_CTL1(adc_periph) |= (uint32_t)ADC_CTL1_ADCON;
172 }
173 }
174
175 /*!
176 \brief disable ADC interface
177 \param[in] adc_periph: ADCx,x=0,1,2
178 \param[out] none
179 \retval none
180 */
adc_disable(uint32_t adc_periph)181 void adc_disable(uint32_t adc_periph)
182 {
183 /* disable ADC */
184 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_ADCON);
185 }
186
187 /*!
188 \brief ADC calibration and reset calibration
189 \param[in] adc_periph: ADCx,x=0,1,2
190 \param[out] none
191 \retval none
192 */
adc_calibration_enable(uint32_t adc_periph)193 void adc_calibration_enable(uint32_t adc_periph)
194 {
195 /* reset the selected ADC calibration registers */
196 ADC_CTL1(adc_periph) |= (uint32_t) ADC_CTL1_RSTCLB;
197 /* check the RSTCLB bit state */
198 while(RESET != (ADC_CTL1(adc_periph) & ADC_CTL1_RSTCLB)) {
199 }
200 /* enable ADC calibration process */
201 ADC_CTL1(adc_periph) |= ADC_CTL1_CLB;
202 /* check the CLB bit state */
203 while(RESET != (ADC_CTL1(adc_periph) & ADC_CTL1_CLB)) {
204 }
205 }
206
207 /*!
208 \brief configure temperature sensor and internal reference voltage channel or VBAT channel function
209 \param[in] function: temperature sensor and internal reference voltage channel or VBAT channel
210 only one parameter can be selected which is shown as below:
211 \arg ADC_VBAT_CHANNEL_SWITCH: channel 18 (1/4 voltate of external battery) switch of ADC0
212 \arg ADC_TEMP_VREF_CHANNEL_SWITCH: channel 16 (temperature sensor) and 17 (internal reference voltage) switch of ADC0
213 \param[in] newvalue: ENABLE or DISABLE
214 \param[out] none
215 \retval none
216 */
adc_channel_16_to_18(uint32_t function,ControlStatus newvalue)217 void adc_channel_16_to_18(uint32_t function, ControlStatus newvalue)
218 {
219 if(newvalue) {
220 if(RESET != (function & ADC_VBAT_CHANNEL_SWITCH)) {
221 /* enable ADC0 Vbat channel */
222 ADC_SYNCCTL |= ADC_VBAT_CHANNEL_SWITCH;
223 }
224 if(RESET != (function & ADC_TEMP_VREF_CHANNEL_SWITCH)) {
225 /* enable ADC0 Vref and Temperature channel */
226 ADC_SYNCCTL |= ADC_TEMP_VREF_CHANNEL_SWITCH;
227 }
228 } else {
229 if(RESET != (function & ADC_VBAT_CHANNEL_SWITCH)) {
230 /* disable ADC0 Vbat channel */
231 ADC_SYNCCTL &= ~ADC_VBAT_CHANNEL_SWITCH;
232 }
233 if(RESET != (function & ADC_TEMP_VREF_CHANNEL_SWITCH)) {
234 /* disable ADC0 Vref and Temperature channel */
235 ADC_SYNCCTL &= ~ADC_TEMP_VREF_CHANNEL_SWITCH;
236 }
237 }
238 }
239
240 /*!
241 \brief configure ADC resolution
242 \param[in] adc_periph: ADCx,x=0,1,2
243 \param[in] resolution: ADC resolution
244 only one parameter can be selected which is shown as below:
245 \arg ADC_RESOLUTION_12B: 12-bit ADC resolution
246 \arg ADC_RESOLUTION_10B: 10-bit ADC resolution
247 \arg ADC_RESOLUTION_8B: 8-bit ADC resolution
248 \arg ADC_RESOLUTION_6B: 6-bit ADC resolution
249 \param[out] none
250 \retval none
251 */
adc_resolution_config(uint32_t adc_periph,uint32_t resolution)252 void adc_resolution_config(uint32_t adc_periph, uint32_t resolution)
253 {
254 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_DRES);
255 ADC_CTL0(adc_periph) |= (uint32_t)resolution;
256 }
257
258 /*!
259 \brief configure ADC oversample mode
260 \param[in] adc_periph: ADCx,x=0,1,2
261 \param[in] mode: ADC oversampling mode
262 only one parameter can be selected which is shown as below:
263 \arg ADC_OVERSAMPLING_ALL_CONVERT: all oversampled conversions for a channel are done consecutively after a trigger
264 \arg ADC_OVERSAMPLING_ONE_CONVERT: each oversampled conversion for a channel needs a trigger
265 \param[in] shift: ADC oversampling shift
266 only one parameter can be selected which is shown as below:
267 \arg ADC_OVERSAMPLING_SHIFT_NONE: no oversampling shift
268 \arg ADC_OVERSAMPLING_SHIFT_1B: 1-bit oversampling shift
269 \arg ADC_OVERSAMPLING_SHIFT_2B: 2-bit oversampling shift
270 \arg ADC_OVERSAMPLING_SHIFT_3B: 3-bit oversampling shift
271 \arg ADC_OVERSAMPLING_SHIFT_4B: 3-bit oversampling shift
272 \arg ADC_OVERSAMPLING_SHIFT_5B: 5-bit oversampling shift
273 \arg ADC_OVERSAMPLING_SHIFT_6B: 6-bit oversampling shift
274 \arg ADC_OVERSAMPLING_SHIFT_7B: 7-bit oversampling shift
275 \arg ADC_OVERSAMPLING_SHIFT_8B: 8-bit oversampling shift
276 \param[in] ratio: ADC oversampling ratio
277 only one parameter can be selected which is shown as below:
278 \arg ADC_OVERSAMPLING_RATIO_MUL2: oversampling ratio multiple 2
279 \arg ADC_OVERSAMPLING_RATIO_MUL4: oversampling ratio multiple 4
280 \arg ADC_OVERSAMPLING_RATIO_MUL8: oversampling ratio multiple 8
281 \arg ADC_OVERSAMPLING_RATIO_MUL16: oversampling ratio multiple 16
282 \arg ADC_OVERSAMPLING_RATIO_MUL32: oversampling ratio multiple 32
283 \arg ADC_OVERSAMPLING_RATIO_MUL64: oversampling ratio multiple 64
284 \arg ADC_OVERSAMPLING_RATIO_MUL128: oversampling ratio multiple 128
285 \arg ADC_OVERSAMPLING_RATIO_MUL256: oversampling ratio multiple 256
286 \param[out] none
287 \retval none
288 */
adc_oversample_mode_config(uint32_t adc_periph,uint32_t mode,uint16_t shift,uint8_t ratio)289 void adc_oversample_mode_config(uint32_t adc_periph, uint32_t mode, uint16_t shift, uint8_t ratio)
290 {
291 if(ADC_OVERSAMPLING_ONE_CONVERT == mode) {
292 ADC_OVSAMPCTL(adc_periph) |= (uint32_t)ADC_OVSAMPCTL_TOVS;
293 } else {
294 ADC_OVSAMPCTL(adc_periph) &= ~((uint32_t)ADC_OVSAMPCTL_TOVS);
295 }
296 /* config the shift and ratio */
297 ADC_OVSAMPCTL(adc_periph) &= ~((uint32_t)(ADC_OVSAMPCTL_OVSR | ADC_OVSAMPCTL_OVSS));
298 ADC_OVSAMPCTL(adc_periph) |= ((uint32_t)shift | (uint32_t)ratio);
299 }
300
301 /*!
302 \brief enable ADC oversample mode
303 \param[in] adc_periph: ADCx,x=0,1,2
304 \param[out] none
305 \retval none
306 */
adc_oversample_mode_enable(uint32_t adc_periph)307 void adc_oversample_mode_enable(uint32_t adc_periph)
308 {
309 ADC_OVSAMPCTL(adc_periph) |= ADC_OVSAMPCTL_OVSEN;
310 }
311
312 /*!
313 \brief disable ADC oversample mode
314 \param[in] adc_periph: ADCx,x=0,1,2
315 \param[out] none
316 \retval none
317 */
adc_oversample_mode_disable(uint32_t adc_periph)318 void adc_oversample_mode_disable(uint32_t adc_periph)
319 {
320 ADC_OVSAMPCTL(adc_periph) &= ~((uint32_t)ADC_OVSAMPCTL_OVSEN);
321 }
322
323 /*!
324 \brief enable DMA request
325 \param[in] adc_periph: ADCx,x=0,1,2
326 \param[out] none
327 \retval none
328 */
adc_dma_mode_enable(uint32_t adc_periph)329 void adc_dma_mode_enable(uint32_t adc_periph)
330 {
331 /* enable DMA request */
332 ADC_CTL1(adc_periph) |= (uint32_t)(ADC_CTL1_DMA);
333 }
334
335 /*!
336 \brief disable DMA request
337 \param[in] adc_periph: ADCx,x=0,1,2
338 \param[out] none
339 \retval none
340 */
adc_dma_mode_disable(uint32_t adc_periph)341 void adc_dma_mode_disable(uint32_t adc_periph)
342 {
343 /* disable DMA request */
344 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_DMA);
345 }
346
347 /*!
348 \brief when DMA=1, the DMA engine issues a request at end of each regular conversion
349 \param[in] adc_periph: ADCx,x=0,1,2
350 \param[out] none
351 \retval none
352 */
adc_dma_request_after_last_enable(uint32_t adc_periph)353 void adc_dma_request_after_last_enable(uint32_t adc_periph)
354 {
355 ADC_CTL1(adc_periph) |= (uint32_t)(ADC_CTL1_DDM);
356 }
357
358 /*!
359 \brief the DMA engine is disabled after the end of transfer signal from DMA controller is detected
360 \param[in] adc_periph: ADCx,x=0,1,2
361 \param[out] none
362 \retval none
363 */
adc_dma_request_after_last_disable(uint32_t adc_periph)364 void adc_dma_request_after_last_disable(uint32_t adc_periph)
365 {
366 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_DDM);
367 }
368
369 /*!
370 \brief configure ADC discontinuous mode
371 \param[in] adc_periph: ADCx,x=0,1,2
372 \param[in] adc_channel_group: select the channel group
373 only one parameter can be selected which is shown as below:
374 \arg ADC_REGULAR_CHANNEL: regular channel group
375 \arg ADC_INSERTED_CHANNEL: inserted channel group
376 \arg ADC_CHANNEL_DISCON_DISABLE: disable discontinuous mode of regular & inserted channel
377 \param[in] length: number of conversions in discontinuous mode,the number can be 1..8
378 for regular channel ,the number has no effect for inserted channel
379 \param[out] none
380 \retval none
381 */
adc_discontinuous_mode_config(uint32_t adc_periph,uint8_t adc_channel_group,uint8_t length)382 void adc_discontinuous_mode_config(uint32_t adc_periph, uint8_t adc_channel_group, uint8_t length)
383 {
384 /* disable discontinuous mode of regular & inserted channel */
385 ADC_CTL0(adc_periph) &= ~((uint32_t)(ADC_CTL0_DISRC | ADC_CTL0_DISIC));
386 switch(adc_channel_group) {
387 case ADC_REGULAR_CHANNEL:
388 /* config the number of conversions in discontinuous mode */
389 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_DISNUM);
390 if((length <= 8U) && (length >= 1U)) {
391 ADC_CTL0(adc_periph) |= CTL0_DISNUM(((uint32_t)length - ADC_CHANNEL_LENGTH_SUBTRACT_ONE));
392 }
393 /* enable regular channel group discontinuous mode */
394 ADC_CTL0(adc_periph) |= (uint32_t)ADC_CTL0_DISRC;
395 break;
396 case ADC_INSERTED_CHANNEL:
397 /* enable inserted channel group discontinuous mode */
398 ADC_CTL0(adc_periph) |= (uint32_t)ADC_CTL0_DISIC;
399 break;
400 case ADC_CHANNEL_DISCON_DISABLE:
401 /* disable discontinuous mode of regular & inserted channel */
402 default:
403 break;
404 }
405 }
406
407 /*!
408 \brief configure the length of regular channel group or inserted channel group
409 \param[in] adc_periph: ADCx,x=0,1,2
410 \param[in] adc_channel_group: select the channel group
411 only one parameter can be selected which is shown as below:
412 \arg ADC_REGULAR_CHANNEL: regular channel group
413 \arg ADC_INSERTED_CHANNEL: inserted channel group
414 \param[in] length: the length of the channel
415 regular channel 1-16
416 inserted channel 1-4
417 \param[out] none
418 \retval none
419 */
adc_channel_length_config(uint32_t adc_periph,uint8_t adc_channel_group,uint32_t length)420 void adc_channel_length_config(uint32_t adc_periph, uint8_t adc_channel_group, uint32_t length)
421 {
422 switch(adc_channel_group) {
423 case ADC_REGULAR_CHANNEL:
424 if((length >= 1U) && (length <= 16U)) {
425 ADC_RSQ0(adc_periph) &= ~((uint32_t)ADC_RSQ0_RL);
426 ADC_RSQ0(adc_periph) |= RSQ0_RL((uint32_t)(length - ADC_CHANNEL_LENGTH_SUBTRACT_ONE));
427 }
428 break;
429 case ADC_INSERTED_CHANNEL:
430 if((length >= 1U) && (length <= 4U)) {
431 ADC_ISQ(adc_periph) &= ~((uint32_t)ADC_ISQ_IL);
432 ADC_ISQ(adc_periph) |= ISQ_IL((uint32_t)(length - ADC_CHANNEL_LENGTH_SUBTRACT_ONE));
433 }
434 break;
435 default:
436 break;
437 }
438 }
439
440 /*!
441 \brief configure ADC regular channel
442 \param[in] adc_periph: ADCx,x=0,1,2
443 \param[in] rank: the regular group sequencer rank,this parameter must be between 0 to 15
444 \param[in] adc_channel: the selected ADC channel
445 only one parameter can be selected which is shown as below:
446 \arg ADC_CHANNEL_x(x=0..18): ADC Channelx
447 \param[in] sample_time: the sample time value
448 only one parameter can be selected which is shown as below:
449 \arg ADC_SAMPLETIME_3: 3 cycles
450 \arg ADC_SAMPLETIME_15: 15 cycles
451 \arg ADC_SAMPLETIME_28: 28 cycles
452 \arg ADC_SAMPLETIME_56: 56 cycles
453 \arg ADC_SAMPLETIME_84: 84 cycles
454 \arg ADC_SAMPLETIME_112: 112 cycles
455 \arg ADC_SAMPLETIME_144: 144 cycles
456 \arg ADC_SAMPLETIME_480: 480 cycles
457 \param[out] none
458 \retval none
459 */
adc_regular_channel_config(uint32_t adc_periph,uint8_t rank,uint8_t adc_channel,uint32_t sample_time)460 void adc_regular_channel_config(uint32_t adc_periph, uint8_t rank, uint8_t adc_channel, uint32_t sample_time)
461 {
462 uint32_t rsq, sampt;
463
464 /* ADC regular sequence config */
465 if(rank < ADC_REGULAR_CHANNEL_RANK_SIX) {
466 /* the regular group sequence rank is smaller than six */
467 rsq = ADC_RSQ2(adc_periph);
468 rsq &= ~((uint32_t)(ADC_RSQX_RSQN << (ADC_REGULAR_CHANNEL_RANK_LENGTH * rank)));
469 /* the channel number is written to these bits to select a channel as the nth conversion in the regular channel group */
470 rsq |= ((uint32_t)adc_channel << (ADC_REGULAR_CHANNEL_RANK_LENGTH * rank));
471 ADC_RSQ2(adc_periph) = rsq;
472 } else if(rank < ADC_REGULAR_CHANNEL_RANK_TWELVE) {
473 /* the regular group sequence rank is smaller than twelve */
474 rsq = ADC_RSQ1(adc_periph);
475 rsq &= ~((uint32_t)(ADC_RSQX_RSQN << (ADC_REGULAR_CHANNEL_RANK_LENGTH * (rank - ADC_REGULAR_CHANNEL_RANK_SIX))));
476 /* the channel number is written to these bits to select a channel as the nth conversion in the regular channel group */
477 rsq |= ((uint32_t)adc_channel << (ADC_REGULAR_CHANNEL_RANK_LENGTH * (rank - ADC_REGULAR_CHANNEL_RANK_SIX)));
478 ADC_RSQ1(adc_periph) = rsq;
479 } else if(rank < ADC_REGULAR_CHANNEL_RANK_SIXTEEN) {
480 /* the regular group sequence rank is smaller than sixteen */
481 rsq = ADC_RSQ0(adc_periph);
482 rsq &= ~((uint32_t)(ADC_RSQX_RSQN << (ADC_REGULAR_CHANNEL_RANK_LENGTH * (rank - ADC_REGULAR_CHANNEL_RANK_TWELVE))));
483 /* the channel number is written to these bits to select a channel as the nth conversion in the regular channel group */
484 rsq |= ((uint32_t)adc_channel << (ADC_REGULAR_CHANNEL_RANK_LENGTH * (rank - ADC_REGULAR_CHANNEL_RANK_TWELVE)));
485 ADC_RSQ0(adc_periph) = rsq;
486 } else {
487 }
488
489 /* ADC sampling time config */
490 if(adc_channel < ADC_CHANNEL_SAMPLE_TEN) {
491 /* the regular group sequence rank is smaller than ten */
492 sampt = ADC_SAMPT1(adc_periph);
493 sampt &= ~((uint32_t)(ADC_SAMPTX_SPTN << (ADC_CHANNEL_SAMPLE_LENGTH * adc_channel)));
494 /* channel sample time set*/
495 sampt |= (uint32_t)(sample_time << (ADC_CHANNEL_SAMPLE_LENGTH * adc_channel));
496 ADC_SAMPT1(adc_periph) = sampt;
497 } else if(adc_channel <= ADC_CHANNEL_SAMPLE_EIGHTEEN) {
498 /* the regular group sequence rank is smaller than eighteen */
499 sampt = ADC_SAMPT0(adc_periph);
500 sampt &= ~((uint32_t)(ADC_SAMPTX_SPTN << (ADC_CHANNEL_SAMPLE_LENGTH * (adc_channel - ADC_CHANNEL_SAMPLE_TEN))));
501 /* channel sample time set*/
502 sampt |= (uint32_t)(sample_time << (ADC_CHANNEL_SAMPLE_LENGTH * (adc_channel - ADC_CHANNEL_SAMPLE_TEN)));
503 ADC_SAMPT0(adc_periph) = sampt;
504 } else {
505 }
506 }
507
508 /*!
509 \brief configure ADC inserted channel
510 \param[in] adc_periph: ADCx,x=0,1,2
511 \param[in] rank: the inserted group sequencer rank,this parameter must be between 0 to 3
512 \param[in] adc_channel: the selected ADC channel
513 only one parameter can be selected which is shown as below:
514 \arg ADC_CHANNEL_x(x=0..18): ADC Channelx
515 \param[in] sample_time: The sample time value
516 only one parameter can be selected which is shown as below:
517 \arg ADC_SAMPLETIME_3: 3 cycles
518 \arg ADC_SAMPLETIME_15: 15 cycles
519 \arg ADC_SAMPLETIME_28: 28 cycles
520 \arg ADC_SAMPLETIME_56: 56 cycles
521 \arg ADC_SAMPLETIME_84: 84 cycles
522 \arg ADC_SAMPLETIME_112: 112 cycles
523 \arg ADC_SAMPLETIME_144: 144 cycles
524 \arg ADC_SAMPLETIME_480: 480 cycles
525 \param[out] none
526 \retval none
527 */
adc_inserted_channel_config(uint32_t adc_periph,uint8_t rank,uint8_t adc_channel,uint32_t sample_time)528 void adc_inserted_channel_config(uint32_t adc_periph, uint8_t rank, uint8_t adc_channel, uint32_t sample_time)
529 {
530 uint8_t inserted_length;
531 uint32_t isq, sampt;
532
533 /* get inserted channel group length */
534 inserted_length = (uint8_t)GET_BITS(ADC_ISQ(adc_periph), 20U, 21U);
535 /* the channel number is written to these bits to select a channel as the nth conversion in the inserted channel group */
536 if(rank < 4U) {
537 isq = ADC_ISQ(adc_periph);
538 isq &= ~((uint32_t)(ADC_ISQ_ISQN << (ADC_INSERTED_CHANNEL_SHIFT_LENGTH - (inserted_length - rank) * ADC_INSERTED_CHANNEL_RANK_LENGTH)));
539 isq |= ((uint32_t)adc_channel << (ADC_INSERTED_CHANNEL_SHIFT_LENGTH - (inserted_length - rank) * ADC_INSERTED_CHANNEL_RANK_LENGTH));
540 ADC_ISQ(adc_periph) = isq;
541 }
542
543 /* ADC sampling time config */
544 if(adc_channel < ADC_CHANNEL_SAMPLE_TEN) {
545 /* the inserted group sequence rank is smaller than ten */
546 sampt = ADC_SAMPT1(adc_periph);
547 sampt &= ~((uint32_t)(ADC_SAMPTX_SPTN << (ADC_CHANNEL_SAMPLE_LENGTH * adc_channel)));
548 /* channel sample time set*/
549 sampt |= (uint32_t) sample_time << (ADC_CHANNEL_SAMPLE_LENGTH * adc_channel);
550 ADC_SAMPT1(adc_periph) = sampt;
551 } else if(adc_channel <= ADC_CHANNEL_SAMPLE_EIGHTEEN) {
552 /* the inserted group sequence rank is smaller than eighteen */
553 sampt = ADC_SAMPT0(adc_periph);
554 sampt &= ~((uint32_t)(ADC_SAMPTX_SPTN << (ADC_CHANNEL_SAMPLE_LENGTH * (adc_channel - ADC_CHANNEL_SAMPLE_TEN))));
555 /* channel sample time set*/
556 sampt |= ((uint32_t)sample_time << (ADC_CHANNEL_SAMPLE_LENGTH * (adc_channel - ADC_CHANNEL_SAMPLE_TEN)));
557 ADC_SAMPT0(adc_periph) = sampt;
558 } else {
559 }
560 }
561
562 /*!
563 \brief configure ADC inserted channel offset
564 \param[in] adc_periph: ADCx,x=0,1,2
565 \param[in] inserted_channel : insert channel select
566 only one parameter can be selected which is shown as below:
567 \arg ADC_INSERTED_CHANNEL_0: inserted channel0
568 \arg ADC_INSERTED_CHANNEL_1: inserted channel1
569 \arg ADC_INSERTED_CHANNEL_2: inserted channel2
570 \arg ADC_INSERTED_CHANNEL_3: inserted channel3
571 \param[in] offset : the offset data
572 \param[out] none
573 \retval none
574 */
adc_inserted_channel_offset_config(uint32_t adc_periph,uint8_t inserted_channel,uint16_t offset)575 void adc_inserted_channel_offset_config(uint32_t adc_periph, uint8_t inserted_channel, uint16_t offset)
576 {
577 uint8_t inserted_length;
578 uint32_t num = 0U;
579
580 inserted_length = (uint8_t)GET_BITS(ADC_ISQ(adc_periph), 20U, 21U);
581 num = ((uint32_t)ADC_OFFSET_LENGTH - ((uint32_t)inserted_length - (uint32_t)inserted_channel));
582
583 if(num <= ADC_OFFSET_LENGTH) {
584 /* calculate the offset of the register */
585 num = num * ADC_OFFSET_SHIFT_LENGTH;
586 /* config the offset of the selected channels */
587 REG32((adc_periph) + 0x14U + num) = IOFFX_IOFF((uint32_t)offset);
588 }
589 }
590
591 /*!
592 \brief configure ADC external trigger source
593 \param[in] adc_periph: ADCx,x=0,1,2
594 \param[in] adc_channel_group: select the channel group
595 only one parameter can be selected which is shown as below:
596 \arg ADC_REGULAR_CHANNEL: regular channel group
597 \arg ADC_INSERTED_CHANNEL: inserted channel group
598 \param[in] external_trigger_source: regular or inserted group trigger source
599 for regular channel:
600 only one parameter can be selected which is shown as below:
601 \arg ADC_EXTTRIG_REGULAR_T0_CH0: external trigger timer 0 CC0 event select for regular channel
602 \arg ADC_EXTTRIG_REGULAR_T0_CH1: external trigger timer 0 CC1 event select for regular channel
603 \arg ADC_EXTTRIG_REGULAR_T0_CH2: external trigger timer 0 CC2 event select for regular channel
604 \arg ADC_EXTTRIG_REGULAR_T1_CH1: external trigger timer 1 CC1 event select for regular channel
605 \arg ADC_EXTTRIG_REGULAR_T1_CH2: external trigger timer 1 CC2 event select for regular channel
606 \arg ADC_EXTTRIG_REGULAR_T1_CH3: external trigger timer 1 CC3 event select for regular channel
607 \arg ADC_EXTTRIG_REGULAR_T1_TRGO: external trigger timer 1 TRGO event select for regular channel
608 \arg ADC_EXTTRIG_REGULAR_T2_CH0 : external trigger timer 2 CC0 event select for regular channel
609 \arg ADC_EXTTRIG_REGULAR_T2_TRGO : external trigger timer 2 TRGO event select for regular channel
610 \arg ADC_EXTTRIG_REGULAR_T3_CH3: external trigger timer 3 CC3 event select for regular channel
611 \arg ADC_EXTTRIG_REGULAR_T4_CH0: external trigger timer 4 CC0 event select for regular channel
612 \arg ADC_EXTTRIG_REGULAR_T4_CH1: external trigger timer 4 CC1 event select for regular channel
613 \arg ADC_EXTTRIG_REGULAR_T4_CH2: external trigger timer 4 CC2 event select for regular channel
614 \arg ADC_EXTTRIG_REGULAR_T7_CH0: external trigger timer 7 CC0 event select for regular channel
615 \arg ADC_EXTTRIG_REGULAR_T7_TRGO: external trigger timer 7 TRGO event select for regular channel
616 \arg ADC_EXTTRIG_REGULAR_EXTI_11: external trigger extiline 11 select for regular channel
617 for inserted channel:
618 only one parameter can be selected which is shown as below:
619 \arg ADC_EXTTRIG_INSERTED_T0_CH3: timer0 capture compare 3
620 \arg ADC_EXTTRIG_INSERTED_T0_TRGO: timer0 TRGO event
621 \arg ADC_EXTTRIG_INSERTED_T1_CH0: timer1 capture compare 0
622 \arg ADC_EXTTRIG_INSERTED_T1_TRGO: timer1 TRGO event
623 \arg ADC_EXTTRIG_INSERTED_T2_CH1: timer2 capture compare 1
624 \arg ADC_EXTTRIG_INSERTED_T2_CH3: timer2 capture compare 3
625 \arg ADC_EXTTRIG_INSERTED_T3_CH0: timer3 capture compare 0
626 \arg ADC_EXTTRIG_INSERTED_T3_CH1: timer3 capture compare 1
627 \arg ADC_EXTTRIG_INSERTED_T3_CH2: timer3 capture compare 2
628 \arg ADC_EXTTRIG_INSERTED_T3_TRGO: timer3 capture compare TRGO
629 \arg ADC_EXTTRIG_INSERTED_T4_CH3: timer4 capture compare 3
630 \arg ADC_EXTTRIG_INSERTED_T4_TRGO: timer4 capture compare TRGO
631 \arg ADC_EXTTRIG_INSERTED_T7_CH1: timer7 capture compare 1
632 \arg ADC_EXTTRIG_INSERTED_T7_CH2: timer7 capture compare 2
633 \arg ADC_EXTTRIG_INSERTED_T7_CH3: timer7 capture compare 3
634 \arg ADC_EXTTRIG_INSERTED_EXTI_15: external interrupt line 15
635 \param[out] none
636 \retval none
637 */
adc_external_trigger_source_config(uint32_t adc_periph,uint8_t adc_channel_group,uint32_t external_trigger_source)638 void adc_external_trigger_source_config(uint32_t adc_periph, uint8_t adc_channel_group, uint32_t external_trigger_source)
639 {
640 switch(adc_channel_group) {
641 case ADC_REGULAR_CHANNEL:
642 /* configure ADC regular group external trigger source */
643 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_ETSRC);
644 ADC_CTL1(adc_periph) |= (uint32_t)external_trigger_source;
645 break;
646 case ADC_INSERTED_CHANNEL:
647 /* configure ADC inserted group external trigger source */
648 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_ETSIC);
649 ADC_CTL1(adc_periph) |= (uint32_t)external_trigger_source;
650 break;
651 default:
652 break;
653 }
654 }
655
656 /*!
657 \brief enable ADC external trigger
658 \param[in] adc_periph: ADCx,x=0,1,2
659 \param[in] adc_channel_group: select the channel group
660 only one parameter can be selected which is shown as below:
661 \arg ADC_REGULAR_CHANNEL: regular channel group
662 \arg ADC_INSERTED_CHANNEL: inserted channel group
663 \param[in] trigger_mode: external trigger mode
664 only one parameter can be selected which is shown as below:
665 \arg EXTERNAL_TRIGGER_DISABLE: external trigger disable
666 \arg EXTERNAL_TRIGGER_RISING: rising edge of external trigger
667 \arg EXTERNAL_TRIGGER_FALLING: falling edge of external trigger
668 \arg EXTERNAL_TRIGGER_RISING_FALLING: rising and falling edge of external trigger
669 \param[out] none
670 \retval none
671 */
adc_external_trigger_config(uint32_t adc_periph,uint8_t adc_channel_group,uint32_t trigger_mode)672 void adc_external_trigger_config(uint32_t adc_periph, uint8_t adc_channel_group, uint32_t trigger_mode)
673 {
674 switch(adc_channel_group) {
675 case ADC_REGULAR_CHANNEL:
676 /* configure ADC regular channel group external trigger mode */
677 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_ETMRC);
678 ADC_CTL1(adc_periph) |= (uint32_t)(trigger_mode << REGULAR_TRIGGER_MODE);
679 break;
680 case ADC_INSERTED_CHANNEL:
681 /* configure ADC inserted channel group external trigger mode */
682 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_ETMIC);
683 ADC_CTL1(adc_periph) |= (uint32_t)(trigger_mode << INSERTED_TRIGGER_MODE);
684 break;
685 default:
686 break;
687 }
688 }
689
690 /*!
691 \brief enable ADC software trigger
692 \param[in] adc_periph: ADCx,x=0,1,2
693 \param[in] adc_channel_group: select the channel group
694 only one parameter can be selected which is shown as below:
695 \arg ADC_REGULAR_CHANNEL: regular channel group
696 \arg ADC_INSERTED_CHANNEL: inserted channel group
697 \param[out] none
698 \retval none
699 */
adc_software_trigger_enable(uint32_t adc_periph,uint8_t adc_channel_group)700 void adc_software_trigger_enable(uint32_t adc_periph, uint8_t adc_channel_group)
701 {
702 switch(adc_channel_group) {
703 case ADC_REGULAR_CHANNEL:
704 /* enable ADC regular channel group software trigger */
705 ADC_CTL1(adc_periph) |= (uint32_t)ADC_CTL1_SWRCST;
706 break;
707 case ADC_INSERTED_CHANNEL:
708 /* enable ADC inserted channel group software trigger */
709 ADC_CTL1(adc_periph) |= (uint32_t)ADC_CTL1_SWICST;
710 break;
711 default:
712 break;
713 }
714 }
715
716 /*!
717 \brief configure end of conversion mode
718 \param[in] adc_periph: ADCx,x=0,1,2
719 \param[in] end_selection: end of conversion mode
720 only one parameter can be selected which is shown as below:
721 \arg ADC_EOC_SET_SEQUENCE: only at the end of a sequence of regular conversions, the EOC bit is set.Overflow detection is disabled unless DMA=1.
722 \arg ADC_EOC_SET_CONVERSION: at the end of each regular conversion, the EOC bit is set.Overflow is detected automatically.
723 \param[out] none
724 \retval none
725 */
adc_end_of_conversion_config(uint32_t adc_periph,uint8_t end_selection)726 void adc_end_of_conversion_config(uint32_t adc_periph, uint8_t end_selection)
727 {
728 switch(end_selection) {
729 case ADC_EOC_SET_SEQUENCE:
730 /* only at the end of a sequence of regular conversions, the EOC bit is set */
731 ADC_CTL1(adc_periph) &= ~((uint32_t)ADC_CTL1_EOCM);
732 break;
733 case ADC_EOC_SET_CONVERSION:
734 /* at the end of each regular conversion, the EOC bit is set.Overflow is detected automatically */
735 ADC_CTL1(adc_periph) |= (uint32_t)(ADC_CTL1_EOCM);
736 break;
737 default:
738 break;
739 }
740 }
741
742 /*!
743 \brief read ADC regular group data register
744 \param[in] adc_periph: ADCx,x=0,1,2
745 \param[in] none
746 \param[out] none
747 \retval the conversion value
748 */
adc_regular_data_read(uint32_t adc_periph)749 uint16_t adc_regular_data_read(uint32_t adc_periph)
750 {
751 return (uint16_t)(ADC_RDATA(adc_periph));
752 }
753
754 /*!
755 \brief read ADC inserted group data register
756 \param[in] adc_periph: ADCx,x=0,1,2
757 \param[in] inserted_channel : insert channel select
758 only one parameter can be selected which is shown as below:
759 \arg ADC_INSERTED_CHANNEL_0: inserted Channel0
760 \arg ADC_INSERTED_CHANNEL_1: inserted channel1
761 \arg ADC_INSERTED_CHANNEL_2: inserted Channel2
762 \arg ADC_INSERTED_CHANNEL_3: inserted Channel3
763 \param[out] none
764 \retval the conversion value
765 */
adc_inserted_data_read(uint32_t adc_periph,uint8_t inserted_channel)766 uint16_t adc_inserted_data_read(uint32_t adc_periph, uint8_t inserted_channel)
767 {
768 uint32_t idata;
769 /* read the data of the selected channel */
770 switch(inserted_channel) {
771 case ADC_INSERTED_CHANNEL_0:
772 /* read the data of channel 0 */
773 idata = ADC_IDATA0(adc_periph);
774 break;
775 case ADC_INSERTED_CHANNEL_1:
776 /* read the data of channel 1 */
777 idata = ADC_IDATA1(adc_periph);
778 break;
779 case ADC_INSERTED_CHANNEL_2:
780 /* read the data of channel 2 */
781 idata = ADC_IDATA2(adc_periph);
782 break;
783 case ADC_INSERTED_CHANNEL_3:
784 /* read the data of channel 3 */
785 idata = ADC_IDATA3(adc_periph);
786 break;
787 default:
788 idata = 0U;
789 break;
790 }
791 return (uint16_t)idata;
792 }
793
794 /*!
795 \brief disable ADC analog watchdog single channel
796 \param[in] adc_periph: ADCx,x=0,1,2
797 \param[out] none
798 \retval none
799 */
adc_watchdog_single_channel_disable(uint32_t adc_periph)800 void adc_watchdog_single_channel_disable(uint32_t adc_periph)
801 {
802 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_WDSC);
803 }
804
805 /*!
806 \brief enable ADC analog watchdog single channel
807 \param[in] adc_periph: ADCx,x=0,1,2
808 \param[in] adc_channel: the selected ADC channel
809 only one parameter can be selected which is shown as below:
810 \arg ADC_CHANNEL_x: ADC Channelx(x=0..18)
811 \param[out] none
812 \retval none
813 */
adc_watchdog_single_channel_enable(uint32_t adc_periph,uint8_t adc_channel)814 void adc_watchdog_single_channel_enable(uint32_t adc_periph, uint8_t adc_channel)
815 {
816 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_WDCHSEL);
817
818 /* analog watchdog channel select */
819 ADC_CTL0(adc_periph) |= (uint32_t)adc_channel;
820 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_WDSC;
821 }
822
823 /*!
824 \brief configure ADC analog watchdog group channel
825 \param[in] adc_periph: ADCx,x=0,1,2
826 \param[in] adc_channel_group: the channel group use analog watchdog
827 only one parameter can be selected which is shown as below:
828 \arg ADC_REGULAR_CHANNEL: regular channel group
829 \arg ADC_INSERTED_CHANNEL: inserted channel group
830 \arg ADC_REGULAR_INSERTED_CHANNEL: both regular and inserted group
831 \param[out] none
832 \retval none
833 */
adc_watchdog_group_channel_enable(uint32_t adc_periph,uint8_t adc_channel_group)834 void adc_watchdog_group_channel_enable(uint32_t adc_periph, uint8_t adc_channel_group)
835 {
836 ADC_CTL0(adc_periph) &= ~((uint32_t)(ADC_CTL0_RWDEN | ADC_CTL0_IWDEN | ADC_CTL0_WDSC));
837 /* select the group */
838 switch(adc_channel_group) {
839 case ADC_REGULAR_CHANNEL:
840 /* regular channel analog watchdog enable */
841 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_RWDEN;
842 break;
843 case ADC_INSERTED_CHANNEL:
844 /* inserted channel analog watchdog enable */
845 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_IWDEN;
846 break;
847 case ADC_REGULAR_INSERTED_CHANNEL:
848 /* regular and inserted channel analog watchdog enable */
849 ADC_CTL0(adc_periph) |= (uint32_t)(ADC_CTL0_RWDEN | ADC_CTL0_IWDEN);
850 break;
851 default:
852 break;
853 }
854 }
855
856 /*!
857 \brief disable ADC analog watchdog
858 \param[in] adc_periph: ADCx,x=0,1,2
859 \param[in] adc_channel_group: the channel group use analog watchdog
860 only one parameter can be selected which is shown as below:
861 \arg ADC_REGULAR_CHANNEL: regular channel group
862 \arg ADC_INSERTED_CHANNEL: inserted channel group
863 \arg ADC_REGULAR_INSERTED_CHANNEL: both regular and inserted group
864 \param[out] none
865 \retval none
866 */
adc_watchdog_disable(uint32_t adc_periph,uint8_t adc_channel_group)867 void adc_watchdog_disable(uint32_t adc_periph, uint8_t adc_channel_group)
868 {
869 /* select the group */
870 switch(adc_channel_group) {
871 case ADC_REGULAR_CHANNEL:
872 /* disable ADC analog watchdog regular channel group */
873 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_RWDEN);
874 break;
875 case ADC_INSERTED_CHANNEL:
876 /* disable ADC analog watchdog inserted channel group */
877 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_IWDEN);
878 break;
879 case ADC_REGULAR_INSERTED_CHANNEL:
880 /* disable ADC analog watchdog regular and inserted channel group */
881 ADC_CTL0(adc_periph) &= ~((uint32_t)(ADC_CTL0_RWDEN | ADC_CTL0_IWDEN));
882 break;
883 default:
884 break;
885 }
886 }
887
888 /*!
889 \brief configure ADC analog watchdog threshold
890 \param[in] adc_periph: ADCx,x=0,1,2
891 \param[in] low_threshold: analog watchdog low threshold,0..4095
892 \param[in] high_threshold: analog watchdog high threshold,0..4095
893 \param[out] none
894 \retval none
895 */
adc_watchdog_threshold_config(uint32_t adc_periph,uint16_t low_threshold,uint16_t high_threshold)896 void adc_watchdog_threshold_config(uint32_t adc_periph, uint16_t low_threshold, uint16_t high_threshold)
897 {
898 /* configure ADC analog watchdog low threshold */
899 ADC_WDLT(adc_periph) = (uint32_t)WDLT_WDLT(low_threshold);
900 /* configure ADC analog watchdog high threshold */
901 ADC_WDHT(adc_periph) = (uint32_t)WDHT_WDHT(high_threshold);
902 }
903
904 /*!
905 \brief get the ADC flag bits
906 \param[in] adc_periph: ADCx,x=0,1,2
907 \param[in] adc_flag: the adc flag bits
908 only one parameter can be selected which is shown as below:
909 \arg ADC_FLAG_WDE: analog watchdog event flag
910 \arg ADC_FLAG_EOC: end of group conversion flag
911 \arg ADC_FLAG_EOIC: end of inserted group conversion flag
912 \arg ADC_FLAG_STIC: start flag of inserted channel group
913 \arg ADC_FLAG_STRC: start flag of regular channel group
914 \arg ADC_FLAG_ROVF: regular data register overflow flag
915 \param[out] none
916 \retval FlagStatus: SET or RESET
917 */
adc_flag_get(uint32_t adc_periph,uint32_t adc_flag)918 FlagStatus adc_flag_get(uint32_t adc_periph, uint32_t adc_flag)
919 {
920 FlagStatus reval = RESET;
921 if(ADC_STAT(adc_periph) & adc_flag) {
922 reval = SET;
923 }
924 return reval;
925
926 }
927
928 /*!
929 \brief clear the ADC flag bits
930 \param[in] adc_periph: ADCx,x=0,1,2
931 \param[in] adc_flag: the adc flag bits
932 only one parameter can be selected which is shown as below:
933 \arg ADC_FLAG_WDE: analog watchdog event flag
934 \arg ADC_FLAG_EOC: end of group conversion flag
935 \arg ADC_FLAG_EOIC: end of inserted group conversion flag
936 \arg ADC_FLAG_STIC: start flag of inserted channel group
937 \arg ADC_FLAG_STRC: start flag of regular channel group
938 \arg ADC_FLAG_ROVF: regular data register overflow flag
939 \param[out] none
940 \retval none
941 */
adc_flag_clear(uint32_t adc_periph,uint32_t adc_flag)942 void adc_flag_clear(uint32_t adc_periph, uint32_t adc_flag)
943 {
944 ADC_STAT(adc_periph) &= ~((uint32_t)adc_flag);
945 }
946
947 /*!
948 \brief get the bit state of ADCx software start conversion
949 \param[in] adc_periph: ADCx, x=0,1,2 only one among these parameters can be selected
950 \param[in] none
951 \param[out] none
952 \retval FlagStatus: SET or RESET
953 */
adc_regular_software_startconv_flag_get(uint32_t adc_periph)954 FlagStatus adc_regular_software_startconv_flag_get(uint32_t adc_periph)
955 {
956 FlagStatus reval = RESET;
957 if((uint32_t)RESET != (ADC_STAT(adc_periph) & ADC_STAT_STRC)) {
958 reval = SET;
959 }
960 return reval;
961 }
962
963 /*!
964 \brief get the bit state of ADCx software inserted channel start conversion
965 \param[in] adc_periph: ADCx, x=0,1,2 only one among these parameters can be selected
966 \param[in] none
967 \param[out] none
968 \retval FlagStatus: SET or RESET
969 */
adc_inserted_software_startconv_flag_get(uint32_t adc_periph)970 FlagStatus adc_inserted_software_startconv_flag_get(uint32_t adc_periph)
971 {
972 FlagStatus reval = RESET;
973 if((uint32_t)RESET != (ADC_STAT(adc_periph) & ADC_STAT_STIC)) {
974 reval = SET;
975 }
976 return reval;
977 }
978
979 /*!
980 \brief get the ADC interrupt bits
981 \param[in] adc_periph: ADCx,x=0,1,2
982 \param[in] adc_interrupt: the adc interrupt bits
983 only one parameter can be selected which is shown as below:
984 \arg ADC_INT_FLAG_WDE: analog watchdog interrupt
985 \arg ADC_INT_FLAG_EOC: end of group conversion interrupt
986 \arg ADC_INT_FLAG_EOIC: end of inserted group conversion interrupt
987 \arg ADC_INT_FLAG_ROVF: regular data register overflow interrupt
988 \param[out] none
989 \retval FlagStatus: SET or RESET
990 */
adc_interrupt_flag_get(uint32_t adc_periph,uint32_t adc_interrupt)991 FlagStatus adc_interrupt_flag_get(uint32_t adc_periph, uint32_t adc_interrupt)
992 {
993 FlagStatus interrupt_flag = RESET;
994 uint32_t state;
995 /* check the interrupt bits */
996 switch(adc_interrupt) {
997 case ADC_INT_FLAG_WDE:
998 /* get the ADC analog watchdog interrupt bits */
999 state = ADC_STAT(adc_periph) & ADC_STAT_WDE;
1000 if((ADC_CTL0(adc_periph) & ADC_CTL0_WDEIE) && state) {
1001 interrupt_flag = SET;
1002 }
1003 break;
1004 case ADC_INT_FLAG_EOC:
1005 /* get the ADC end of group conversion interrupt bits */
1006 state = ADC_STAT(adc_periph) & ADC_STAT_EOC;
1007 if((ADC_CTL0(adc_periph) & ADC_CTL0_EOCIE) && state) {
1008 interrupt_flag = SET;
1009 }
1010 break;
1011 case ADC_INT_FLAG_EOIC:
1012 /* get the ADC end of inserted group conversion interrupt bits */
1013 state = ADC_STAT(adc_periph) & ADC_STAT_EOIC;
1014 if((ADC_CTL0(adc_periph) & ADC_CTL0_EOICIE) && state) {
1015 interrupt_flag = SET;
1016 }
1017 break;
1018 case ADC_INT_FLAG_ROVF:
1019 /* get the ADC regular data register overflow interrupt bits */
1020 state = ADC_STAT(adc_periph) & ADC_STAT_ROVF;
1021 if((ADC_CTL0(adc_periph) & ADC_CTL0_ROVFIE) && state) {
1022 interrupt_flag = SET;
1023 }
1024 break;
1025 default:
1026 break;
1027 }
1028 return interrupt_flag;
1029 }
1030
1031 /*!
1032 \brief clear the ADC flag
1033 \param[in] adc_periph: ADCx,x=0,1,2
1034 \param[in] adc_interrupt: the adc status flag
1035 only one parameter can be selected which is shown as below:
1036 \arg ADC_INT_FLAG_WDE: analog watchdog interrupt
1037 \arg ADC_INT_FLAG_EOC: end of group conversion interrupt
1038 \arg ADC_INT_FLAG_EOIC: end of inserted group conversion interrupt
1039 \arg ADC_INT_FLAG_ROVF: regular data register overflow interrupt
1040 \param[out] none
1041 \retval none
1042 */
adc_interrupt_flag_clear(uint32_t adc_periph,uint32_t adc_interrupt)1043 void adc_interrupt_flag_clear(uint32_t adc_periph, uint32_t adc_interrupt)
1044 {
1045 ADC_STAT(adc_periph) &= ~((uint32_t)adc_interrupt);
1046 }
1047
1048 /*!
1049 \brief enable ADC interrupt
1050 \param[in] adc_periph: ADCx,x=0,1,2
1051 \param[in] adc_interrupt: the adc interrupt flag
1052 only one parameter can be selected which is shown as below:
1053 \arg ADC_INT_WDE: analog watchdog interrupt flag
1054 \arg ADC_INT_EOC: end of group conversion interrupt flag
1055 \arg ADC_INT_EOIC: end of inserted group conversion interrupt flag
1056 \arg ADC_INT_ROVF: regular data register overflow interrupt flag
1057 \param[out] none
1058 \retval none
1059 */
adc_interrupt_enable(uint32_t adc_periph,uint32_t adc_interrupt)1060 void adc_interrupt_enable(uint32_t adc_periph, uint32_t adc_interrupt)
1061 {
1062 switch(adc_interrupt) {
1063 case ADC_INT_WDE:
1064 /* enable analog watchdog interrupt */
1065 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_WDEIE;
1066 break;
1067 case ADC_INT_EOC:
1068 /* enable end of group conversion interrupt */
1069 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_EOCIE;
1070 break;
1071 case ADC_INT_EOIC:
1072 /* enable end of inserted group conversion interrupt */
1073 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_EOICIE;
1074 break;
1075 case ADC_INT_ROVF:
1076 ADC_CTL0(adc_periph) |= (uint32_t) ADC_CTL0_ROVFIE;
1077 break;
1078 default:
1079 break;
1080 }
1081 }
1082
1083 /*!
1084 \brief disable ADC interrupt
1085 \param[in] adc_periph: ADCx,x=0,1,2
1086 \param[in] adc_flag: the adc interrupt flag
1087 only one parameter can be selected which is shown as below:
1088 \arg ADC_INT_WDE: analog watchdog interrupt flag
1089 \arg ADC_INT_EOC: end of group conversion interrupt flag
1090 \arg ADC_INT_EOIC: end of inserted group conversion interrupt flag
1091 \arg ADC_INT_ROVF: regular data register overflow interrupt flag
1092 \param[out] none
1093 \retval none
1094 */
adc_interrupt_disable(uint32_t adc_periph,uint32_t adc_interrupt)1095 void adc_interrupt_disable(uint32_t adc_periph, uint32_t adc_interrupt)
1096 {
1097 switch(adc_interrupt) {
1098 /* select the interrupt source */
1099 case ADC_INT_WDE:
1100 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_WDEIE);
1101 break;
1102 case ADC_INT_EOC:
1103 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_EOCIE);
1104 break;
1105 case ADC_INT_EOIC:
1106 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_EOICIE);
1107 break;
1108 case ADC_INT_ROVF:
1109 ADC_CTL0(adc_periph) &= ~((uint32_t)ADC_CTL0_ROVFIE);
1110 break;
1111 default:
1112 break;
1113 }
1114 }
1115
1116 /*!
1117 \brief configure the ADC sync mode
1118 \param[in] sync_mode: ADC sync mode
1119 only one parameter can be selected which is shown as below:
1120 \arg ADC_SYNC_MODE_INDEPENDENT: all the ADCs work independently
1121 \arg ADC_DAUL_REGULAL_PARALLEL_INSERTED_PARALLEL: ADC0 and ADC1 work in combined regular parallel & inserted parallel mode
1122 \arg ADC_DAUL_REGULAL_PARALLEL_INSERTED_ROTATION: ADC0 and ADC1 work in combined regular parallel & trigger rotation mode
1123 \arg ADC_DAUL_INSERTED_PARALLEL: ADC0 and ADC1 work in inserted parallel mode
1124 \arg ADC_DAUL_REGULAL_PARALLEL: ADC0 and ADC1 work in regular parallel mode
1125 \arg ADC_DAUL_REGULAL_FOLLOW_UP: ADC0 and ADC1 work in follow-up mode
1126 \arg ADC_DAUL_INSERTED_TRRIGGER_ROTATION: ADC0 and ADC1 work in trigger rotation mode
1127 \arg ADC_ALL_REGULAL_PARALLEL_INSERTED_PARALLEL: all ADCs work in combined regular parallel & inserted parallel mode
1128 \arg ADC_ALL_REGULAL_PARALLEL_INSERTED_ROTATION: all ADCs work in combined regular parallel & trigger rotation mode
1129 \arg ADC_ALL_INSERTED_PARALLEL: all ADCs work in inserted parallel mode
1130 \arg ADC_ALL_REGULAL_PARALLEL: all ADCs work in regular parallel mode
1131 \arg ADC_ALL_REGULAL_FOLLOW_UP: all ADCs work in follow-up mode
1132 \arg ADC_ALL_INSERTED_TRRIGGER_ROTATION: all ADCs work in trigger rotation mode
1133 \param[out] none
1134 \retval none
1135 */
adc_sync_mode_config(uint32_t sync_mode)1136 void adc_sync_mode_config(uint32_t sync_mode)
1137 {
1138 ADC_SYNCCTL &= ~(ADC_SYNCCTL_SYNCM);
1139 ADC_SYNCCTL |= sync_mode;
1140 }
1141
1142 /*!
1143 \brief configure the delay between 2 sampling phases in ADC sync modes
1144 \param[in] sample_delay: the delay between 2 sampling phases in ADC sync modes
1145 only one parameter can be selected which is shown as below:
1146 \arg ADC_SYNC_DELAY_xCYCLE: x=5..20,the delay between 2 sampling phases in ADC sync modes is x ADC clock cycles
1147 \param[out] none
1148 \retval none
1149 */
adc_sync_delay_config(uint32_t sample_delay)1150 void adc_sync_delay_config(uint32_t sample_delay)
1151 {
1152 ADC_SYNCCTL &= ~(ADC_SYNCCTL_SYNCDLY);
1153 ADC_SYNCCTL |= sample_delay;
1154 }
1155
1156 /*!
1157 \brief configure ADC sync DMA mode selection
1158 \param[in] dma_mode: ADC sync DMA mode
1159 only one parameter can be selected which is shown as below:
1160 \arg ADC_SYNC_DMA_DISABLE: ADC sync DMA disabled
1161 \arg ADC_SYNC_DMA_MODE0: ADC sync DMA mode 0
1162 \arg ADC_SYNC_DMA_MODE1: ADC sync DMA mode 1
1163 \param[out] none
1164 \retval none
1165 */
adc_sync_dma_config(uint32_t dma_mode)1166 void adc_sync_dma_config(uint32_t dma_mode)
1167 {
1168 ADC_SYNCCTL &= ~(ADC_SYNCCTL_SYNCDMA);
1169 ADC_SYNCCTL |= dma_mode;
1170 }
1171
1172 /*!
1173 \brief configure ADC sync DMA engine is disabled after the end of transfer signal from DMA controller is detected
1174 \param[in] none
1175 \param[out] none
1176 \retval none
1177 */
adc_sync_dma_request_after_last_enable(void)1178 void adc_sync_dma_request_after_last_enable(void)
1179 {
1180 ADC_SYNCCTL |= ADC_SYNCCTL_SYNCDDM;
1181 }
1182
1183 /*!
1184 \brief configure ADC sync DMA engine issues requests according to the SYNCDMA bits
1185 \param[in] none
1186 \param[out] none
1187 \retval none
1188 */
adc_sync_dma_request_after_last_disable(void)1189 void adc_sync_dma_request_after_last_disable(void)
1190 {
1191 ADC_SYNCCTL &= ~(ADC_SYNCCTL_SYNCDDM);
1192 }
1193
1194 /*!
1195 \brief read ADC sync regular data register
1196 \param[in] none
1197 \param[out] none
1198 \retval sync regular data
1199 */
adc_sync_regular_data_read(void)1200 uint32_t adc_sync_regular_data_read(void)
1201 {
1202 return (uint32_t)ADC_SYNCDATA;
1203 }
1204