cancel
Showing results for 
Search instead for 
Did you mean: 

ADC Error to HIGH.

CMart.3
Associate II

Hey Everyone;

I`m working with the STM32L031K6T6 in a project that I require 2 ADC channels.

The ADC look to be working with a huge measurement error:

Project description:

Signal Type: Sinusoidal ( 1Vpp) with offset of 1.492 ( Offset provide by independent power source - Voltage Reference IC , as shown below)

Sampling rate: 1920Hz

0693W000001t4AZQAY.png

For the analog voltage in STM32L031k6T6, i have an independent voltage source with reference in 2.985. ( All voltages were read with Fluke multimeter)

0693W000001t4BvQAI.png

With my sinusoidal source disconnected my voltage in the PA0 is 1.492V

My ADC reading is currently : 2112

0693W000001t4CAQAY.png

However the ADC read should be 2047 for the voltage.

I did some change in the code as suggested in the post :

https://community.st.com/s/question/0D50X0000B8jGv5/adc-accuracy-offset-and-gain-big-errors

Initially without the calibration my adc was reading 2145 ( with high oscilation in the values +- 10 steps)

The I include the calibration:

if (HAL_OK != HAL_ADCEx_Calibration_Start(&hadc, ADC_SINGLE_ENDED))
	  Error_Handler();

The calibration improved my reading and start to read 2130 ( Stable)

My next step was change the sampling time

I change it to 79 cycles

static void MX_ADC_Init(void)
{
 
  /* USER CODE BEGIN ADC_Init 0 */
 
  /* USER CODE END ADC_Init 0 */
 
  ADC_ChannelConfTypeDef sConfig = {0};
 
  /* USER CODE BEGIN ADC_Init 1 */
 
  /* USER CODE END ADC_Init 1 */
  /** Configure the global features of the ADC (Clock, Resolution, Data Alignment and number of conversion) 
  */
  hadc.Instance = ADC1;
  hadc.Init.OversamplingMode = DISABLE;
  hadc.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV2;
  hadc.Init.Resolution = ADC_RESOLUTION_12B;
  hadc.Init.SamplingTime = ADC_SAMPLETIME_79CYCLES_5;
  hadc.Init.ScanConvMode = ADC_SCAN_DIRECTION_FORWARD;
  hadc.Init.DataAlign = ADC_DATAALIGN_RIGHT;
  hadc.Init.ContinuousConvMode = DISABLE;
  hadc.Init.DiscontinuousConvMode = DISABLE;
  hadc.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_RISING;
  hadc.Init.ExternalTrigConv = ADC_EXTERNALTRIGCONV_T2_TRGO;
  hadc.Init.DMAContinuousRequests = ENABLE;
  hadc.Init.EOCSelection = ADC_EOC_SINGLE_CONV;
  hadc.Init.Overrun = ADC_OVR_DATA_PRESERVED;
  hadc.Init.LowPowerAutoWait = DISABLE;
  hadc.Init.LowPowerFrequencyMode = DISABLE;
  hadc.Init.LowPowerAutoPowerOff = DISABLE;
  if (HAL_ADC_Init(&hadc) != HAL_OK)
  {
    Error_Handler();
  }
  /** Configure for the selected ADC regular channel to be converted. 
  */
  sConfig.Channel = ADC_CHANNEL_0;
  sConfig.Rank = ADC_RANK_CHANNEL_NUMBER;
  if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /** Configure for the selected ADC regular channel to be converted. 
  */
  sConfig.Channel = ADC_CHANNEL_1;
  if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN ADC_Init 2 */
 
  /* USER CODE END ADC_Init 2 */
 
}

Then my reading start to be 2112 ( Stable reading )

My Power supply and reference voltages are pretty clean

0693W000001t4D3QAI.jpg

 0693W000001t4D8QAI.jpg

Considering the maximum amplitude noise my adc in this board will have error of 5 steps.

 However my reading are far away of the correct value.

What I should to do to fix it?

 Question 2:

AFter my code run the first time, the code stop in:

void HardFault_Handler(void)
{
  /* USER CODE BEGIN HardFault_IRQn 0 */
 
  /* USER CODE END HardFault_IRQn 0 */
  while (1)
  {
    /* USER CODE BEGIN W1_HardFault_IRQn 0 */
    /* USER CODE END W1_HardFault_IRQn 0 */
  }
}

Everything that I found in internet says about memory problem in my code, however the memory is ok

0693W000001t4DXQAY.png

 The error is

0693W000001t4DcQAI.png

0693W000001t4btQAA.png

How I can solve it?

The STM look a formidable MCU, however the simple code ( Attached Atollic + CubeMX ) is not running well.

Can you help me solve it?

Thank you and best regards

3 REPLIES 3
TDK
Guru

This is a very well written question. Thank you for putting in the effort.

From the device datasheet and reference manuals:

> VDDA and VSSA must be connected to VDD and VSS, respectively.

My guess is it's working okay since VDD and VDDA are different by only 0.3V, which is near the max allowed without protection diodes blowing up, but of course accuracy and function are not guaranteed here.

I also see another note:

> Analog power supply and positive reference voltage for the ADC, VDDA ≥ VDD

In either case, your design is violating both of these.

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

Dear TDK,

Thank you for your fast answer.

As you mentioned, the VDDA must be no more that VCC - 0.3.

I did the changes in the board and update voltage reference. Previosly I was with MCP1501T-30 ( 3V) and I updated to MCP1501T-33 (3V3)

As result nothing change about the error.

My DC component is 1.492V that in 12 bits adc with VREF equal to 3.3 (3.285V) should result in the reading 1860 is reading 1925 +- 10. The same 65 steps of the previous case.

0693W000001t4veQAA.png

The second failure the HardFault_Handler didn't stop with the component change, I believe that this fault is not connected with VDDA.

Can someone explain me what is happening with this ADC?

Thank you and best regards

TDK
Guru

The datasheet doesn't say they need to be close, it says they need to be tied to each other.

My guess is you don't have enough capacitance on VDDA and it gets pulled down during sampling.

The hard fault is almost certainly due to a bug in the code. Perhaps a missing ISR, perhaps a buffer overrun. The SCB register should contain details on what went wrong.

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