OpenEdv-开源电子网

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

关于DMA初学者的提问

[复制链接]

4

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
77
金钱
77
注册时间
2018-4-4
在线时间
15 小时
发表于 2018-4-4 19:18:04 | 显示全部楼层 |阅读模式
1金钱
我通过控制外置AD7606来采集模拟信号,数据通过DMA发送到串口1的接收端。现在可以查看到串口1能够接收到数据,数据也是正确的,但是我更换模拟量电压值时候DMA传上来的数据却没有发生变化。比如说我初始电压值为1V,把电压值更换为2V后DMA给串口的数据依然是1V。这个问题是不是我初始化或者其他地方写错了?
#include "dma.h"

void dma_init()
{
       
        DMA_InitTypeDef DMA_InitStructure;
        RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1,ENABLE);

        DMA_InitStructure.DMA_BufferSize=2;//设置传输数据位数为2个
        DMA_InitStructure.DMA_DIR=DMA_DIR_PeripheralDST;//外设作为数据地址,由内存到数据
        DMA_InitStructure.DMA_M2M=DMA_M2M_Disable;//失能从内存到内存
        DMA_InitStructure.DMA_MemoryBaseAddr=(u32) &caiyangE;//内存地址为caiyangE
        DMA_InitStructure.DMA_MemoryDataSize=DMA_MemoryDataSize_Byte;//内存字节长度为16位
        DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;//内存地址递增
        DMA_InitStructure.DMA_Mode=DMA_Mode_Circular;//循环发送
        DMA_InitStructure.DMA_PeripheralBaseAddr =(u32) &USART1->DR;//外设地址为串口1地址
        DMA_InitStructure.DMA_PeripheralDataSize=DMA_PeripheralDataSize_Byte ;//外设接受字节长度为16位
        DMA_InitStructure.DMA_PeripheralInc=DMA_PeripheralInc_Disable;//失能外设地址递增
        DMA_InitStructure.DMA_Priority=DMA_Priority_High ;//优先级高
        DMA_Init(DMA1_Channel4,&DMA_InitStructure);
       
        USART_DMACmd(USART1,USART_DMAReq_Tx,ENABLE);
        DMA_Cmd(DMA1_Channel4,ENABLE);

}

主函数如下
int main()
{
        static        u16 caiyangA[2000];
        static  u16 caiyangB;
        double ture=0.0,ture1=0.0;
        u16 i;
        printf_init();
        ad_init_GPIO();
        usart_init();
        dma_init();
        for(i=0;i<2000;i++)
        {

                GPIO_SetBits(GPIOD,RE);
                GPIO_ResetBits(GPIOD,RE);//软件复位
               
                GPIO_ResetBits(GPIOD,CVA);
                GPIO_SetBits(GPIOD,CVA);
               
                while(GPIO_ReadInputDataBit(GPIOD,BUSY)==1);
                GPIO_ResetBits(GPIOD,RD);
                caiyangB=GPIO_ReadInputData(GPIOE);
                GPIO_SetBits(GPIOD,RD);
                caiyangE[0]=caiyangB/256;
                caiyangE[1]=caiyangB%256;
       
                GPIO_ResetBits(GPIOD,RD);
                caiyangA[i]=GPIO_ReadInputData(GPIOE);
                GPIO_SetBits(GPIOD,RD);
                if(DMA_GetFlagStatus(DMA1_FLAG_TC4)!=RESET)
                {
                        DMA_ClearFlag(DMA1_FLAG_TC4);
                        break;
                }
                MYDMA_Enable(DMA1_Channel4);
                dma_init();
        }

}

还有,在主函数中我如果用while(1)循环的话,采样只采1次,但是换成了for就没有这个问题了,请帮忙看看,谢谢各位!

最佳答案

查看完整内容[请看2#楼]

1,你这仅仅是ADC采集数据,然后dma到串口,并不是直接dma采集adc数据,只需要修改你的发送数组即可。 2,你的ADC采集,先看不用dma,传输是否正确? 3,main函数用while才对,不要用for判断i这种写法。 最后,所有这些疑点,仿真很容易找到问题,所以,多仿真吧。
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2018-4-4 19:18:05 | 显示全部楼层
1,你这仅仅是ADC采集数据,然后dma到串口,并不是直接dma采集adc数据,只需要修改你的发送数组即可。
2,你的ADC采集,先看不用dma,传输是否正确?
3,main函数用while才对,不要用for判断i这种写法。
最后,所有这些疑点,仿真很容易找到问题,所以,多仿真吧。
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复

使用道具 举报

4

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
77
金钱
77
注册时间
2018-4-4
在线时间
15 小时
 楼主| 发表于 2018-4-4 19:18:45 | 显示全部楼层
自己顶一下,@原子哥 帮忙看一下
回复

使用道具 举报

4

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
77
金钱
77
注册时间
2018-4-4
在线时间
15 小时
 楼主| 发表于 2018-4-5 15:18:30 | 显示全部楼层
已经找到问题了,谢谢原子哥
回复

使用道具 举报

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

本版积分规则



关闭

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

正点原子公众号

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

GMT+8, 2025-6-16 19:53

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

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