cancel
Showing results for 
Search instead for 
Did you mean: 

STM32H723 ADC read stuck (using LL libraries)

Linas L
Senior II

Hello,
In my project I just sometimes need to read ADC values. I figure I could simply connect two of my signals to ADC1 and ADC2 respectively.

What it strange that it does sometimes working, but sometimes it is stuck at constant value ( maybe first read i think)

ADC is clocked from PLL at 100MHz



 

 

void ADC_Init(void)
{
  uint32_t timeout = 0xFFFFF;

  LL_ADC_InitTypeDef ADC_InitStruct = {0};
  LL_ADC_REG_InitTypeDef ADC_REG_InitStruct = {0};
  LL_ADC_CommonInitTypeDef ADC_CommonInitStruct = {0};

  LL_GPIO_InitTypeDef GPIO_InitStruct = {0};

  LL_RCC_SetADCClockSource(LL_RCC_ADC_CLKSOURCE_PLL3R);

  LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_ADC12);

  GPIO_InitStruct.Pin = LL_GPIO_PIN_11|LL_GPIO_PIN_13;
  GPIO_InitStruct.Mode = LL_GPIO_MODE_ANALOG;
  GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
  LL_GPIO_Init(GPIOF, &GPIO_InitStruct);


  LL_ADC_SetOverSamplingScope(ADC1, LL_ADC_OVS_GRP_REGULAR_CONTINUED);
  LL_ADC_ConfigOverSamplingRatioShift(ADC1, 1024, LL_ADC_OVS_SHIFT_RIGHT_6);
  LL_ADC_SetOverSamplingDiscont(ADC1, LL_ADC_OVS_REG_CONT);

  LL_ADC_SetOverSamplingScope(ADC2, LL_ADC_OVS_GRP_REGULAR_CONTINUED);
  LL_ADC_ConfigOverSamplingRatioShift(ADC2, 1024, LL_ADC_OVS_SHIFT_RIGHT_6);
  LL_ADC_SetOverSamplingDiscont(ADC2, LL_ADC_OVS_REG_CONT);


  ADC_InitStruct.Resolution = LL_ADC_RESOLUTION_16B;
  ADC_InitStruct.LowPowerMode = LL_ADC_LP_MODE_NONE;

  LL_ADC_Init(ADC1, &ADC_InitStruct);
  LL_ADC_Init(ADC2, &ADC_InitStruct);

  ADC_REG_InitStruct.TriggerSource = LL_ADC_REG_TRIG_SOFTWARE;
  ADC_REG_InitStruct.SequencerLength = LL_ADC_REG_SEQ_SCAN_DISABLE;
  ADC_REG_InitStruct.SequencerDiscont = DISABLE;
  ADC_REG_InitStruct.ContinuousMode = LL_ADC_REG_CONV_CONTINUOUS;
  ADC_REG_InitStruct.Overrun = LL_ADC_REG_OVR_DATA_PRESERVED;

  LL_ADC_REG_Init(ADC1, &ADC_REG_InitStruct);
  LL_ADC_REG_Init(ADC2, &ADC_REG_InitStruct);


  ADC_CommonInitStruct.CommonClock = LL_ADC_CLOCK_ASYNC_DIV1;
  ADC_CommonInitStruct.Multimode = LL_ADC_MULTI_INDEPENDENT;

  LL_ADC_CommonInit(__LL_ADC_COMMON_INSTANCE(ADC1), &ADC_CommonInitStruct);
  LL_ADC_CommonInit(__LL_ADC_COMMON_INSTANCE(ADC2), &ADC_CommonInitStruct);

  LL_ADC_DisableDeepPowerDown(ADC1);
  LL_ADC_DisableDeepPowerDown(ADC2);

  LL_ADC_EnableInternalRegulator(ADC1);
  LL_ADC_EnableInternalRegulator(ADC2);

  Delay(0xFFFF);

  LL_ADC_StartCalibration(ADC1,LL_ADC_CALIB_OFFSET_LINEARITY,LL_ADC_SINGLE_ENDED);
  LL_ADC_StartCalibration(ADC2,LL_ADC_CALIB_OFFSET_LINEARITY,LL_ADC_SINGLE_ENDED);

  timeout = 0xFFFFF;
  while(LL_ADC_IsCalibrationOnGoing(ADC1)!=0)
  {
    timeout--;
    if(timeout==0)
    {
      break;
    }
  }
  timeout = 0xFFFFF;
  while(LL_ADC_IsCalibrationOnGoing(ADC2)!=0)
  {
    timeout--;
    if(timeout==0)
    {
      break;
    }
  }

  LL_ADC_REG_SetSequencerRanks(ADC1, LL_ADC_REG_RANK_1, LL_ADC_CHANNEL_2);
  LL_ADC_SetChannelSamplingTime(ADC1, LL_ADC_CHANNEL_2, LL_ADC_SAMPLINGTIME_16CYCLES_5);
  LL_ADC_SetChannelSingleDiff(ADC1, LL_ADC_CHANNEL_2, LL_ADC_SINGLE_ENDED);
  LL_ADC_SetChannelPreselection(ADC1, LL_ADC_CHANNEL_2);

  LL_ADC_REG_SetSequencerRanks(ADC2, LL_ADC_REG_RANK_1, LL_ADC_CHANNEL_2);
  LL_ADC_SetChannelSamplingTime(ADC2, LL_ADC_CHANNEL_2, LL_ADC_SAMPLINGTIME_16CYCLES_5);
  LL_ADC_SetChannelSingleDiff(ADC2, LL_ADC_CHANNEL_2, LL_ADC_SINGLE_ENDED);
  LL_ADC_SetChannelPreselection(ADC2, LL_ADC_CHANNEL_2);

  LL_ADC_Enable(ADC1);
  LL_ADC_Enable(ADC2);

  timeout = 0xFFFFF;
  while (LL_ADC_IsActiveFlag_ADRDY(ADC1) == 0UL)
  {
    timeout--;
    if(timeout==0)
    {
      break;
    }
  }
  timeout = 0xFFFFF;
   while (LL_ADC_IsActiveFlag_ADRDY(ADC2) == 0UL)
  {
    timeout--;
    if(timeout==0)
    {
      break;
    }
  }
  LL_ADC_REG_StartConversion(ADC1);
  LL_ADC_REG_StartConversion(ADC2);
}

uint16_t ADC_READ_IN1(void)
{
    return (ADC2->DR)>>4;
}
uint16_t ADC_READ_IN2(void)
{
  return (ADC1->DR)>>4;
}

 

 

So I have two question:
Does any one can spot a problem, or tell my why I simply can't read ADC->DR register  if i am running only single channel per ADC ?

Thank you !
Any

1 ACCEPTED SOLUTION

Accepted Solutions
raptorhal2
Lead

I checked the H725 Data sheet and the ADCs are limited to 50 and 75 MHz. Check the H723 data sheet for maximum ADC frequency.

View solution in original post

4 REPLIES 4
raptorhal2
Lead

I checked the H725 Data sheet and the ADCs are limited to 50 and 75 MHz. Check the H723 data sheet for maximum ADC frequency.

50MHz max.

see:

AScha3_0-1689427328003.png

 

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

Hello,
Thanks for pointing this out, CubeMX did allowed me to config it for 100MHz, while adding divider helped and now it's working ! I even did not checked it for clock, since 100MHz does not look too high and code was generated by software that does indicate values out of spec.

Hi @Linas L ,

 

Glad to know that your problem is resolved.
To fix the issue on STM32CubeMX side, could you please:

  • confirm that issue is faced with latest version of STM32CubeMX (6.9.0)
  • share your ioc file so that I can reproduce the problem with exact configuration on my side

-Amel

To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.