Skip to main content
jvadillo
Associate II
Aug 18, 2019 9:53 AM UTC
Solved

Is there any example with DMA and ADC1 for the STM32G431 using the Low-Level layer?

I am trying to make the ADC and the DMA work in the STM32G431 without success. I can make the ADC work but the DMA transaction is not triggered.

This is my code:

//******************************************************************************
void ADCInit(void)
//******************************************************************************
{
 LL_GPIO_InitTypeDef GPIO_InitStructure;
 LL_ADC_InitTypeDef adcInit;
 LL_ADC_REG_InitTypeDef adcRegInit;
 
 // Enable clocks
 LL_AHB2_GRP1_EnableClock(LL_AHB2_GRP1_PERIPH_GPIOA|LL_AHB2_GRP1_PERIPH_GPIOB);
 LL_AHB2_GRP1_EnableClock(LL_AHB2_GRP1_PERIPH_ADC12);
 
 // Reset any previous configuration
 LL_ADC_CommonDeInit(ADC12_COMMON);
 LL_ADC_DeInit(ADC1); // For voltage and current 
 
 // Enable Power regulators
 LL_ADC_DisableDeepPowerDown(ADC1);
 LL_ADC_EnableInternalRegulator(ADC1);
 LL_ADC_SetCommonClock(ADC12_COMMON, LL_ADC_CLOCK_SYNC_PCLK_DIV1);
 Delay(100); // tADCVREG_STUP = 20us --> stabilization
 
 // Start calibration of the ADCs
 LL_ADC_StartCalibration(ADC1,LL_ADC_SINGLE_ENDED);
 while (LL_ADC_IsCalibrationOnGoing(ADC1)); 
 
 LL_ADC_SetCommonPathInternalCh(ADC12_COMMON, LL_ADC_PATH_INTERNAL_VREFINT);
 
 // Configure all analog pins
 GPIO_InitStructure.Mode = LL_GPIO_MODE_ANALOG;
 GPIO_InitStructure.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
 GPIO_InitStructure.Speed = LL_GPIO_SPEED_HIGH;
 GPIO_InitStructure.Pull = LL_GPIO_PULL_NO;
 
 GPIO_InitStructure.Pin = LL_GPIO_PIN_0;
 LL_GPIO_Init(GPIOA, &GPIO_InitStructure); 
 GPIO_InitStructure.Pin = LL_GPIO_PIN_1; 
 LL_GPIO_Init(GPIOA, &GPIO_InitStructure); 
 
 memset((void *)iSamplingBuf,0xFF,sizeof(iSamplingBuf));
 
 // Now Initialize the ADCs
 LL_ADC_StructInit(&adcInit);
 adcInit.Resolution = LL_ADC_RESOLUTION_12B;
 adcInit.DataAlignment = LL_ADC_DATA_ALIGN_RIGHT;
 adcInit.LowPowerMode = LL_ADC_LP_MODE_NONE;
 LL_ADC_Init(ADC1, &adcInit);
 
 LL_ADC_REG_StructInit(&adcRegInit);
 adcRegInit.TriggerSource = LL_ADC_REG_TRIG_SOFTWARE;
 adcRegInit.SequencerDiscont = LL_ADC_REG_SEQ_DISCONT_DISABLE;
 adcRegInit.ContinuousMode = LL_ADC_REG_CONV_SINGLE;
 adcRegInit.DMATransfer = LL_ADC_REG_DMA_TRANSFER_LIMITED;
 adcRegInit.Overrun = LL_ADC_REG_OVR_DATA_OVERWRITTEN;
 adcRegInit.SequencerLength = LL_ADC_REG_SEQ_SCAN_DISABLE;
 LL_ADC_REG_Init(ADC1, &adcRegInit);
 
 LL_ADC_REG_SetSequencerRanks (ADC1,LL_ADC_REG_RANK_1,LL_ADC_CHANNEL_1);
 LL_ADC_REG_SetSequencerRanks (ADC1,LL_ADC_REG_RANK_2,LL_ADC_CHANNEL_2);
 LL_ADC_SetChannelSamplingTime(ADC1,LL_ADC_CHANNEL_1, LL_ADC_SAMPLINGTIME_47CYCLES_5);
 LL_ADC_SetChannelSingleDiff (ADC1,LL_ADC_CHANNEL_1, LL_ADC_SINGLE_ENDED);
 LL_ADC_SetChannelSamplingTime(ADC1,LL_ADC_CHANNEL_2, LL_ADC_SAMPLINGTIME_47CYCLES_5);
 LL_ADC_SetChannelSingleDiff (ADC1,LL_ADC_CHANNEL_2, LL_ADC_SINGLE_ENDED);
 LL_ADC_REG_SetSequencerLength(ADC1,LL_ADC_REG_SEQ_SCAN_DISABLE);
 
 
 
 LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMA1); //enable clock
 LL_DMA_ConfigTransfer(DMA1,
 LL_DMA_CHANNEL_1,
 LL_DMA_DIRECTION_PERIPH_TO_MEMORY |
 LL_DMA_MODE_CIRCULAR |
 LL_DMA_PERIPH_NOINCREMENT |
 LL_DMA_MEMORY_INCREMENT |
 LL_DMA_PDATAALIGN_HALFWORD |
 LL_DMA_MDATAALIGN_HALFWORD |
 LL_DMA_PRIORITY_HIGH );
 LL_DMA_SetPeriphRequest(DMA1, LL_DMA_CHANNEL_1, LL_DMAMUX_REQ_ADC1);
 
 LL_DMA_ConfigAddresses(DMA1,
 LL_DMA_CHANNEL_1,
 LL_ADC_DMA_GetRegAddr(ADC1, LL_ADC_DMA_REG_REGULAR_DATA),
 (uint32_t)iSamplingBuf,
 LL_DMA_DIRECTION_PERIPH_TO_MEMORY);
 LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_1, ARRAYSIZE(iSamplingBuf));
 LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_1); 
 
 
 // Enable ADC1
 LL_ADC_ClearFlag_ADRDY(ADC1);
 LL_ADC_Enable(ADC1);
 while (!LL_ADC_IsEnabled(ADC1));
 
 LL_ADC_REG_StartConversion(ADC1);
 
 for (;;)
 {
 
 }
} 
 

What I am doing wrong?

Is there any example with DMA and ADC1 for the STM32G431 using the Low-Level layer?

This topic has been closed for replies.
jvadillo
jvadilloBest answer
Associate II
Aug 20, 2019 2:46 PM UTC

After working some hours on the subject and with the help of the STM32 Cube MX code generator, I found that the ADCMUX clock initialization was missing:

LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMAMUX1);

4 replies

jvadillo
jvadilloAuthor
Associate II
Aug 20, 2019 8:55 AM UTC

Is there any person working with an STM32G4 and using the ADC with the DMA?

snjy1697
Associate II
Dec 14, 2019 7:08 AM UTC

I am working on ADC w/DMA. Using HAL libraries and SATM32CUBEMX for config. But i am facing issues, not able to get any output using DMA interface

jvadillo
jvadilloAuthorBest answer
Associate II
Aug 20, 2019 2:46 PM UTC

After working some hours on the subject and with the help of the STM32 Cube MX code generator, I found that the ADCMUX clock initialization was missing:

LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMAMUX1);

AScen.1
Associate II
Feb 5, 2020 1:19 PM UTC

Does the above example with the below 2 lines to configure the clocks work fine?

LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMA1);

LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMAMUX1);

For the above code, few LL APIs like the below give me compilation error and the others are fine.

For example, "undefined reference to `LL_ADC_DeInit' ". Any idea why?

LL_ADC_DeInit()

LL_GPIO_Init()

LL_ADC_Init()

Here are my includes:

#include <zephyr.h>

#include <sys/printk.h>

#include <drivers/adc.h>

#include <stm32g4xx_ll_system.h>

#include <stm32g4xx_ll_dma.h>

#include <stm32g4xx_ll_adc.h>