系统电池供电,3.6V电池,经过一个二极管(3A),大概是3.3V到Vbat . 测量电压为2.98V 左右。 继续采用直流电源供电,当输入Vbat 3.0v 时,测量为 2.86V左右。 同时还发现一些怪现象,aADCxConvertedData[0],明显比后续的采集值小很多。! S5 I! S& C, u# X5 z 哪里操作有问题?- m; F! O7 K! g% S1 R3 q ! J8 a* `$ G( k# Y åçå¾ /* Definition of ADCx conversions data table size */ #define ADC_CONVERTED_DATA_BUFFER_SIZE ((uint32_t) 10) /* Size of array aADCxConvertedData[] */ static uint16_t aADCxConvertedData[ADC_CONVERTED_DATA_BUFFER_SIZE];0 u: r3 G& P1 { /**6 W. o1 y4 H' o9 l4 ]0 @ * @brief Conversion complete callback in non-blocking mode." Q# G- d3 }% ]# { * @param hadc ADC handle9 c1 ] g7 g8 v; H0 p7 d4 {8 j% U * @retval None */: F e! F0 c& {$ K# c0 | void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc)/ k1 ^4 K7 V1 x" _4 \, O8 E {" [3 O1 Y7 B5 n& L* H /* Prevent unused argument(s) compilation warning *// ^' h1 w. i% _' G' A' z5 k if(BinarySem_ADCHandle) osSemaphoreRelease(BinarySem_ADCHandle); 1 i; |& q/ ^( f. ]# f /* NOTE : This function should not be modified. When the callback is needed,5 [. G$ Q4 W6 n6 ^4 O- y! b function HAL_ADC_ConvCpltCallback must be implemented in the user file. */ }4 o4 g- d4 I! a7 V2 { /**, ~* e* ^/ ~( a* l* @7 \+ ` * @brief 测量电池电压 * @param[IN], T2 p, m; A( U$ n- e * @retval None */5 x4 `1 ^4 ?! ~5 w$ H uint32_t getBattaryTemperatureMeasure(uint8_t bat_flag)8 p2 E2 a! I! N. w. f7 I# h { ADC_ChannelConfTypeDef sConfig = {0}; memset(aADCxConvertedData,0,sizeof(aADCxConvertedData)); /* ### - 1 - Initialize ADC peripheral #################################### */2 Y/ T3 N" c$ } hadc1.Instance = ADC1; if (HAL_ADC_DeInit(&hadc1) != HAL_OK)+ x. Y5 R: |; l4 d+ H7 @+ I {; G0 c7 ~) s9 P: D! Z5 w9 Q/ S, i% ` /* ADC de-initialization Error */ {& z2 z5 W2 q5 P8 y Error_Handler();, B$ n3 C" n7 R, v/ H } hadc1.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV1; /* Synchronous clock mode, input ADC clock divided by 2*/ hadc1.Init.Resolution = ADC_RESOLUTION_12B; /* 12-bit resolution for converted data */ hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT; /* Right-alignment for converted data */ hadc1.Init.ScanConvMode = DISABLE; /* Sequencer disabled (ADC conversion on only 1 channel: channel set on rank 1) */ hadc1.Init.EOCSelection = ADC_EOC_SINGLE_CONV; /* EOC flag picked-up to indicate conversion end */1 F5 b1 R5 S* L" n; c: [- u6 }' f& U. } hadc1.Init.LowPowerAutoWait = DISABLE; /* Auto-delayed conversion feature disabled */ hadc1.Init.ContinuousConvMode = ENABLE; /* Continuous mode enabled (automatic conversion restart after each conversion) */ hadc1.Init.NbrOfConversion = 1; /* Parameter discarded because sequencer is disabled */4 _- e* ~* ?% {. z3 b. [ hadc1.Init.DiscontinuousConvMode = DISABLE; /* Parameter discarded because sequencer is disabled */0 i9 o% M; W c y2 S7 ] hadc1.Init.NbrOfDiscConversion = 1; /* Parameter discarded because sequencer is disabled */ hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START; /* Software start to trig the 1st conversion manually, without external event */ hadc1.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE; /* Parameter discarded because software trigger chosen */ hadc1.Init.DMAContinuousRequests = ENABLE; /* ADC DMA continuous request to match with DMA circular mode */ hadc1.Init.Overrun = ADC_OVR_DATA_OVERWRITTEN; /* DR register is overwritten with the last conversion result in case of overrun */4 p; }+ }7 ] B$ A) a hadc1.Init.OversamplingMode = DISABLE; /* No oversampling */+ |! ?5 J* e: `9 K! q+ e /* Initialize ADC peripheral according to the passed parameters */* U* `8 D. D* c/ ?$ ?6 a if (HAL_ADC_Init(&hadc1) != HAL_OK) {/ L9 K l- u, g6 M- J Error_Handler(); }, `" l( n7 j* X. T, S : p6 u, i5 D7 g4 e8 i , H) M* G; D& c/ t6 J4 D /* ### - 2 - Start calibration ############################################ */0 a) `& ~. m9 `6 `: d; N+ R% { if (HAL_ADCEx_Calibration_Start(&hadc1, ADC_SINGLE_ENDED) != HAL_OK) { Error_Handler(); } /* ### - 3 - Channel configuration ######################################## */" R/ {# H$ V; F5 q, W sConfig.Channel = ADC_CHANNEL_VBAT; /* Sampled channel number */ sConfig.Rank = ADC_REGULAR_RANK_1; /* Rank of sampled channel number ADCx_CHANNEL */ sConfig.SamplingTime = ADC_SAMPLETIME_6CYCLES_5; /* Sampling time (number of clock cycles unit) */ sConfig.SingleDiff = ADC_SINGLE_ENDED; /* Single-ended input channel */ sConfig.OffsetNumber = ADC_OFFSET_NONE; /* No offset subtraction */ sConfig.Offset = 0; /* Parameter discarded because offset correction is disabled */ if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK) {( q: G/ d4 E2 W Error_Handler();6 c/ g0 d$ v( W) z4 G1 f } /* ### - 4 - Start conversion in DMA mode ################################# */3 `; Z* s1 S/ C2 _% J& f5 O if (HAL_ADC_Start_DMA(&hadc1, (uint32_t *)aADCxConvertedData,5 h% W+ o$ h) z ADC_CONVERTED_DATA_BUFFER_SIZE ) != HAL_OK) {8 S- Y, E8 o% u* F! M/ G: e Error_Handler();! @4 {4 x% Z% p& ~ } uint32_t ret = 0 ;8 Y+ X- X4 d0 J6 _$ v5 F if(osOK == osSemaphoreWait(BinarySem_ADCHandle,10))( D$ x% t1 ~( O7 ]3 i {( K* ^. S1 r1 e uint32_t adc_val = 0;//aADCxConvertedData[1]; for (int i = ADC_CONVERTED_DATA_BUFFER_SIZE/2 ; i < ADC_CONVERTED_DATA_BUFFER_SIZE ; i++)9 D3 \: M& j1 O9 d* u {& B# u: ?/ Q5 Q0 G z& _8 W adc_val += aADCxConvertedData; }$ Y% z0 d, p+ \7 a" T6 q9 f adc_val = adc_val / (ADC_CONVERTED_DATA_BUFFER_SIZE/2);) j: b5 g; n& f5 r: i ret = __HAL_ADC_CALC_DATA_TO_VOLTAGE(2500,adc_val,ADC_RESOLUTION_12B);4 ~1 d8 A) L9 R K) x' N ret *= 3;$ ]- [3 P2 M, a+ w } 1 Z7 |6 X6 z6 a3 J) g1 U$ z return (ret);. p6 s! p) s9 }' D1 d/ D3 `4 Z0 O6 S } " i. ]' X% ?, f* n5 T# G |
通过两天调试,讲采样周期设置长一些,比较接近了。要大于 ADC_SAMPLETIME_12CYCLES_5 。技术支持一直没响应。 |