2022-09-27 10:38 PM
I'm using ADC1 of STM32L452CC.
Multi ADCs are connected to 2 Potentiometers and battery level port on ADC1.
2 Potentialmeters are connected to channel 5(PA0) and 6(PA1). (pin10, pin 11)
And battery is connected to channel 16(PB1) like below.(pin 19)
However the battery level ADC value is changed continuously when other ADC value is changing.
Like below, (other adc value is flow : x , battery value is battery : x)
shutoff : 0 flow : 1 battery : 2076
shutoff : 0 flow : 1 battery : 2067
shutoff : 0 flow : 1 battery : 2069
shutoff : 0 flow : 1 battery : 2069
shutoff : 0 flow : 0 battery : 2068
shutoff : 0 flow : 1497 battery : 2148
shutoff : 0 flow : 2234 battery : 2271
shutoff : 0 flow : 2568 battery : 2285
shutoff : 0 flow : 2812 battery : 2294
shutoff : 0 flow : 3058 battery : 2301
shutoff : 0 flow : 3146 battery : 2307
shutoff : 0 flow : 3148 battery : 2308
shutoff : 0 flow : 3145 battery : 2308
I attached the source.
static void MX_ADC1_Init(void)
{
/* USER CODE BEGIN ADC1_Init 0 */
/* USER CODE END ADC1_Init 0 */
ADC_ChannelConfTypeDef sConfig = {0};
/* USER CODE BEGIN ADC1_Init 1 */
/* USER CODE END ADC1_Init 1 */
/** Common config
*/
hadc1.Instance = ADC1;
hadc1.Init.ClockPrescaler = ADC_CLOCK_ASYNC_DIV4;
hadc1.Init.Resolution = ADC_RESOLUTION_12B;
hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
hadc1.Init.ScanConvMode = ADC_SCAN_ENABLE;
hadc1.Init.EOCSelection = ADC_EOC_SINGLE_CONV;
hadc1.Init.LowPowerAutoWait = DISABLE;
hadc1.Init.ContinuousConvMode = DISABLE;
hadc1.Init.NbrOfConversion = 3;
hadc1.Init.DiscontinuousConvMode = ENABLE;
hadc1.Init.NbrOfDiscConversion = 3;
hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START;
hadc1.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
hadc1.Init.DMAContinuousRequests = DISABLE;
hadc1.Init.Overrun = ADC_OVR_DATA_PRESERVED;
hadc1.Init.OversamplingMode = DISABLE;
if (HAL_ADC_Init(&hadc1) != HAL_OK)
{
Error_Handler();
}
/** Configure Regular Channel
*/
sConfig.Channel = ADC_CHANNEL_5;
sConfig.Rank = ADC_REGULAR_RANK_1;
sConfig.SamplingTime = ADC_SAMPLETIME_47CYCLES_5;
sConfig.SingleDiff = ADC_SINGLE_ENDED;
sConfig.OffsetNumber = ADC_OFFSET_NONE;
sConfig.Offset = 0;
if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
{
Error_Handler();
}
/** Configure Regular Channel
*/
sConfig.Channel = ADC_CHANNEL_6;
sConfig.Rank = ADC_REGULAR_RANK_2;
if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
{
Error_Handler();
}
/** Configure Regular Channel
*/
sConfig.Channel = ADC_CHANNEL_16;
sConfig.Rank = ADC_REGULAR_RANK_3;
if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
{
Error_Handler();
}
/* USER CODE BEGIN ADC1_Init 2 */
/* USER CODE END ADC1_Init 2 */
}
void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc)
{
static uint8_t adcIndex = 0;
static uint32_t adc_temp[3];
adc_temp[adcIndex] = HAL_ADC_GetValue(&hadc1);
if(adcIndex == 2)
{
adc_value[adc_SHUTOFF] = adc_temp[0];
adc_value[adc_FLOW] = adc_temp[1];
adc_value[adc_BATTERY] = adc_temp[2];
}
adcIndex++;
if(adcIndex > 2)
{
adcIndex = 0;
}
HAL_ADC_Start_IT(&hadc1);
}
2022-09-28 12:44 AM
Well, you have connected the ADC input to a voltage divider with two resistors of 1Mohms, which is definitely too high impedance and greatly facilitates interference. The data sheet of the STM32L452 mentions the maximum input impedance for RAIN = 50kohms.
If you really need to measure at high impedance, it is best to use an opamp as a voltage follower to drive the ADC input.
Regards
/Peter
2022-09-29 12:37 AM
Normally, the ADC value is based on both input and Vref. so I think you may check if any impact from Vref. in another side, the output voltage of battery may be changed if the load was changed (from potentiometer) on your board.
2022-10-05 10:30 PM
I could solve the problem changing two resistors.
Next, I should use an opamp. thank you