AnsweredAssumed Answered

STM32F1 ADC+DMA problem

Question asked by panczak.maciej on Jun 22, 2014
Latest reply on Jun 22, 2014 by panczak.maciej
Hi!

I would like to ask you for some help- I wrote a code to get ADC values from 8 channels (regular group). After each conversion there has to be of course DMA request. I wrote everything and... all I get is value from PA0 (1st channel). All table CAN_adc is filled with this value. I dont know what is wrong, I was writing code with reference manual, after that with exemples in the web and i still have no clue. I bet there is some stupid mistake, like always.

#include "ADC_init.h"
#include "stm32f10x.h"
 
unsigned int CAN_adc[8];
 
void ADC_setup()
{
    RCC->CFGR |= RCC_CFGR_ADCPRE_DIV6;        // 72 MHz/6 = 12 MHz (must not exceed 14 MHz)
     
    RCC->APB2ENR |= RCC_APB2ENR_ADC1EN        // ADC clock ON
               | RCC_APB2ENR_IOPAEN;        // GPIOA clock ON
     
    GPIOA->CRL &= ~(GPIO_CRL_CNF0
               | GPIO_CRL_CNF1
               | GPIO_CRL_CNF2
               | GPIO_CRL_CNF3
               | GPIO_CRL_CNF4
               | GPIO_CRL_CNF5
               | GPIO_CRL_CNF6
               | GPIO_CRL_CNF7);              // PA0..7 analog mode
     
    ADC1->CR2 |= ADC_CR2_ADON;                // ADC on, wakes up from power down mode, to start conversion ADON x2
     
    ADC1->CR2 |= ADC_CR2_CAL                  // ADC calibration
              | ADC_CR2_CONT;                 // Continous conversion mode
 
    ADC1->CR2 &= ~(ADC_CR2_ALIGN);            // Right align mode
     
    ADC1->SQR1 |= (ADC_SQR1_L & (8 << 20));   // 8 regular conversions
    ADC1->SQR3 |= (ADC_SQR3_SQ1 & (0 << 0))
               | (ADC_SQR3_SQ2 & (1 << 5))
               | (ADC_SQR3_SQ3 & (2 << 10))
               | (ADC_SQR3_SQ4 & (3 << 15))
               | (ADC_SQR3_SQ5 & (4 << 20))
               | (ADC_SQR3_SQ6 & (5 << 25));
    ADC1->SQR2 |= (ADC_SQR2_SQ7 & (6 << 0))
               | (ADC_SQR2_SQ8 & (7 << 5));   // Regular group 0-1-2-3-4-5-6-7 channel
                          
    ADC1->SMPR2 |= (ADC_SMPR2_SMP0 & (7<<0))  // 239.5 cycles sample time
                | (ADC_SMPR2_SMP1 & (7<<3))
                            | (ADC_SMPR2_SMP2 & (7<<6))
                            | (ADC_SMPR2_SMP3 & (7<<9))
                            | (ADC_SMPR2_SMP4 & (7<<12))
                            | (ADC_SMPR2_SMP5 & (7<<15))
                            | (ADC_SMPR2_SMP6 & (7<<18))
                            | (ADC_SMPR2_SMP7 & (7<<21));
     
    ADC1->CR1 |= ADC_CR1_SCAN;                // Scan mode enable
     
    ADC1->CR2 |= ADC_CR2_DMA;                 // DMA access enable
     
// DMA START CONFIGURATION
    RCC->AHBENR |= RCC_AHBENR_DMA1EN;         // Clock for DMA
 
    DMA1_Channel1->CCR |= DMA_CCR1_MINC       // Memory increment ENABLE
                                         | DMA_CCR1_PSIZE       // Peripheral 32-bit size
                                         | DMA_CCR1_MSIZE       // Memory 32-bit size
                                         | DMA_CCR1_PL          // Priority: very high
                                         | DMA_CCR1_CIRC;       // Circular mode
    DMA1_Channel1->CCR &= ~(DMA_CCR1_DIR      // Read from peripheral
                       | DMA_CCR1_PINC);      // Peripheral increment mode DISABLE
                                          
    DMA1_Channel1->CPAR = (unsigned int)0x4001244C;      // Peripheral adress on DR in ADC1
    DMA1_Channel1->CMAR = (unsigned int)CAN_adc;         // Memory adress
     
    DMA1_Channel1->CNDTR = 8;                 // 8 data to transfer (8 ADC channels)
     
    DMA1_Channel1->CCR |= DMA_CCR1_EN;        // Channel 1 Enable
// DMA END CONFIGURATION
     
    ADC1->CR2 |= ADC_CR2_ADON;                // Start conversions
}

Outcomes