项目上要用到STM32L071 ,很简单的采集4个通道的ADC值。网上找了一下什么IT模式,DMA模式.....太多了,太麻烦。我们的应用很简单,就是每隔1秒采集一下ADC IN0,ADC IN1, 内部参考电压, 内部温度传感器4个通道。4 z4 p6 w! |$ u8 W- x+ ^7 \* w
首先是ADC初始化,用到了Vrefint,和内部温度传感器。% D- P0 R1 m' Z
; N" K% i/ Z4 p, p ^ z- /* ADC init function */
) t+ M9 x, d" f/ O4 m$ { - void MX_ADC_Init(void)
) K; b" t% i" o% @2 z1 Z! a; f - {
- F3 T e4 ^9 y* ^. A
' J. d1 l1 z0 x3 \7 j/ l- ADC_ChannelConfTypeDef sConfig;
3 `( T7 d. W0 M7 ^7 o$ ~3 F
G; r1 M- E4 |+ X2 M0 \, t- /**Configure the global features of the ADC (Clock, Resolution, Data Alignment and number of conversion)
7 ]; W' a+ w% S1 R - */
6 a* A3 F' J8 `5 g* A% V) ^ - hadc.Instance = ADC1;/ _- R/ z) {, f0 S! `6 J
- hadc.Init.OversamplingMode = DISABLE;
' w6 @2 j* Y% j- T$ e - hadc.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV2;* X1 s) O0 N e& Y5 C& E7 a
- hadc.Init.Resolution = ADC_RESOLUTION_12B;2 ?" A: q7 `# n. H1 ?2 @9 Q
- hadc.Init.SamplingTime = ADC_SAMPLETIME_160CYCLES_5;* ~, z9 S9 m$ t/ r, y/ J1 ~
- hadc.Init.ScanConvMode = ADC_SCAN_DIRECTION_FORWARD;
" p' B0 E# l% ]* W# o& c# @ - hadc.Init.DataAlign = ADC_DATAALIGN_RIGHT;7 t9 h" \+ S& |
- hadc.Init.ContinuousConvMode = DISABLE;
3 e+ M# c1 \# D( r - hadc.Init.DiscontinuousConvMode = ENABLE;
8 x; B9 `) W3 r/ }0 `6 E f - hadc.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;1 w: K. C5 t+ q& H0 z0 i
- hadc.Init.ExternalTrigConv = ADC_SOFTWARE_START;
5 M7 o- d5 I# m - hadc.Init.DMAContinuousRequests = DISABLE;6 n5 `1 L) t- @0 w( z( {
- hadc.Init.EOCSelection = ADC_EOC_SINGLE_CONV;' e% p6 Z$ _2 T } ~
- hadc.Init.Overrun = ADC_OVR_DATA_PRESERVED;
7 a [) y; i; w8 W - hadc.Init.LowPowerAutoWait = DISABLE; p- c# @. h3 w- W! J% N5 f
- hadc.Init.LowPowerFrequencyMode = DISABLE;
8 `0 ]" c5 |5 k# Q$ i! o - hadc.Init.LowPowerAutoPowerOff = DISABLE;
% v+ ]) m3 |' |# ~0 F% a - if (HAL_ADC_Init(&hadc) != HAL_OK)
5 ?- I2 {1 A( Y( z - {& F5 l0 }5 A7 Q" y, {; ~+ x3 M/ X, ]
- _Error_Handler(__FILE__, __LINE__);2 \) A) P6 }) Q4 a9 V1 ?
- }
2 L/ n* d6 }% P7 v$ d - /* 校正ADC */& o' H; Q, Y" L g+ u
- if(HAL_ADCEx_Calibration_Start(&hadc, ADC_SINGLE_ENDED) != HAL_OK), ` G( h- G1 e( r' j
- {" f$ n' f# I, B# _
- _Error_Handler(__FILE__, __LINE__);
% E8 e* p/ _5 H( Z: q' R. ]* T* E - }% M4 k8 x$ ~) v$ A
- , n, E- n1 h% r" m' M+ @: M
- /**Configure for the selected ADC regular channel 0 to be converted.*/5 v- S y" D/ A" l. u2 ~: U
- sConfig.Channel = ADC_CHANNEL_0;9 P8 `& f y9 \* V' @
- sConfig.Rank = ADC_RANK_CHANNEL_NUMBER;
! F0 v$ e. c7 y: z - if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
$ \ {+ n2 }/ u0 v6 c - {
2 h L; G, V3 i8 [! U& j" S) k- T - _Error_Handler(__FILE__, __LINE__);8 e, n( D$ i& N$ V8 q
- }- W+ Y& ^2 G o
- /**Configure for the selected ADC regular channel 1 to be converted.*/7 v$ }0 n' q$ c4 W+ e% x# P. J
- sConfig.Channel = ADC_CHANNEL_1;9 d) b5 M3 |" L$ g
- if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
+ i4 B. f5 @+ M3 U8 v) P - {
4 T& a# G; ^% c3 d8 W1 I - _Error_Handler(__FILE__, __LINE__);
; H' _+ Z0 {. Y, t0 v - }
! ?+ M5 y$ E) ~3 D8 J3 K9 T3 h -
% M7 S& W+ B( @- R# D - /**Configure for the selected ADC regular channel 17 to be converted.*/
6 W* Z: s" J" N9 W4 w - sConfig.Channel = ADC_CHANNEL_VREFINT;: I5 w, _; x- u6 u" E; M( [) \5 v
- if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
1 S b" [$ L8 q+ T% v - {
: M/ ^% E" H7 b9 v - _Error_Handler(__FILE__, __LINE__);
; P) Q/ O5 S% T% |/ o7 o, C - }
4 ?! ? W/ z* M7 P+ c8 k: H- [5 G - # G" q3 p/ o# G z1 Y
- /**Configure for the selected ADC regular channel 18 to be converted.*/
$ y0 g* A* M* b9 ^: T5 d - sConfig.Channel = ADC_CHANNEL_TEMPSENSOR;
6 s! {; ~% {; H: \8 a# I - if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)" v1 {. e4 n7 E2 m4 q
- {2 {# V# X$ {) }2 W. \
- _Error_Handler(__FILE__, __LINE__);
- P" [% U, Q5 P3 c7 Z - }2 n3 A* O% [7 x) e. q4 _
-
0 E4 T. d! \2 A; I6 s$ X" s. X. a - HAL_ADCEx_EnableVREFINT();6 o4 @% K, O, e! \' O: p" a+ L
- HAL_ADCEx_EnableVREFINTTempSensor();
3 y% j) K# }- \9 [2 K - }
复制代码
7 k. a4 S8 `7 i( B a+ y n3 P6 i- b# j; v6 |8 z
- m" Q M6 q( e$ v8 f$ w
1 H3 J" Z2 _ [ADC采样函数5 m4 y* A) U: N' D7 s* y) D
- /* Private functions ---------------------------------------------------------*/ N4 ~' Z/ N g8 ]/ X
- #define RES1 10000 //分压电阻R1,10K
. e* k. e0 y% ~& A - #define RES2 10000 //分压电阻R2,10K
: I: i( M' s/ f4 m. y) R, Y: J3 O - #define PRATIO (RES1+RES2)/(RES2)% v' |) D, K. J7 |/ ^' p6 G
, {4 a+ `2 `8 A+ M. a- #define ADC_12BIT 4095.0
- z/ m& U. W. l0 d - #define ADC_REF 3.3
4 k j* }- c1 v$ Y - / f5 X! P5 ?' Y! z% Y5 x
- #define VOL_RADIO ADC_REF/ADC_12BIT //无电阻分压模式系数
3 g$ T: g2 p2 S2 l( S - #define BAT_RADIO (ADC_REF*PRATIO)/ADC_12BIT //电阻分压模式系数
9 y6 k: _/ E; {% V2 n6 {# E) U - , \7 \' l: V" P0 s
- //温度校正! ]+ M0 Q- H; v. i
- #define TEMP130_CAL_ADDR ((uint16_t*) ((uint32_t) 0x1FF8007E))
2 w5 f+ R$ o6 e& q - #define TEMP30_CAL_ADDR ((uint16_t*) ((uint32_t) 0x1FF8007A))% Q9 F6 ?; `7 p& b6 e" p* ?, H
- #define VDD_CALIB ((uint16_t) (300))
) }9 n' x0 a$ s - #define VDD_APPLI ((uint16_t) (330))
( d+ J# g3 `+ {+ Y' C - /*******************************************************************************/ M% [/ a1 K# p& F6 Q8 [( K9 t& p5 @
- * Function Name : ComputeTemperature$ F( b, v* i9 v% O: C
- * Description : Compute STM32 Temperature
2 H# \7 ~2 X. |. l - * Input : None/ _0 M% m* F- \7 b
- * Output : None( q N- V8 Z9 a6 g3 S! x. ?, z
- * Return : None
_* J$ }% w# Q+ d - *******************************************************************************/6 @( d1 t" r9 Q/ v/ d0 |7 Q5 b
- int32_t ComputeTemperature(uint32_t measure)
6 e" @ z- [" ~8 \$ Y U8 E - {
, d) A/ F; P+ ~9 ], S - int32_t temperature;
7 E) _" \+ i/ I3 r, ~ - temperature = ((measure * VDD_APPLI / VDD_CALIB)- (int32_t) *TEMP30_CAL_ADDR );4 L7 V( q4 K5 i) @. ?" ~
- temperature = temperature * (int32_t)(130 - 30);
( a" j" v! W: J% I" o+ { - temperature = temperature / (int32_t)(*TEMP130_CAL_ADDR - *TEMP30_CAL_ADDR);
( Z* F5 q( S! E: Y" \, T - temperature = temperature + 30;
" E0 L( L9 J0 n: }& Y! H4 Q3 ?4 n e - return(temperature);
5 A+ z" s% H* s& j1 } - }
+ O6 V/ ]% Z6 d, L5 ? - /*******************************************************************************
, s9 V# D6 p- o8 y - * Function Name : Get_Adc
8 O6 [! k4 e6 m! ~ - * Description : get voltage
: X) f2 v% S$ l2 r - * Input : None
$ m! r& k3 o9 y& B - * Output : None: m- E* i+ A. r" k
- * Return : None) y7 ?; F3 d# u2 i7 K
- *******************************************************************************/
& r+ V! f7 F% T: I3 D - void Get_Adc(void): h G' `2 D$ U) V
- {: G+ T% `* @, a- j) \) P9 F
- u32 adc_value;2 T' Z! d2 b( s; V% l
- adc_value = 0;
* y. E3 S, M8 B
2 U" P5 |, V4 f- /*Start the conversion process*/
" P" ^9 S# Y7 L) O- M" H - if (HAL_ADC_Start(&hadc) != HAL_OK)# C, g6 z$ T+ @7 I
- {4 Z. ]5 k* p$ {
- /* Start Conversation Error */
/ d) U" K/ t9 b' c7 b - Error_Handler();
5 b6 Q+ O5 L+ w) y - }6 n5 _7 b$ u. s* \7 O9 n# s% J
- HAL_ADC_PollForConversion(&hadc, 50);
: a8 `0 T$ n# w9 e) H" k/ b - /* Check if the continous conversion of regular channel is finished */8 k) a. ]- `# l( R/ F! ~
- if ((HAL_ADC_GetState(&hadc) & HAL_ADC_STATE_REG_EOC) == HAL_ADC_STATE_REG_EOC)8 i v2 X0 k" Y6 u9 h2 d5 ^+ O
- {9 z/ s! b: B- F+ c; X$ ~' Q( ~
- /*Get the converted value of regular channel */
% t* N3 A& Y" T. [% ` - adc_value = HAL_ADC_GetValue(&hadc);1 `1 T- \( H0 J1 { p+ g
- }
; ]3 l$ e6 f3 ]; d9 E - printf("DEBUG: ADC CHANNEL 0 = %fV\r\n", BAT_RADIO*adc_value); //ADC 通道0 用10K,10K电阻分压 z- Y4 x0 h# _( z9 U" L
) W, m1 j4 V' i- 2 A, n0 p0 U$ B) J7 N
- /*Start the conversion process*/
& _" L$ D) T9 V/ |6 j/ U6 h" `) H+ r - if (HAL_ADC_Start(&hadc) != HAL_OK)
/ H+ Z: d; _, _& U9 Z" N6 U/ R9 a - { F P: j) d; M. J
- /* Start Conversation Error */
& M( B- o% _ F* h: R - Error_Handler();
( U6 b. g% E( h% p& o1 L - }
: ~/ s1 n4 S/ J3 f* I - HAL_ADC_PollForConversion(&hadc, 50); 9 \5 x5 Z, C5 W' C% {2 e
- /* Check if the continous conversion of regular channel is finished */
% Z' I% }) g: M V( ]( R, m - if ((HAL_ADC_GetState(&hadc) & HAL_ADC_STATE_REG_EOC) == HAL_ADC_STATE_REG_EOC)
w4 Q" R" k$ {! o - {
) v) L2 {/ H8 h( t+ F1 p8 L1 z) H2 W - /*Get the converted value of regular channel *// b( C. Y+ t9 m6 S3 _( D. o: b0 e
- adc_value = HAL_ADC_GetValue(&hadc);
; E4 Z! {7 P! t1 F - }
, ?! q& R1 q( z7 a9 T2 j4 R - printf("DEBUG: ADC CHANNEL 1 = %fV\r\n", VOL_RADIO*adc_value); //ADC 通道1 没用电阻分压
' [) l5 G) Q* r3 k8 i - ( B: f5 j$ ?2 ]# ?9 e; s4 Q2 `
-
' Y: E, w$ G0 s4 p: i - /*Start the conversion process*/ - `, x& M! d5 W( ` w* \
- if (HAL_ADC_Start(&hadc) != HAL_OK), n+ d/ d: S, h K3 H+ Z
- {
+ S0 {$ N N) Y) g9 {" ], o - /* Start Conversation Error */
6 \0 q; P) E4 m3 `- ^" J+ q - Error_Handler();
5 r+ a( H1 C; H - }
- q o) C- A9 T6 V/ G) d1 l8 o - HAL_ADC_PollForConversion(&hadc, 50); # a5 k+ q4 W$ i* F( H, u
- /* Check if the continous conversion of regular channel is finished */
9 S a* A( ~$ W, o; ?; t" M/ y3 W - if ((HAL_ADC_GetState(&hadc) & HAL_ADC_STATE_REG_EOC) == HAL_ADC_STATE_REG_EOC)4 h9 U# ^# d$ c9 Y t
- {. u% K' U1 n+ x+ T4 U0 a! A" p! K
- /*Get the converted value of regular channel */
3 h; f) j( I# ~; m9 { - adc_value = HAL_ADC_GetValue(&hadc);# K) U( X1 l/ I) R5 N* w% s2 g2 }
- }
2 ^* q3 o2 |% I5 i - printf("DEBUG: ADC CHANNEL 17 = %fV\r\n", VOL_RADIO*adc_value); //内部Vref = 1.2V" X6 ^% j7 {( Q
- # [4 }! y0 w) i# d
-
$ l1 N# F; l+ s1 |& U$ n( W4 m: R - /*Start the conversion process*/ 6 g+ c, x; {. u2 f+ X. k8 D
- if (HAL_ADC_Start(&hadc) != HAL_OK)' X r; s+ c* D1 E2 u
- {
4 S8 q/ Q+ M! ~/ n9 m - /* Start Conversation Error */8 w. k7 d! M6 j. b! D. l% t+ e' s
- Error_Handler();
~ m3 c6 p4 T$ `9 | [! u - }1 k3 U$ t& o9 b" B
- HAL_ADC_PollForConversion(&hadc, 50);
; ? _; }# i* \8 i* s- G - /* Check if the continous conversion of regular channel is finished */
) r5 b+ Q# w8 P! k2 p - if ((HAL_ADC_GetState(&hadc) & HAL_ADC_STATE_REG_EOC) == HAL_ADC_STATE_REG_EOC)' F. ]0 I* e8 b$ T. l# P+ b+ D
- {
; }) k, u- P0 C, }) w - /*Get the converted value of regular channel */6 J' U! O+ ?* N6 \* j2 ~
- adc_value = HAL_ADC_GetValue(&hadc);
+ |# I/ i3 R! I9 s4 P3 D - }' [/ q6 T% |5 c _, _
- printf("DEBUG: ADC CHANNEL 18 = %d℃\r\n", ComputeTemperature(adc_value)); //内部温度传感器) l8 p d: ]6 T0 ?( u
-
+ M/ _" o, G* q. |; h9 G8 A7 g3 K - HAL_ADC_Stop(&hadc);
3 h( T' E! n6 ~ S" } - & L2 L9 Q; e+ q+ S8 ?& |' m
- }
复制代码
% f' o3 A& n4 L# }" p9 b: n2 B$ J# G1 _# z, D! b9 x
|
ST 给的很多历程太复杂,其实大家的应用都很简单。
楼主这个怎么报错呀