STM32 ADC mit DMA - Overrun Verständnisfrage

OP #5189098
Lesenswert?

Moin,
ich habe mit CubeMX ein einfaches Beispiel für den ADC mit DMA 
generiert. Die Initialisierung sieht wie folgt aus:
1
ADC_ChannelConfTypeDef sConfig;
2

3
hadc1.Instance = ADC1;
4
hadc1.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV8;
5
hadc1.Init.Resolution = ADC_RESOLUTION_12B;
6
hadc1.Init.ScanConvMode = ENABLE;
7
hadc1.Init.ContinuousConvMode = ENABLE;
8
hadc1.Init.DiscontinuousConvMode = DISABLE;
9
hadc1.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
10
hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START;
11
hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
12
hadc1.Init.NbrOfConversion = 6;
13
hadc1.Init.DMAContinuousRequests = ENABLE;
14
hadc1.Init.EOCSelection = ADC_EOC_SEQ_CONV;
15
if (HAL_ADC_Init(&hadc1) != HAL_OK)
16
{
17
_Error_Handler(__FILE__, __LINE__);
18
}
19

20
sConfig.Channel = ADC_CHANNEL_0;
21
sConfig.Rank = 1;
22
sConfig.SamplingTime = ADC_SAMPLETIME_480CYCLES;
23
if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
24
{
25
_Error_Handler(__FILE__, __LINE__);
26
}
27

28
// hier folgen Rank 2-6 analog

Der DMA Stream läuft im Circular Mode. Nun starte ich den ADC mit
1
HAL_ADC_Start_DMA(&hadc1, ADC_Buffer, 12);
, wodurch HAL_ADC_ConvCpltCallback kontinuierlich aufgerufen wird, wie 
es sein soll. Testweise habe ich nun ein Delay von 100ms in den Callback 
eingebaut und dachte, damit einen Overrun provozieren zu können. Dazu 
habe ich noch HAL_ADC_ErrorCallback implementiert, allerdings läuft das 
Programm munter weiter. Nur der ConvCplt-Callback wird dann entsprechend 
seltener ausgeführt.

Meine Frage ist nun: Wie genau arbeitet der DMA Transfer im Continuous 
Mode? Werden die Werte vom ADC einfach weiter in mein Array geschrieben, 
sodass ich sicherstellen muss, die Werte im Callback schnell genug 
abzuholen oder wird einfach weniger gesampled, wenn der Callback zu 
lange braucht, wie in meinem Beispiel?
Gast #5189103
Lesenswert?

Der ADC wird munter weiter laufen und auch DMA brav die Werte schreiben, 
wenn in der ISR vor dem Delay das entsprechende Register gesetzt wird - 
verwendest Du das HAL-Callback ist das der Fall.
OP #5193686
Lesenswert?

Danke für eure Antworten, so ergibt das Sinn. Ich hatte ursprünglich nur 
angenommen, dass irgendeine Fehler-ISR aufgerufen wird, wenn der 
ConvCplt-Callback (ja, aus der HAL) nicht schnell genug fertig wird.

Bei meiner Anwendung ist es jetzt nicht kritisch, aber manchmal möchte 
man ja vielleicht wissen, dass man zu langsam war. Aber dann muss man 
die Routine aus der HAL vermutlich neu implementieren...

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