2015-09-29 02:29 AM
Hallo,
I'm trying to modify an example which uses ADC + DMA, which uses the ST-provided HAL, to my needs. I want to use a buffer and be notified when each half is completed, so I can transfer the data in a double buffer scheme. I implemented these functions, which both do get called: void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc) void HAL_ADC_ConvHalfCpltCallback(ADC_HandleTypeDef* hadc) But - I added variables using HAL_GetTicks (1ms resolution) to store for each function when it was called. With a samplerate of roughly 8000 Hz and a buffer of 128 samples, i.e. half buffer of 64 samples, the interval should be about 8 milliseconds. But according to my measurement, the half completed and completed callbacks get called in the same millisecond. What could be wrong?The sysclock is at 80 MHz.
ADC + DMA config:
/* ADC Periph interface clock configuration */
__HAL_RCC_ADC_CONFIG(RCC_ADCCLKSOURCE_SYSCLK)
AdcHandle.Init.ClockPrescaler = ADC_CLOCK_ASYNC_DIV16; /* Asynchronous clock mode, input ADC clock not divided */
AdcHandle.Init.Resolution = ADC_RESOLUTION_12B; /* 12-bit resolution for converted data */
AdcHandle.Init.DataAlign = ADC_DATAALIGN_RIGHT; /* Right-alignment for converted data */
AdcHandle.Init.ScanConvMode = DISABLE; /* Sequencer disabled (ADC conversion on only 1 channel: channel set on rank 1) */
AdcHandle.Init.EOCSelection = ADC_EOC_SINGLE_CONV; /* EOC flag picked-up to indicate conversion end */
AdcHandle.Init.LowPowerAutoWait = DISABLE; /* Auto-delayed conversion feature disabled */
AdcHandle.Init.ContinuousConvMode = ENABLE; /* Continuous mode enabled (automatic conversion restart after each conversion) */
AdcHandle.Init.NbrOfConversion = 1; /* Parameter discarded because sequencer is disabled */
AdcHandle.Init.DiscontinuousConvMode = DISABLE; /* Parameter discarded because sequencer is disabled */
AdcHandle.Init.NbrOfDiscConversion = 1; /* Parameter discarded because sequencer is disabled */
AdcHandle.Init.ExternalTrigConv = ADC_SOFTWARE_START; /* Software start to trig the 1st conversion manually, without external event */
AdcHandle.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE; /* Parameter discarded because software trigger chosen */
AdcHandle.Init.DMAContinuousRequests = ENABLE; /* DMA circular mode selected */
AdcHandle.Init.Overrun = ADC_OVR_DATA_OVERWRITTEN; /* DR register is overwritten with the last conversion result in case of overrun */
AdcHandle.Init.OversamplingMode = DISABLE; /* No oversampling */
//---------------------------------------------------------------------------
/* ### - 3 - Channel configuration ######################################## */
sConfig.Channel = ADCx_CHANNEL; /* Sampled channel number */
sConfig.Rank = ADC_REGULAR_RANK_1; /* Rank of sampled channel number ADCx_CHANNEL */
sConfig.SamplingTime = ADC_SAMPLETIME_640CYCLES_5; /* Sampling time (number of clock cycles unit) */
sConfig.SingleDiff = ADC_SINGLE_ENDED; /* Single-ended input channel */
sConfig.OffsetNumber = ADC_OFFSET_NONE; /* No offset subtraction */
sConfig.Offset = 0;
//---------------------------------------------------------------------------
DmaHandle.Instance = DMA1_Channel1;
DmaHandle.Init.Request = DMA_REQUEST_0;
DmaHandle.Init.Direction = DMA_PERIPH_TO_MEMORY;
DmaHandle.Init.PeriphInc = DMA_PINC_DISABLE;
DmaHandle.Init.MemInc = DMA_MINC_ENABLE;
DmaHandle.Init.PeriphDataAlignment = DMA_PDATAALIGN_WORD;
DmaHandle.Init.MemDataAlignment = DMA_MDATAALIGN_WORD;
DmaHandle.Init.Mode = DMA_CIRCULAR;
DmaHandle.Init.Priority = DMA_PRIORITY_MEDIUM;
#stm32l476