STM32 mit CUBE, ADC mit mehreren Kanälen ansprechen

(Firma: KHTronik) #3970569
Lesenswert?

Hallo,
das Topic sagt schon, womit ich Probleme habe:
Ich habe mit dem STM32CUBE-Tool vier Analogeingänge gewählt und den Code 
erzeugt. Die Eingänge möchte ich in vier Variable einlesen. Das Ganze 
dann alle 10-100ms. Bisheriger Stand:
1
int value1, value2, value3, value4;
2

3
...
4

5
HAL_ADC_Start(&hadc);
6
value1 = HAL_ADC_GetValue(&hadc);
7
value2 = HAL_ADC_GetValue(&hadc);
8
value3 = HAL_ADC_GetValue(&hadc);
9
value4 = HAL_ADC_GetValue(&hadc);
Leider tut sich nichts. Die Zeilen werden durchlaufen, aber die 
Variablen bleiben 0.

Hat jemand eine Idee, was ich da falsch verstehe?

Grüße, Kurt
(Firma: KHTronik) #3970730
Lesenswert?

Hallo Bernd,
es war noch nicht einmal der nicht gepostete Code, sondern der Code, der 
durch unvollständige Konfiguration im STM32CUBE erzeugt wurde. Ich hatte 
die Anzahl der Kanäle und das Ende der Konversion falsch eingestellt. 
Die Anzahl musste (natürlich) auf 4 stehen, und das Ende der Konversion 
ist das Ende der Sequenz. Jetzt läuft der Code schon mal ein wenig, es 
sind wohl noch die Kanäle durcheinander.
Grüße, und danke, Kurt
Gast #3971218
Lesenswert?

Dann probier's mal damit - ich lese 4 Kanäle mit DMA auf einem 
STM32F407VG (Disco)aus und schreibe sie in eine Struktur.


/**
  ************************************************************************ 
******
  * @file    ADC/ADC1_DMA/main.c
  * @author  DD4DA
  * @version V1.0
  * @date    17.06.2013
  * @brief   Main program body
  ************************************************************************ 
******
  * @attention
  * The Program demonstrate how the ADC works with DMA on a 
STM32F407Discovery
  * using ADC1. The used CMSIS Lib is version 1.0.
  * The ADC1 is configured to use Regular Groups by using DMA2,Stream0.
  * <h2><center>DD4DA</center></h2>
  ************************************************************************ 
******
  */

#include <stdio.h>
#include "stm32f4xx.h"
#include "adc1.h"


#define ADC1_DR_Address    ((uint32_t) 0x4001204C )   // ADC1 @ 
$4001:2000  + register offset $4C == $4001244C  <--  ADC1 Data Register

ADC_InitTypeDef         ADC_InitStructure;
ADC_CommonInitTypeDef   ADC_CommonInitStructure;
DMA_InitTypeDef         DMA_InitStructure;
GPIO_InitTypeDef         GPIO_InitStructure;


double Temperature,Voltage; 
// Variables for calculating Temperatur and Voltage

#define V25           0.760
#define AVG_SLOPE     25.0

#define Num_used_ADC_Channels    5 
// The number of ADC channels that will be used.
volatile uint16_t ADCBuffer[Num_used_ADC_Channels + 1] = { 0 , 0 , 0 , 0 
, 0,  0xAA };  // DMA Buffers - one halfword used by every ADC-Channel.
enum _ADC_CHAN_BUFF_ORDER_ { CH0 = 1, CH1 = 2 , TEMP = 3 , VREF = 4, 
VBAT =5 };



void Init_ADC ( void )
{
    // ############## ADC 
######################################################################## 
##################################
    // ---------- Configure PB0 and PB1 (ADC Channel1 and ADC Channel2 ) 
as analog input ------------------
    //
    // GPIOB function block clock enable

    RCC_APB2PeriphClockCmd ( RCC_APB2Periph_ADC1, ENABLE );
    RCC_AHB1PeriphClockCmd ( RCC_AHB1Periph_GPIOB, ENABLE );

    GPIO_InitStructure.GPIO_Pin         = GPIO_Pin_0 | GPIO_Pin_1;    // 
Init Pin 8 and A1
    GPIO_InitStructure.GPIO_Mode         = GPIO_Mode_AN;
    GPIO_InitStructure.GPIO_PuPd         = GPIO_PuPd_NOPULL ;
    GPIO_Init ( GPIOB, &GPIO_InitStructure );                  // Init 
GPIO-PORTA as Analog input



    // DMA2 Stream0 configuration 
------------------------------------------------------------------------ 
------------------------
    //
    // Enable DMA2 clock

    RCC_AHB1PeriphClockCmd ( RCC_AHB1Periph_DMA2, ENABLE );
    DMA_DeInit ( DMA2_Stream0 );

    DMA_InitStructure.DMA_Channel             = DMA_Channel_0;
    DMA_InitStructure.DMA_PeripheralBaseAddr   = 
(uint32_t)ADC1_DR_Address;
    DMA_InitStructure.DMA_Memory0BaseAddr     = (uint32_t)&ADCBuffer;
    DMA_InitStructure.DMA_DIR                 = 
DMA_DIR_PeripheralToMemory;
    DMA_InitStructure.DMA_BufferSize           = Num_used_ADC_Channels;
    DMA_InitStructure.DMA_PeripheralInc       = 
DMA_PeripheralInc_Disable;
    DMA_InitStructure.DMA_MemoryInc           = DMA_MemoryInc_Enable;
    DMA_InitStructure.DMA_PeripheralDataSize   = 
DMA_PeripheralDataSize_HalfWord;
    DMA_InitStructure.DMA_MemoryDataSize       = 
DMA_MemoryDataSize_HalfWord;
    DMA_InitStructure.DMA_Mode                 = DMA_Mode_Circular;
    DMA_InitStructure.DMA_Priority             = DMA_Priority_High;
    DMA_InitStructure.DMA_FIFOMode             = DMA_FIFOMode_Disable;
    DMA_InitStructure.DMA_FIFOThreshold       = 
DMA_FIFOThreshold_HalfFull;
    DMA_InitStructure.DMA_MemoryBurst         = DMA_MemoryBurst_Single;
    DMA_InitStructure.DMA_PeripheralBurst     = 
DMA_PeripheralBurst_Single;

    DMA_Init ( DMA2_Stream0, &DMA_InitStructure );
    DMA_Cmd  ( DMA2_Stream0, ENABLE );


    // ------------------ ADC1 configuration 
-------------------------------------------------------
    //

    ADC_DeInit();

    ADC_CommonInitStructure.ADC_Mode               = 
ADC_Mode_Independent;
    ADC_CommonInitStructure.ADC_Prescaler         = ADC_Prescaler_Div2;
    ADC_CommonInitStructure.ADC_DMAAccessMode    = 
ADC_DMAAccessMode_Disabled;
    ADC_CommonInitStructure.ADC_TwoSamplingDelay = 
ADC_TwoSamplingDelay_20Cycles;

    ADC_CommonInit(&ADC_CommonInitStructure);

    // ########################### ADC1 Init 
#########################################

    ADC_InitStructure.ADC_Resolution               = ADC_Resolution_12b;
    ADC_InitStructure.ADC_ScanConvMode             = ENABLE;
    ADC_InitStructure.ADC_ContinuousConvMode       = ENABLE;
    ADC_InitStructure.ADC_ExternalTrigConvEdge    = 
ADC_ExternalTrigConvEdge_None;
    ADC_InitStructure.ADC_ExternalTrigConv        = 0;
    ADC_InitStructure.ADC_DataAlign               = ADC_DataAlign_Right;
    ADC_InitStructure.ADC_NbrOfConversion        = 
Num_used_ADC_Channels;

    ADC_Init(ADC1, &ADC_InitStructure);
    ADC_DMACmd ( ADC1, ENABLE );           /* Enable ADC1 DMA */

    // ######### ADC1 regular conversation mode  configuration 
####################################
    //                         ADC ,  CHANNEL,           DMA 
MemoryOrder,    SampleTime
    //
    ADC_RegularChannelConfig(ADC1, ADC_Channel_8,           CH0, 
ADC_SampleTime_3Cycles);
    ADC_RegularChannelConfig(ADC1, ADC_Channel_9,           CH1, 
ADC_SampleTime_3Cycles);
    ADC_RegularChannelConfig(ADC1, ADC_Channel_Vbat,        VBAT, 
ADC_SampleTime_3Cycles);
    ADC_RegularChannelConfig(ADC1, ADC_Channel_TempSensor, TEMP, 
ADC_SampleTime_3Cycles);
    ADC_RegularChannelConfig(ADC1, ADC_Channel_Vrefint,    VREF, 
ADC_SampleTime_3Cycles);


    ADC_VBATCmd ( ENABLE );                               // Enable VBAT 
at channel 18
    ADC_TempSensorVrefintCmd ( ENABLE );                  // Enable 
TempSensor and Vrefint at channels 16 and 17

    ADC_DMARequestAfterLastTransferCmd ( ADC1, ENABLE );  // Enable DMA 
request after last transfer (Single-ADC mode)
    ADC_Cmd ( ADC1, ENABLE );                             // Enable ADC1

    ADC_SoftwareStartConv ( ADC1 );                        // Start ADC1 
Software Conversion

    return;
}

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren