Skip to main content
Graduate
March 2, 2024
Question

STM32C031C6T6 Multi channel ADC not working

  • March 2, 2024
  • 2 replies
  • 3022 views

Hello All, I am working on a raw STM32C031C6T6 directly soldered on a breakout board and trying to make a multi channel interrupt based ADC working but the problem i am facing is all the adc's are giving me the same values even after setting the separate channel for individuals and when i decided to use dma it stuck when continue dma request is enable  and when its not dma just reads a single cycle.

below i have  provided you the screenshot of my configuration and clock settings i have used as well as i am attaching my code which i have made for this.

any kind of help will be really appreciable.    

 

 

 

IMG-20240302-WA0000.jpgIMG-20240302-WA0001.jpg

 

 

IMG-20240302-WA0002.jpg

 

 

 

 

 

 

__IO uint16_t counter=0,secCounter=0;
 uint32_t uADCVal[4];
__IO uint8_t ADCflag=0;
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim){

	if (htim->Instance == TIM3) {
		counter++;
		if (counter >= 500) {

			counter=0;
			secCounter++;
			HAL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin);
		}
	}
}

void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef *hadc)
{
 /* Prevent unused argument(s) compilation warning */
 UNUSED(hadc);

 /* NOTE : This function should not be modified. When the callback is needed,
 function HAL_ADC_ConvCpltCallback must be implemented in the user file.
 */
 ADCflag=1;
}

int main(void)
{
 /* USER CODE BEGIN 1 */

 /* USER CODE END 1 */

 /* MCU Configuration--------------------------------------------------------*/

 /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
 HAL_Init();

 /* USER CODE BEGIN Init */

 /* USER CODE END Init */

 /* Configure the system clock */
 SystemClock_Config();

/* Configure the peripherals common clocks */
 PeriphCommonClock_Config();

 /* USER CODE BEGIN SysInit */

 /* USER CODE END SysInit */

 /* Initialize all configured peripherals */
 MX_GPIO_Init();
 MX_TIM3_Init();
 MX_ADC1_Init();
 /* USER CODE BEGIN 2 */
 HAL_TIM_Base_Start_IT(&htim3);
 HAL_ADC_Start_IT(&hadc1);

 /* USER CODE END 2 */

 /* Infinite loop */
 /* USER CODE BEGIN WHILE */
 while (1)
 {
 /* USER CODE END WHILE */

 /* USER CODE BEGIN 3 */
	if (ADCflag) {
		for (int var = 0; var < 4; var++) {
		 uADCVal[var] = HAL_ADC_GetValue(&hadc1);
		}
		ADCflag=0;
		//HAL_ADC_Start_IT(&hadc1);
	}
 }
 /* USER CODE END 3 */
}

 

 

 

 

 

    This topic has been closed for replies.

    2 replies

    Graduate II
    March 2, 2024

    Have you scan mode enabled ? Better as photo is attach ioc file or show code adc init...

    And 1,5 cycle ...

    Visitor II
    March 3, 2024

    Do you know that the ADC has multiple channels and these have to be configured as "RANK"s?

    How many RANKs are configured in your system? I would guess: the CubeMX tool does not configure multiple channels, just the main ADC setup.

    On my STM32U5A5 project, I "need" this:

     /** Configure Regular Channel */
     sConfig.Channel = ADC_CHANNEL_VREFINT;
     sConfig.Rank = ADC_REGULAR_RANK_1;
     sConfig.SamplingTime = ADC_SAMPLETIME_68CYCLES;	//ADC_SAMPLETIME_1CYCLE_5;
     sConfig.SingleDiff = ADC_SINGLE_ENDED;
     sConfig.OffsetNumber = ADC_OFFSET_NONE;
     sConfig.Offset = 0;
     sConfig.OffsetSignedSaturation = DISABLE;
     if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
     {
     //Error_Handler();
     }
    
     sConfig.Channel = ADC_CHANNEL_VBAT;
     sConfig.Rank = ADC_REGULAR_RANK_2;
     if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
     {
     //Error_Handler();
     }
    
     sConfig.Channel = ADC_CHANNEL_TEMPSENSOR;
     sConfig.Rank = ADC_REGULAR_RANK_3;
     if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK)
     {
     //Error_Handler();
     }
    
     HAL_ADCEx_Calibration_Start(&hadc, ADC_CALIB_OFFSET, ADC_SINGLE_ENDED);

     

    RChou.1Author
    Graduate
    March 4, 2024

    Above on Mr MM..1's post i have attached my ioc file and if you could check them once for any error would be really appreciable.

    And if you could provide me any sample code using Multichannel ADC interrupt mode can help me a lot to understand better.

    Super User
    March 3, 2024
    		for (int var = 0; var < 4; var++) {
    		 uADCVal[var] = HAL_ADC_GetValue(&hadc1);
    		}

    This is not how the ADC works. It does not store the values for all channels in a buffer which you can read out later.

    Use DMA to convert multiple channels.

    RChou.1Author
    Graduate
    March 4, 2024

    Then how can i read multiple channel using ADC interrupt when End of Sequence conversion happens.

    This example is based on some tutorial on youtube. 

    For your reference I'm attaching my ioc file and hoping for your reply.

    Super User
    March 4, 2024

    Using DMA would be the supported solution. You can use interrupts if your code is fast enough. The reference manual provides instructions on how to set this up. You probably won't find examples of it as it's prone to overrun errors.

     

    TDK_0-1709560104792.png