Forum: Mikrocontroller und Digitale Elektronik STM32F4 HAL ADC Problem


von timertick_t (Gast)


Lesenswert?

Ächz. Ich klebe fest.
Hab mehrere Examples für nen STM32F4 gefunden aber alle verwenden kein 
HAL.
Ich habe den Code größtenteils aus dem Cube DMA Example und habe ihn 
leicht abgeändert - aber bei mir muckst sich nichts.
Wenn ich
HAL_ADC_PollForConversion(&myAdcHandle, 20);  // 20 = 20ms
abfrage bekomme ich keine Antwort und hänge vermutlich in einer 
while-Schleife fest, d.h. es sieht aus als ob der ADC überhaupt nicht 
gestartet wurde.
Wenn ich mit einer Zeitverzögerung die Zeile überbrücke ist das Ergebnis 
Null (an GPIO A5 liegen 1.8V an).


Seltsam: in dem Example taucht der entsprechende GPIO-Pin zur 
Initialisierung wie man das üblicherweise kennt gar nicht auf. Hmmm...

in meiner .h:
1
#include "stm32f4xx_hal.h"
2
3
#include "stm32f4_discovery.h"
4
5
/* Exported types ------------------------------------------------------------*/
6
/* Exported constants --------------------------------------------------------*/
7
/* User can use this section to tailor ADCx instance used and associated
8
   resources */
9
/* Definition for ADCx clock resources */
10
#define ADCx                            ADC1
11
#define ADCx_CLK_ENABLE()               __HAL_RCC_ADC1_CLK_ENABLE()
12
#define DMAx_CLK_ENABLE()               __HAL_RCC_DMA2_CLK_ENABLE()
13
//#define ADCx_CHANNEL_GPIO_CLK_ENABLE()  __HAL_RCC_GPIOA_CLK_ENABLE()   GPIO B???
14
#define ADCx_CHANNEL_GPIO_CLK_ENABLE()  __HAL_RCC_GPIOA_CLK_ENABLE()
15
16
#define ADCx_FORCE_RESET()              __HAL_RCC_ADC_FORCE_RESET()
17
#define ADCx_RELEASE_RESET()            __HAL_RCC_ADC_RELEASE_RESET()
18
19
/* Definition for ADCx Channel Pin */
20
//#define ADCx_CHANNEL_PIN                GPIO_PIN_0
21
//#define ADCx_CHANNEL_GPIO_PORT          GPIOB
22
#define ADCx_CHANNEL_PIN                GPIO_PIN_5
23
#define ADCx_CHANNEL_GPIO_PORT          GPIOA
24
25
26
/* Definition for ADCx's Channel */
27
//#define ADCx_CHANNEL                    ADC_CHANNEL_8
28
#define ADCx_CHANNEL                    ADC_CHANNEL_5
29
30
31
/* Definition for ADCx's DMA */
32
#define ADCx_DMA_CHANNEL                DMA_CHANNEL_0
33
#define ADCx_DMA_STREAM                 DMA2_Stream0
34
35
/* Definition for ADCx's NVIC */
36
#define ADCx_DMA_IRQn                   DMA2_Stream0_IRQn
37
#define ADCx_DMA_IRQHandler             DMA2_Stream0_IRQHandler
38
39
40
/* Exported macro ------------------------------------------------------------*/
41
42
43
/* Exported functions ------------------------------------------------------- */
44
void adctest(void);
und der Code:
1
#include "adctest.h"
2
3
4
5
6
/** @addtogroup STM32F4xx_HAL_Examples
7
  * @{
8
  */
9
10
/** @addtogroup ADC_RegularConversion_DMA
11
  * @{
12
  */ 
13
14
/* Private typedef -----------------------------------------------------------*/
15
/* Private define ------------------------------------------------------------*/
16
/* Private macro -------------------------------------------------------------*/
17
/* Private variables ---------------------------------------------------------*/
18
/* ADC handler declaration */
19
ADC_HandleTypeDef    myAdcHandle;
20
21
/* Variable used to get converted value */
22
__IO uint16_t uhADCxConvertedValue = 0;
23
24
/* Private function prototypes -----------------------------------------------*/
25
static void SystemClock_Config(void);
26
static void Error_Handler(void);
27
28
/* Private functions ---------------------------------------------------------*/
29
30
/**
31
  * @brief  Main program
32
  * @param  None
33
  * @retval None
34
  */
35
void adctest(void)
36
{
37
  ADC_ChannelConfTypeDef sConfig;
38
  
39
  /* STM32F4xx HAL library initialization:
40
       - Configure the Flash prefetch, instruction and Data caches
41
       - Configure the Systick to generate an interrupt each 1 msec
42
       - Set NVIC Group Priority to 4
43
       - Global MSP (MCU Support Package) initialization
44
     */
45
  HAL_Init();
46
  
47
  /* Configure the system clock to 144 MHz */
48
  SystemClock_Config();
49
  
50
51
52
  /* First and foremost: Enable ADC Port */
53
  RCC->AHB1ENR |=  RCC_AHB1ENR_GPIOAEN;
54
55
GPIO_InitTypeDef GPIO_InitStructure;
56
GPIO_InitStructure.Pin = GPIO_PIN_5;
57
GPIO_InitStructure.Mode =  GPIO_MODE_ANALOG; //GPIO_MODE_AF_PP; //Alternate function  ? ? ?
58
GPIO_InitStructure.Speed = GPIO_SPEED_FAST;
59
GPIO_InitStructure.Pull = GPIO_NOPULL;
60
//GPIO_InitStructure.Alternate = GPIO_AF1_TIM2; 
61
HAL_GPIO_Init(GPIOA, &GPIO_InitStructure);
62
63
64
  /* Configure LED4 and LED5 */
65
  BSP_LED_Init(LED4);
66
  BSP_LED_Init(LED5);
67
  
68
  /*##-1- Configure the ADC peripheral #######################################*/
69
  myAdcHandle.Instance = ADCx;
70
  
71
  myAdcHandle.Init.ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV2;
72
  myAdcHandle.Init.Resolution = ADC_RESOLUTION_12B;
73
  myAdcHandle.Init.ScanConvMode = DISABLE;
74
  myAdcHandle.Init.ContinuousConvMode = ENABLE;
75
  myAdcHandle.Init.DiscontinuousConvMode = DISABLE;
76
  myAdcHandle.Init.NbrOfDiscConversion = 0;
77
  myAdcHandle.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
78
  myAdcHandle.Init.ExternalTrigConv = ADC_EXTERNALTRIGCONV_T1_CC1;
79
  myAdcHandle.Init.DataAlign = ADC_DATAALIGN_RIGHT;
80
  myAdcHandle.Init.NbrOfConversion = 1;
81
  myAdcHandle.Init.DMAContinuousRequests = ENABLE;
82
  myAdcHandle.Init.EOCSelection = DISABLE;
83
      
84
  if(HAL_ADC_Init(&myAdcHandle) != HAL_OK)
85
  {
86
    /* Initialization Error */
87
    Error_Handler(); 
88
  }
89
  
90
  /*##-2- Configure ADC regular channel ######################################*/
91
  /* Note: Considering IT occurring after each number of size of              */
92
  /*       "uhADCxConvertedValue"  ADC conversions (IT by DMA end             */
93
  /*       of transfer), select sampling time and ADC clock with sufficient   */
94
  /*       duration to not create an overhead situation in IRQHandler.        */  
95
  sConfig.Channel = ADCx_CHANNEL;
96
  sConfig.Rank = 1;
97
  sConfig.SamplingTime = ADC_SAMPLETIME_84CYCLES;
98
  sConfig.Offset = 0;
99
  
100
  if(HAL_ADC_ConfigChannel(&myAdcHandle, &sConfig) != HAL_OK)
101
  {
102
    /* Channel Configuration Error */
103
    Error_Handler(); 
104
  }
105
106
//ausgeblendet
107
#ifdef NO_CODE_HERE
108
  /*##-3- Start the conversion process and enable interrupt ##################*/  
109
  if(HAL_ADC_Start_DMA(&myAdcHandle, (uint32_t*)&uhADCxConvertedValue, 1) != HAL_OK)
110
  {
111
    /* Start Conversation Error */
112
    Error_Handler(); 
113
  }
114
#endif //NO_CODE_HERE
115
116
117
  /*##-3- Start the conversion process and enable interrupt ##################*/
118
  if(HAL_ADC_Start(&myAdcHandle) != HAL_OK)
119
  {
120
    /* Start Conversation Error */
121
    Error_Handler();
122
  }
123
124
125
//ausgeblendet
126
#ifdef NO_CODE_HERE
127
  /* Infinite loop */
128
  while (1)
129
  {
130
  }
131
#endif //NO_CODE_HERE
132
133
}
134
135
/**
136
  * @brief  System Clock Configuration
137
  *         The system Clock is configured as follow : 
138
  *            System Clock source            = PLL (HSE)
139
  *            SYSCLK(Hz)                     = 144000000
140
  *            HCLK(Hz)                       = 144000000
141
  *            AHB Prescaler                  = 1
142
  *            APB1 Prescaler                 = 4
143
  *            APB2 Prescaler                 = 2
144
  *            HSE Frequency(Hz)              = 8000000
145
  *            PLL_M                          = 8
146
  *            PLL_N                          = 288
147
  *            PLL_P                          = 2
148
  *            PLL_Q                          = 6
149
  *            VDD(V)                         = 3.3
150
  *            Main regulator output voltage  = Scale2 mode
151
  *            Flash Latency(WS)              = 4
152
  * @param  None
153
  * @retval None
154
  */
155
static void SystemClock_Config(void)
156
{
157
  RCC_ClkInitTypeDef RCC_ClkInitStruct;
158
  RCC_OscInitTypeDef RCC_OscInitStruct;
159
160
  /* Enable Power Control clock */
161
  __HAL_RCC_PWR_CLK_ENABLE();
162
  
163
  /* The voltage scaling allows optimizing the power consumption when the device is 
164
     clocked below the maximum system frequency, to update the voltage scaling value 
165
     regarding system frequency refer to product datasheet.  */
166
  __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE2);
167
  
168
  /* Enable HSE Oscillator and activate PLL with HSE as source */
169
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
170
  RCC_OscInitStruct.HSEState = RCC_HSE_ON;
171
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
172
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
173
  RCC_OscInitStruct.PLL.PLLM = 8;
174
  RCC_OscInitStruct.PLL.PLLN = 288;
175
  RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2;
176
  RCC_OscInitStruct.PLL.PLLQ = 6;
177
  HAL_RCC_OscConfig(&RCC_OscInitStruct);
178
  
179
  /* Select PLL as system clock source and configure the HCLK, PCLK1 and PCLK2 
180
     clocks dividers */
181
  RCC_ClkInitStruct.ClockType = (RCC_CLOCKTYPE_SYSCLK | RCC_CLOCKTYPE_HCLK | RCC_CLOCKTYPE_PCLK1 | RCC_CLOCKTYPE_PCLK2);
182
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
183
  RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
184
  RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV4;  
185
  RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV2;  
186
  HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_4);
187
188
  /* STM32F405x/407x/415x/417x Revision Z devices: prefetch is supported  */
189
  if (HAL_GetREVID() == 0x1001)
190
  {
191
    /* Enable the Flash prefetch */
192
    __HAL_FLASH_PREFETCH_BUFFER_ENABLE();
193
  }
194
}
195
196
/**
197
  * @brief  This function is executed in case of error occurrence.
198
  * @param  None
199
  * @retval None
200
  */
201
static void Error_Handler(void)
202
{
203
  /* Turn LED5 on */
204
  BSP_LED_On(LED5);
205
  while(1)
206
  {
207
  }
208
}
209
//#pragma GCC diagnostic ignored "-Wunused-parameter"
210
/**
211
  * @brief  Conversion complete callback in non blocking mode 
212
  * @param  AdcHandle : AdcHandle handle
213
  * @note   This example shows a simple way to report end of conversion, and 
214
  *         you can add your own implementation.    
215
  * @retval None
216
  */
217
void HAL_ADC_ConvCpltCallback(__attribute__((unused)) ADC_HandleTypeDef *AdcHandle)
218
//void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* AdcHandle)
219
{
220
  /* Turn LED4 on: Transfer process is correct */
221
222
  BSP_LED_On(LED4);
223
}
aufgerufen:
1
extern ADC_HandleTypeDef    myAdcHandle;
2
void count(void){
3
//  timerSync();
4
//  while(1);
5
//  tim4irq();
6
7
//test new artifical 7segment-LED Display:
8
#define SEVENSEGSMALL_X 35
9
#define SEVENSEGSMALL_Y 50
10
#define XPOS 0
11
#define YPOS 0
12
13
14
  adctest();
15
  delay(100);  // DEBUG: conv complete überbrücken
16
17
  uint32_t adcval;
18
  //HAL_ADC_PollForConversion(&myAdcHandle, 20);  //Hier hängt's.
19
20
  adcval = HAL_ADC_GetValue(&myAdcHandle);
21
22
  printNumI((int32_t)adcval, XPOS, YPOS, 4, ' ', 0); 
23
  while(1);
24
}

von timertick_t (Gast)


Lesenswert?

Wie so oft: Drei Stunden halbherzige Fehlersuche kann fünf Minuten 
konzentriertes Arbeiten mit dem Debugger ersetzen. Hrrmpf.

Für den nächsten der über das Example stolpert:

Der ADC wurde nicht betaktet.
ADCx_CLK_ENABLE(); // <- wirkt Wunder!

Mein böser Verdacht: Die Burschen die die Cube Examples geschrieben 
haben haben sie nie wirklich auf dem finalen Zielsystem getestet sondern 
für einen uC geschrieben und dann einfach angepasst. Gewiddernochemol!

War das wieder mal so ein böser Praktikant dem man um des 
Kosten-senken-willens den Code schreiben ließ?

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.