OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 8702|回复: 42

多通道ADC+DMA及3ADC+DMA+AWD

[复制链接]

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
发表于 2015-12-25 00:34:05 | 显示全部楼层 |阅读模式
本帖最后由 313668972 于 2020-7-6 21:30 编辑

多通道ADC+DMA以及3ADC+DMA+AWD的实例,只有配置文件及测试部分,整个工程比较大,包括了系统,就不一起发上来了,如果要更细的说明,请下载附件文件,里边说明更细一些
     下列程序功能测试通过,绝非到处乱抄,程序为本人自会PCB上测试,不能直接适用于任何一款开发板(主要指ADC端口)请根据实际情况进行修改。
     小弟能力有限,如果表述中有错误及不当之处,还请各位指教。

首先是多通道ADC的:
void ADC_task(void *p_agr) //多路ADC 任务
{
OS_ERR err;
u16  adcx[140];
float V=0;
u8 i=0,j=0,k=0;
Adc_Init();   //ADC初始化
MYDMA_Config(DMA1_Channel1,(u32)&ADC1->DR,(u32)&adcx,132,16);//DMA1通道1,外设为ADC1,存储器为adcx,长度132.
ADC1->CR2|=1<<22; //开始规则转换
while(1)
{
V=(float)adcx[0]*(3300.0/4096);
OLED_ShowNum(16,16,(u16)V,4,16);//显示ADC的值
OLED_ShowNum(56,16,adcx[1],4,16);//显示ADC的值
OLED_ShowNum(96,16,adcx[2],4,16);//显示ADC的值
OLED_Refresh_Gram();
k=0;
for(i=0;i<14;i++)
{
for(j=0;j<6;j++)
{
LCD_ShowNum(j*40,i*16,adcx[k],4,16);
k++;
}
}
OSTimeDlyHMSM(0,0,0,500,OS_OPT_TIME_PERIODIC,&err);//延时5ms
}
}

void  Adc_Init(void)
{   
//先初始化IO口
  RCC->APB2ENR|=1<<2;    //使能PORTA口时钟
RCC->APB2ENR|=1<<4; //全能PORTC口时钟
GPIOA->CRL&=0X00FFFFFF; //PA6、PA7 anolog输入
GPIOC->CRL&=0XFFF00000; //PC0、PC1、PC2、PC3、PC4 模拟输入
RCC->APB2ENR|=1<<9;    //ADC1时钟使能   
RCC->APB2RSTR|=1<<9;    //ADC1复位
RCC->APB2RSTR&=~(1<<9); //复位结束     
RCC->CFGR&=~(3<<14);    //分频因子清零
RCC->CFGR|=1<<15; //设置为6分频给ADC转换时钟 0  2分频;1 4分频; 2  6分频;3  8分频
//SYSCLK/DIV2=12M ADC时钟设置为12M,ADC最大时钟不能超过14M!
//否则将导致ADC准确度下降!
ADC1->CR1&=0XF0FFFF;   //工作模式清零
// ADC1->CR1|=0<<16;      //独立工作模式
ADC1->CR1|=1<<8;    //扫描模式
ADC1->CR2|=1<<1; //连续转换模式
ADC1->CR2&=~(7<<17);    
ADC1->CR2|=7<<17;    //软件控制转换  
ADC1->CR2|=1<<20;      //使用外部触发(SWSTART)!!! 必须使用一个事件来触发
ADC1->CR2&=~(1<<11);   //右对齐  

ADC1->SQR1&=~(0XF<<20);
ADC1->SQR1|=2<<20;     //3个转换在规则序列中 
  ADC1->SMPR1&=~(7<<0);  //清除通道10原来的设置  
ADC1->SMPR1|=7<<0;     //通道10  239.5周期,提高采样时间可以提高精确度
ADC1->SMPR1&=~(7<<3);  //清除通道11原来的设置  
ADC1->SMPR1|=7<<3;     //通道11  239.5周期,提高采样时间可以提高精确度
ADC1->SMPR1&=~(7<<6);  //清除通道12原来的设置  
ADC1->SMPR1|=7<<6;     //通道12  239.5周期,提高采样时间可以提高精确度
ADC1->SMPR1&=~(7<<9);  //清除通道13原来的设置  
ADC1->SMPR1|=7<<9;     //通道13  239.5周期,提高采样时间可以提高精确度
ADC1->SMPR1&=~(7<<12);  //清除通道14原来的设置  
ADC1->SMPR1|=7<<12;     //通道14  239.5周期,提高采样时间可以提高精确度
ADC1->SMPR1&=~(7<<18);  //清除通道16原来的设置  
ADC1->SMPR1|=7<<18;     //通道16  239.5周期,提高采样时间可以提高精确度  

ADC1->CR2|=1<<0;     //开启AD转换器
ADC1->CR2|=1<<8; //允许DMA访问
ADC1->CR2|=1<<3;        //使能复位校准  
while(ADC1->CR2&1<<3); //等待校准结束  
//该位由软件设置并由硬件清除。在校准寄存器被初始化后该位将被清除。  
ADC1->CR2|=1<<2;        //开启AD校准    
while(ADC1->CR2&1<<2);  //等待校准结束 //该位由软件设置以开始校准,并在校准结束时由硬件清除
// ADC1->CR2|=1<<22; //开始规则转换
ADC1->SQR3=10|11<<5|12<<10;
// ADC1->SQR3=10|11<<5|12<<10|13<<15|16<<20|6<<25;
// ADC1->SQR2=7|14<<5;
}

//DMA_CHx: DMA通道CHx
//cpar:外设地址
//cmar:存储器地址
//cndtr:数据传输量 
//LEN:传输数据宽度
void MYDMA_Config(DMA_Channel_TypeDef*DMA_CHx,u32 cpar,u32 cmar,u16 cndtr,u8 LEN)
{
RCC->AHBENR|=1<<0; //开启DMA1时钟
RCC->AHBENR|=1<<1; //开启DMA2时钟
delay_ms(5); //等待DMA时钟稳定
DMA_CHx->CPAR=cpar; //DMA 外设地址 
DMA_CHx->CMAR=(u32)cmar; //DMA,存储器地址
DMA1_MEM_LEN=cndtr;      //保存DMA传输数据量
DMA_CHx->CNDTR=cndtr;    //DMA,传输数据量
DMA_CHx->CCR=0X00000000; //复位
DMA_CHx->CCR|=1<<5;  //循环模式
DMA_CHx->CCR|=1<<7; //存储器增量模式
if(LEN==8)
{
DMA_CHx->CCR|=0<<8; //外设数据宽度为8位
DMA_CHx->CCR|=0<<10; //存储器数据宽度8位
}
else if(LEN==16)
{
DMA_CHx->CCR|=1<<8; //外设数据宽度为16位
DMA_CHx->CCR|=1<<10; //存储器数据宽度16位
}
else if(LEN==32)
{
DMA_CHx->CCR|=2<<8; //外设数据宽度为32位
DMA_CHx->CCR|=2<<10; //存储器数据宽度32位
}
DMA_CHx->CCR|=2<<12; //高等优先级
DMA_CHx->CCR|=0<<14; //非存储器到存储器模式
DMA_CHx->CCR|=(1<<0); //开启dma传输
}

————————————————————————————————————————————————————
以下是3ADC+DMA+AWD
void ADC_3_task((void *p_agr) //3ADC,3路通道任务,转换速度每通道都为1M
{
OS_ERR err;
u16  adcx[3];
u32 AD1[3];
u32  AD[3];
u16 ADV1[3];
u16 ADV2[3];
Adc_3_Init();   //3ADC初始化
MYDMA_Config(DMA1_Channel1,(u32)&ADC1->DR,(u32)&AD1,3,32);//DMA1通道1,外设为ADC1,存储器为adcx,长度8,32位数据宽度
MYDMA_Config(DMA2_Channel5,(u32)&ADC3->DR,(u32)&adcx,3,16);//DMA1通道1,外设为ADC1,存储器为adcx,长度8.16位数据宽度
ADC1->CR2|=1<<22; //开始规则转换
ADC3->CR2|=1<<22; //开始规则转换
while(1)
{
AD[0]=AD1[0];
AD[1]=AD1[1];
AD[2]=AD1[2];
ADV1[0]=AD[0]; //提取低半字
ADV2[0]=AD[0]>>16;
ADV1[1]=AD[1]; //提取低半字
ADV2[1]=AD[1]>>16;
ADV1[2]=AD[2]; //提取低半字
ADV2[2]=AD[2]>>16;
OLED_ShowNum(16,16,ADV1[0],4,16);//显示ADC的值
OLED_ShowNum(56,16,ADV2[0],4,16);//显示ADC的值
OLED_ShowNum(96,16,adcx[0],4,16);//显示ADC的值
OLED_ShowNum(16,32,(u16)((float)ADV1[0]*(3300.0/4096)),4,16);//显示ADC的值
OLED_ShowNum(56,32,(u16)((float)ADV2[0]*(3300.0/4096)),4,16);//显示ADC的值
OLED_ShowNum(96,32,(u16)((float)adcx[0]*(3300.0/4096)),4,16);//显示ADC的值
OLED_Refresh_Gram();
OSTimeDlyHMSM(0,0,0,500,OS_OPT_TIME_PERIODIC,&err);//延时5ms
}
}

void ADC1_2_IRQHandler(void)    //ADC1和ADC2的中断向量
{
OSIntEnter();
ADC1->SR&=~(1<<0); //清除看门狗中断标示
ADC2->SR&=~(1<<0);
OLED_ShowString(0,48,"ADC1/2 IRQ");
NVIC->ICER[0]=1<<18; //ADC1 2中断向量 除能
//如果不进行 除能,程序将一直执行中断程序,其他程序得不到执行
OSIntExit();
}

void ADC3_IRQHandler(void)    //ADC3的中断向量
{
OSIntEnter();
ADC3->SR&=~(1<<0); //清除看门狗中断标示
OLED_ShowString(0,48,"ADC3 IRQ");
NVIC->ICER[1]=1<<15; //ADC3 中断向量 除能
OSIntExit();
}
void  Adc_3_Init(void)
{   
RCC->APB2ENR|=1<<4; //全能PORTC口时钟
GPIOC->CRL&=0XFFFFF000; //PC0、PC1、PC2模拟输入

RCC->APB2ENR|=1<<9;    //ADC1时钟使能
RCC->APB2ENR|=1<<10; //ADC2时钟使能
RCC->APB2ENR|=1<<15; //ADC3时钟使能 ADC3数据由DMA2 通道5控制
RCC->APB2RSTR|=1<<9;    //ADC1复位
RCC->APB2RSTR|=1<<10; //ADC2复位
RCC->APB2RSTR|=1<<15; //ADC3复位
RCC->APB2RSTR&=~(1<<9|1<<10|1<<15);//复位结束
RCC->CFGR&=~(3<<14);   //分频因子清零
RCC->CFGR|=1<<15;//设置为4分频给ADC转换时钟  
//SYSCLK/DIV2=12M ADC时钟设置为12M,ADC最大时钟不能超过14M!
//否则将导致ADC准确度下降!
ADC1->CR1&=0XF0FFFF;   //工作模式清零
ADC1->CR1|=6<<16;      //同步规则模式 此寄存器只有ADC1有,ADC2 3此位为保留位
ADC1->CR1|=1<<8;    //扫描模式
ADC2->CR1|=1<<8; //扫描模式
ADC3->CR1|=1<<8;
ADC1->CR2|=1<<1; //连续转换模式
ADC2->CR2|=1<<1;
ADC3->CR2|=1<<1;
ADC1->CR2&=~(7<<17); //清除外部事件
ADC2->CR2&=~(7<<17);
ADC3->CR2&=~(7<<17);

ADC1->CR2|=7<<17;    //软件控制转换  
ADC1->CR2|=1<<20;      //使用外部触发(SWSTART)!!! 必须使用一个事件来触发
ADC2->CR2|=7<<17;    //软件控制转换  
ADC2->CR2|=1<<20;      //使用外部触发(SWSTART)!!! 必须使用一个事件来触发
ADC3->CR2|=7<<17;    //软件控制转换  
ADC3->CR2|=1<<20;      //使用外部触发(SWSTART)!!! 必须使用一个事件来触发

ADC1->CR2&=~(1<<11);   //右对齐
ADC2->CR2&=~(1<<11);
ADC3->CR2&=~(1<<11);
ADC1->CR2|=1<<0;     //开启AD转换器
ADC2->CR2|=1<<0;
ADC3->CR2|=1<<0;
ADC1->CR1|=1<<23; //在规格通道上开启模拟看门狗(监测所有规则通道)
ADC2->CR1|=1<<23;
ADC3->CR1|=1<<23;
ADC1->CR1|=1<<6; //允许产生模拟看门狗中断
ADC2->CR1|=1<<6;
ADC3->CR1|=1<<6;
//ADC1->CR1|=* //模拟看门狗通道选择位  4:0,
ADC1->HTR=3000; //ADC看门狗高阀值寄存器
ADC2->HTR=4000;
ADC3->HTR=3000;
ADC1->LTR=1000; //ADC看门狗低阀值寄存器
ADC2->LTR=100;
ADC3->LTR=300;
NVIC->ISER[0]=1<<18; //ADC1 2中断向量
NVIC->ISER[1]=1<<15; //ADC3 中断向量

ADC1->SQR1&=~(0XF<<20);
ADC1->SQR1|=0<<20;     //1个转换在规则序列中 
ADC2->SQR1&=~(0XF<<20);
ADC2->SQR1|=0<<20;     //1个转换在规则序列中 
ADC3->SQR1&=~(0XF<<20);
ADC3->SQR1|=0<<20;
// ADC1->SMPR1&=~(7<<0);  //清除通道10原来的设置  
// ADC1->SMPR1|=7<<0;     //通道10  239.5周期,提高采样时间可以提高精确度
//
// ADC2->SMPR1&=~(7<<3);  //清除通道11原来的设置  
// ADC2->SMPR1|=7<<3;     //通道11  239.5周期,提高采样时间可以提高精确度
//
// ADC3->SMPR1&=~(7<<6);  //清除通道12原来的设置  
// ADC3->SMPR1|=7<<6;     //通道12  239.5周期,提高采样时间可以提高精确度

ADC1->CR2|=1<<8; //允许DMA访问 只有ADC1 和ADC3能使用DMA
ADC3->CR2|=1<<8;

ADC1->CR2|=1<<3;        //使能复位校准  
while(ADC1->CR2&1<<3); //等待校准结束 //该位由软件设置并由硬件清除。在校准寄存器被初始化后该位将被清除。
ADC2->CR2|=1<<3;        //使能复位校准  
while(ADC2->CR2&1<<3); //等待校准结束 //该位由软件设置并由硬件清除。在校准寄存器被初始化后该位将被清除。
ADC3->CR2|=1<<3;        //使能复位校准
while(ADC3->CR2&1<<3); //等待校准结束 //该位由软件设置并由硬件清除。在校准寄存器被初始化后该位将被清除。
ADC1->CR2|=1<<2;        //开启AD校准     开启ADC校准之前ADC必须处于断电状态2个ADC时钟周期
while(ADC1->CR2&1<<2);  //等待校准结束 //该位由软件设置以开始校准,并在校准结束时由硬件清除
ADC2->CR2|=1<<2;        //开启AD校准    
while(ADC2->CR2&1<<2);  //等待校准结束 //该位由软件设置以开始校准,并在校准结束时由硬件清除
ADC3->CR2|=1<<2;        //开启AD校准    
while(ADC3->CR2&1<<2);  //等待校准结束 //该位由软件设置以开始校准,并在校准结束时由硬件清除
// ADC1->CR2|=1<<22; //开始规则转换
// ADC2->CR2|=1<<22;
// ADC3->CR2|=1<<22;
ADC1->SQR3=10;
ADC2->SQR3=11;
ADC3->SQR3=12;
}

DMA函数没有变化,就不再贴上来了




多通道ADC及3ADC +DMA+AWD.pdf

196.6 KB, 下载次数: 1841

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

15

主题

786

帖子

5

精华

论坛大神

Rank: 7Rank: 7Rank: 7

积分
3223
金钱
3223
注册时间
2015-7-26
在线时间
811 小时
发表于 2015-12-25 08:10:31 | 显示全部楼层
我的博客:http://blog.csdn.net/itdo_just
回复 支持 反对

使用道具 举报

27

主题

711

帖子

0

精华

版主

Rank: 7Rank: 7Rank: 7

积分
12592
金钱
12592
注册时间
2015-11-5
在线时间
2153 小时
发表于 2015-12-25 09:10:41 | 显示全部楼层
顶风筝哥!!!
拿来长岛冰茶换我半晚安睡
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2015-12-28 11:55:15 | 显示全部楼层

一点心得,只是希望遇到同样问题的朋友少走一点弯路
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2015-12-28 11:55:44 | 显示全部楼层

谢谢恩哥的顶
回复 支持 反对

使用道具 举报

1

主题

5

帖子

0

精华

新手上路

积分
36
金钱
36
注册时间
2015-7-28
在线时间
7 小时
发表于 2016-1-5 18:24:38 | 显示全部楼层
请问在一个循环内十四次显示同一个数组,是因为dma会在程序运行中不打断程序而不断更新数据吗?
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-5 22:52:52 | 显示全部楼层
西安的新人 发表于 2016-1-5 18:24
请问在一个循环内十四次显示同一个数组,是因为dma会在程序运行中不打断程序而不断更新数据吗?

你好,你所说的在一个循环中十四次显示同一个数组,其实不是14次,而是显示数组 adcx 的前14x6个元素,只是在显示屏中以14行,6列的形式显示。
DMA在运行中基本不干扰程序的运行,示例程序只是实现了一个最基本的功能。实际在显示的时候,比如显示到adcx[20]的时候,一个DMA过程刚好传输到这第20个参数,则adcx[0]至adcx[20]的数据是刚更新的,而adcx[21]以之后的数据是上一次DMA传进来的数据,如果ADC端口输入的模拟量为正弦波,在adcx[20]至adcx[21]这个点上就可以看到明显的波形不连续的情况;如果想要在进行数据显示的时候得到连续的采样的数据,需要使用DMA传输完成中断,当DMA完成一个数据传输周期(如程序中的132个数据)后发生中断,通过中断把数组中的数据进行一次拷贝,以保证用于显示的数组中的数据是完整且是连续采样的。
回复 支持 反对

使用道具 举报

1

主题

5

帖子

0

精华

新手上路

积分
36
金钱
36
注册时间
2015-7-28
在线时间
7 小时
发表于 2016-1-6 08:57:47 | 显示全部楼层
313668972 发表于 2016-1-5 22:52
你好,你所说的在一个循环中十四次显示同一个数组,其实不是14次,而是显示数组 adcx 的前14x6个元素,只 ...

多谢解释,是我没看程序看清楚,至于补充的数据不连续问题我也正好碰到,多谢指点
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-6 09:13:09 | 显示全部楼层
西安的新人 发表于 2016-1-6 08:57
多谢解释,是我没看程序看清楚,至于补充的数据不连续问题我也正好碰到,多谢指点

不用谢,客气了。
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
37
金钱
37
注册时间
2015-12-2
在线时间
5 小时
发表于 2016-1-16 06:55:26 | 显示全部楼层
很详细,很幽默。学习了。感谢!
回复 支持 反对

使用道具 举报

0

主题

12

帖子

0

精华

新手上路

积分
39
金钱
39
注册时间
2016-1-5
在线时间
10 小时
发表于 2016-1-16 09:06:33 | 显示全部楼层
谢谢楼主分享!
回复 支持 反对

使用道具 举报

2

主题

394

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
2115
金钱
2115
注册时间
2012-5-8
在线时间
314 小时
发表于 2016-1-16 09:10:05 | 显示全部楼层
注释很详尽也很有意思!
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-19 22:27:51 | 显示全部楼层
zuoyi 发表于 2016-1-16 09:10
注释很详尽也很有意思!

详细一些,更容易看懂,我希望是每一个看过的人,基本能懂
注释嘛,反正就是自己逗自己开心一下,不然全是if/for/switch 那多没意思
回复 支持 反对

使用道具 举报

0

主题

3

帖子

0

精华

新手入门

积分
5
金钱
5
注册时间
2016-1-20
在线时间
0 小时
发表于 2016-1-20 22:17:25 | 显示全部楼层
楼主你好,我有关于DMA和AD的问题请教您:
怎么实现ADC转换完成一个数据,DMA保存一次。
我配置了DMA和AD后,DMA一直在存储AD数据寄存器中的数据。中间产生了很多冗余的数据
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-21 09:19:57 | 显示全部楼层
qulei 发表于 2016-1-20 22:17
楼主你好,我有关于DMA和AD的问题请教您:
怎么实现ADC转换完成一个数据,DMA保存一次。
我配置了DMA和AD ...

如果你使用了DMA来转存ADC数据,根据配置(比如规则通道序列)来对数据进行转存,每当ADC转换完成后,DMA就会把数据搬运到你指定的缓存中(比如数组),这个过程一段初始化成功,如果使用了循环模式,是不需要CPU再进行干涉的,DMA会自动处理接下来的工作。
至于你说的中间产生了很多冗余的数据,这个根你配置的采样率有关系,其实你不必在意这个问题,当你需要ADC数据的时候,直接从缓存中读取数据就可以了,不需要做额外的处理,不需要等待,可以有效的提高程序运行速度。
回复 支持 反对

使用道具 举报

2

主题

21

帖子

0

精华

初级会员

Rank: 2

积分
65
金钱
65
注册时间
2016-1-4
在线时间
13 小时
发表于 2016-1-21 14:18:09 | 显示全部楼层
新手,正在搞这个,很重要,弄下来看看,务必要谢谢楼主!!!
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-21 21:31:41 | 显示全部楼层
cpu12g000 发表于 2016-1-21 14:18
新手,正在搞这个,很重要,弄下来看看,务必要谢谢楼主!!!

希望对你有帮助
回复 支持 反对

使用道具 举报

0

主题

3

帖子

0

精华

新手入门

积分
43
金钱
43
注册时间
2014-11-12
在线时间
4 小时
发表于 2016-1-29 00:24:16 | 显示全部楼层
谢谢分享,学习了。
回复 支持 反对

使用道具 举报

5

主题

56

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
227
金钱
227
注册时间
2015-11-29
在线时间
46 小时
发表于 2016-1-29 17:07:56 | 显示全部楼层
谢谢分享!!!
回复 支持 反对

使用道具 举报

154

主题

289

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
1067
金钱
1067
注册时间
2015-4-13
在线时间
189 小时
发表于 2016-1-29 21:27:37 | 显示全部楼层
谢谢分享,才学到2ADC,3ADC资料很少
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-1-29 22:44:24 | 显示全部楼层
jeraw 发表于 2016-1-29 21:27
谢谢分享,才学到2ADC,3ADC资料很少

希望对你有帮助
回复 支持 反对

使用道具 举报

3

主题

92

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
275
金钱
275
注册时间
2012-6-19
在线时间
37 小时
发表于 2016-2-5 10:31:41 | 显示全部楼层
感谢楼主,感谢大公无私的分享!很有帮助。
回复 支持 反对

使用道具 举报

1

主题

8

帖子

0

精华

初级会员

Rank: 2

积分
70
金钱
70
注册时间
2016-1-11
在线时间
20 小时
发表于 2016-2-6 20:38:15 | 显示全部楼层
谢谢
回复 支持 反对

使用道具 举报

1

主题

78

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
211
金钱
211
注册时间
2015-12-10
在线时间
49 小时
发表于 2016-2-14 02:21:11 | 显示全部楼层
313668972 发表于 2016-1-21 09:19
如果你使用了DMA来转存ADC数据,根据配置(比如规则通道序列)来对数据进行转存,每当ADC转换完成后,DMA ...

楼主很棒的分享。
菜鸟提问:
如果连续等间隔采集(用于FFT分析的波形)数据,冗余的数据就有害了。
比如,对ADC的某一通道,以10us为间隔,连续采集1024点(一个波形序列),用DMA把每次的ADC数据转存的RAM,波形序列采集完成后,DMA产生中断,在这个中断中为已经挂起的波形处理任务发送一个消息,启动新的一次处理...
这是一种典型的综合应用。
请大侠指点。
逆水行舟不进则退
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-2-15 09:22:21 | 显示全部楼层
gelin_ss 发表于 2016-2-14 02:21
楼主很棒的分享。
菜鸟提问:
如果连续等间隔采集(用于FFT分析的波形)数据,冗余的数据就有 ...

你好,我没太明白你说的冗余数据是那一部分
回复 支持 反对

使用道具 举报

1

主题

78

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
211
金钱
211
注册时间
2015-12-10
在线时间
49 小时
发表于 2016-2-16 03:19:28 | 显示全部楼层
313668972 发表于 2016-2-15 09:22
你好,我没太明白你说的冗余数据是那一部分

我可能没理解对你15楼的回帖。
逆水行舟不进则退
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-2-16 09:42:16 | 显示全部楼层
gelin_ss 发表于 2016-2-16 03:19
我可能没理解对你15楼的回帖。

哦,15楼回贴,他是考虑DMA在对ADC数据进行转存时,如果使用了循环模式,DMA会连续不断地将数据存到指定的地址中;但在实际使用时,并不需要这么多数据,多余的采样就会出现数据冗余;实际上这种数据冗余可以不用担心,DMA对ADC数据进行转存是不消耗CPU资源的,所以不用考虑这些。
对于你所需要的采样后进行FFT处理,改变DMA工作模式(我在程序中使用了循环模式),就可以完成单次数据转存。
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-2-16 22:53:52 | 显示全部楼层
gelin_ss 发表于 2016-2-16 03:19
我可能没理解对你15楼的回帖。

不好意思,更正一下之前的说法,当使用DMA转存ADC数据时,是会占用系统资源的(虽然不消耗CPU资源,因为中间过程不需要CPU干预)。
当CPU和DMA同时访问相同的目标(RAM或外设)时,DMA请求会暂停CPU访问系统总线达若干个周期,总线仲裁器执行循环调度,以保证CPU至少可以得到一半的系统总线(存储器或外设)带宽。
虽然ADC最高速度只有1MHz,以3ADC来计算,也最多3MHz,但必定还是占用了系统总线。
回复 支持 反对

使用道具 举报

66

主题

364

帖子

0

精华

初级会员

Rank: 2

积分
132
金钱
132
注册时间
2015-6-18
在线时间
129 小时
发表于 2016-4-8 16:47:42 | 显示全部楼层
   MYDMA_Config(DMA1_Channel1,(u32)&ADC1->DR,(u32)&adcx,132,16);//DMA1通道1,外设为ADC1,存储器为adcx,长度132.  为什么长度是132?
回复 支持 反对

使用道具 举报

66

主题

364

帖子

0

精华

初级会员

Rank: 2

积分
132
金钱
132
注册时间
2015-6-18
在线时间
129 小时
发表于 2016-4-8 16:57:16 | 显示全部楼层
良心贴啊,大神我要加你QQ
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-4-11 12:58:04 | 显示全部楼层
xiaobudonglaosh 发表于 2016-4-8 16:47
MYDMA_Config(DMA1_Channel1,(u32)&ADC1->DR,(u32)&adcx,132,16);//DMA1通道1,外设为ADC1,存储器为adcx, ...

长度132只是根据我的序列数等参数来确定的,比如我有4个序列,则在一次DMA过程中,包含每个通道的33次转换,这些数据可以用于滤波、求平均值等等运算,完全是根据自己需要
回复 支持 反对

使用道具 举报

5

主题

36

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
263
金钱
263
注册时间
2015-4-18
在线时间
70 小时
发表于 2016-4-18 16:22:54 | 显示全部楼层
能否给我发一份整个工程
回复 支持 反对

使用道具 举报

5

主题

36

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
263
金钱
263
注册时间
2015-4-18
在线时间
70 小时
发表于 2016-4-18 16:23:45 | 显示全部楼层
能否给我发一份整个工程,799224707@qq.com, @313668972
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-4-18 17:10:38 | 显示全部楼层
我zai路上 发表于 2016-4-18 16:23
能否给我发一份整个工程,, @313668972

整个工程没啥用啊,板子是自己画的,基本所有接口都不适用,关于ADC的所有功能函数都在文档里边了
回复 支持 反对

使用道具 举报

5

主题

36

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
263
金钱
263
注册时间
2015-4-18
在线时间
70 小时
发表于 2016-4-19 10:07:21 | 显示全部楼层
313668972 发表于 2016-4-18 17:10
整个工程没啥用啊,板子是自己画的,基本所有接口都不适用,关于ADC的所有功能函数都在文档里边了

我是想看看系统部分
回复 支持 反对

使用道具 举报

5

主题

36

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
263
金钱
263
注册时间
2015-4-18
在线时间
70 小时
发表于 2016-4-20 08:10:27 | 显示全部楼层
@313668972 我不知道在ucos下怎么写的,所以有可能的话,还是能给发一份好,拜托了
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2016-4-24 14:17:35 | 显示全部楼层
我zai路上 发表于 2016-4-20 08:10
@313668972 我不知道在ucos下怎么写的,所以有可能的话,还是能给发一份好,拜托了

如果你了解过操作系统部分,应该就知道,这和其他应用 没什么区别
整个工程有许多其他资料,不能外发,希望能理解,谢谢
回复 支持 反对

使用道具 举报

0

主题

52

帖子

0

精华

初级会员

Rank: 2

积分
83
金钱
83
注册时间
2013-5-30
在线时间
3 小时
发表于 2016-5-19 16:52:39 | 显示全部楼层
做自己喜欢做的的事,爱自己所爱的人!
回复 支持 反对

使用道具 举报

0

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
61
金钱
61
注册时间
2019-12-1
在线时间
11 小时
发表于 2019-12-1 09:33:19 | 显示全部楼层
看到在是乱码
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2019-12-11 12:57:31 | 显示全部楼层

不知道为啥,以前不是乱的,你下载PDF文件吧,
回复 支持 反对

使用道具 举报

0

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
61
金钱
61
注册时间
2019-12-1
在线时间
11 小时
发表于 2020-2-14 15:36:43 | 显示全部楼层
?BANGMA帮忙看下
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2020-7-6 21:32:49 | 显示全部楼层
今天自己也正好用到之前的代码,来看了看页面,发现居码了,附件也不见了,重新简单整理了一下。
回复 支持 反对

使用道具 举报

13

主题

276

帖子

0

精华

高级会员

Rank: 4

积分
697
金钱
697
注册时间
2014-6-20
在线时间
146 小时
 楼主| 发表于 2020-7-6 21:33:37 | 显示全部楼层

现在已经不乱了,如果还需要,您可以看看
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-6-29 15:34

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表