Hello,
I have small test that is based on adc_dma, where I am collecting data from 2 ADC simultaneously. I would like to call a call_back function after each successfull measuring of each my 16K samples. I tried to use
but it seems that I should do it other way. The complete source is below:
Please, help me to modify this code such a way that instead to call to abdma1.interrupted() several times, my call back function ic1() is call backed.
Thank you!
I have small test that is based on adc_dma, where I am collecting data from 2 ADC simultaneously. I would like to call a call_back function after each successfull measuring of each my 16K samples. I tried to use
Code:
attachInterruptVector(IRQ_ADC_ETC0, ic1);
attachInterruptVector(IRQ_ADC_ETC1, ic2);
NVIC_ENABLE_IRQ(IRQ_ADC_ETC0);
NVIC_ENABLE_IRQ(IRQ_ADC_ETC1);
Code:
#pragma GCC push_options
#pragma GCC optimize ("Ofast")
#include <ADC.h>
#include <AnalogBufferDMA.cpp>
const int readPin_adc_0 = A16; // Fast:A0-11,16-17; No:A12-15;
const int readPin_adc_1 = A17; // Slow:A0-9,12-17; No:10-11
ADC *adc = new ADC();
const uint32_t buffer_size = 16*1024;
#define MT DMAMEM
// #define MT
MT static volatile uint16_t __attribute__((aligned(32))) dma_adc_buff1[buffer_size];
MT static volatile uint16_t __attribute__((aligned(32))) dma_adc_buff2[buffer_size];
AnalogBufferDMA abdma1(dma_adc_buff1, buffer_size, dma_adc_buff2, buffer_size);
MT static volatile uint16_t __attribute__((aligned(32))) dma_adc2_buff1[buffer_size];
MT static volatile uint16_t __attribute__((aligned(32))) dma_adc2_buff2[buffer_size];
AnalogBufferDMA abdma2(dma_adc2_buff1, buffer_size, dma_adc2_buff2, buffer_size);
// const uint32_t initial_average_value = 2048;
unsigned int CurTime[2];
int LoopCount[2];
void ProcessAnalogData(AnalogBufferDMA *pabdma, int8_t adc_num);
int IC_Count[2]={0,0};
void ic1()
{ IC_Count[0]++; }
void ic2()
{ IC_Count[1]++; }
void setup()
{ // while (!Serial && millis() < 5000) ;
pinMode(LED_BUILTIN, OUTPUT);
pinMode(readPin_adc_0, INPUT);
pinMode(readPin_adc_1, INPUT);
Serial.begin(9600);
Serial.println("Setup ADC_0");
adc->adc0->setAveraging(0); // set number of averages
adc->adc1->setAveraging(0); // set number of averages
#define ACS ADC_CONVERSION_SPEED::VERY_HIGH_SPEED
#define ASS ADC_SAMPLING_SPEED::VERY_HIGH_SPEED
#define ARE 12
adc->adc0->setResolution(ARE);
adc->adc1->setResolution(ARE);
adc->adc0->setConversionSpeed(ACS);
adc->adc0->setSamplingSpeed(ASS);
adc->adc1->setConversionSpeed(ACS);
adc->adc1->setSamplingSpeed(ASS);
abdma1.init(adc, ADC_0);
abdma2.init(adc, ADC_1);
adc->adc1->startContinuous(readPin_adc_1);
adc->adc0->startContinuous(readPin_adc_0);
Serial.println("End Setup");
CurTime[0]=CurTime[1]=ARM_DWT_CYCCNT;
LoopCount[0]=LoopCount[1]=0;
attachInterruptVector(IRQ_ADC_ETC0, ic1);
attachInterruptVector(IRQ_ADC_ETC1, ic2);
NVIC_ENABLE_IRQ(IRQ_ADC_ETC0);
NVIC_ENABLE_IRQ(IRQ_ADC_ETC1);
}
void loop()
{ if (abdma1.interrupted()) ProcessAnalogData(&abdma1, 0);
if (abdma2.interrupted()) ProcessAnalogData(&abdma2, 1);
}
void ProcessAnalogData(AnalogBufferDMA *pabdma, int8_t adc_num)
{ uint16_t min_val = 0xffff;
uint16_t max_val = 0;
volatile uint16_t *pbuffer = pabdma->bufferLastISRFilled();
int Len = pabdma->bufferCountLastISRFilled();
if ((uint32_t)pbuffer >= 0x20200000u) arm_dcache_delete((void*)pbuffer, sizeof(dma_adc_buff1));
if(((LoopCount[adc_num]++)&31)==0)
{ float sum = 0.0;
float sum2 = 0.0;
float InvLen = 1./(float)Len;
for(int i=0; i<Len; i++)
{ uint16_t val = *pbuffer;
if (val < min_val) min_val = *pbuffer;
if (val > max_val) max_val = *pbuffer;
sum += val;
}
sum*=InvLen;
for(int i=0; i<Len; i++)
{ float val = ((float)(*pbuffer)) - sum;
sum2 += val*val;
}
sum2*=InvLen;
unsigned int ct=ARM_DWT_CYCCNT;
unsigned int ct2=CurTime[adc_num]; CurTime[adc_num]=ct;
unsigned int tpc=(((ct-ct2)>>19)+1)>>1;
Serial.printf(" %d - %u(%u): Ticks/Conversion=%d, Len=%d, %u <= %u(%u) <= %u : %d %d\n", adc_num, pabdma->interruptCount(), pabdma->interruptDeltaTime(), tpc, Len,
min_val, (unsigned int)(sum+0.5), (unsigned int)(sum2+0.5), max_val, IC_Count[0], IC_Count[1]);
}
pabdma->clearInterrupt();
}
#pragma GCC pop_options
Please, help me to modify this code such a way that instead to call to abdma1.interrupted() several times, my call back function ic1() is call backed.
Thank you!