cancel
Showing results for 
Search instead for 
Did you mean: 

Problems with ADC after calibration - STM32L010K8

ledi001
Senior

Hello!

i develop an outdoor temperature measurement system and read every 30 minutes the ADC values -> all works fine! ADC calibration was done one times after start up.

Now i changed the ADC calibration and calibrate every 30 minutes just before i read the ADC values. I want to do this because the temperature in the environment changes between +20°C and - 5°C within 24 hours.

But now, i got wrong results after ADC conversion.

here is my code for calibration:

void ADC_calibration(void)
{
	/* (1) Ensure that ADEN = 0 */
	/* (2) Clear ADEN */
	/* (3) Set ADCAL=1 */
	/* (4) Wait until EOCAL=1 */
	/* (5) Clear EOCAL */
	if ((ADC1->CR & ADC_CR_ADEN) != 0) /* (1) */
	{
		ADC1->CR |= ADC_CR_ADDIS; /* (2) */
	}
 
	ADC1->CR |= ADC_CR_ADCAL; /* (3) */
 
	while ((ADC1->ISR & ADC_ISR_EOCAL) == 0) /* (4) */
	{
		/* For robust implementation, add here time-out management */
		HAL_Delay(200);
	}
	ADC1->ISR |= ADC_ISR_EOCAL; /* (5) */
}

and here my code in the ADC conversion function:

void concatenate_tx_data(void)
{
	ADC_calibration();		// ADC Calibration just before ADC conversion every 30 minutes
 
	vrefint_raw_value = adcBuffer[4];			// VREFINT Rohwert
	vrefint_cal_value = (*VREFINT_CAL_ADDR);	// VREFINT Factory Calibration Value @ 3V, 25C
 
 
	/*********** calculate R NTC1 (NTC mounted on PCB) ************/
	ADCx = (double)vrefint_cal_value * (double)adcBuffer[0];
	ADCy = vrefint_raw_value * ADC_RESOLUTION;
	ADCtemp = 3000.0 * (ADCx / ADCy);
	Uadc1 = ADCtemp;
	R_NTC1 = (R2*(UCONST-Uadc1))/Uadc1;
 
...
...

Can somebody give me a hint whats going wrong?

This discussion is locked. Please start a new topic to ask your question.
1 REPLY 1
TDK
Super User

The calibration procedure in the RM is slightly different than what you're doing here. May or may not be the issue.

Software calibration procedure

1. Ensure that ADEN=0 and DMAEN=0.

2. Set ADCAL=1.

3. Wait until ADCAL=0 (or until EOCAL=1). This can be handled by interrupt if the

interrupt is enabled by setting the EOCALIE bit in the ADC_IER register. The ADCAL

bit can remain set for some time even after EOCAL has been set. As a result, the

software must wait for ADCAL=0 after EOCAL=1 to be able to set ADEN=1 for next

ADC conversions.

4. The calibration factor can be read from bits 6:0 of ADC_DR or ADC_CALFACT

registers.

If you feel a post has answered your question, please click "Accept as Solution".