你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

用TIMER+DMA+DAC写的一个简单DDS,能输出幅值频率可变的正弦...

[复制链接]
蓝凌风 发布时间:2017-5-22 10:32
代码如下,小伙伴们也可以增加波形的类型,使其输出更多的波形
  1. #include "dac.h"
  2. #include <math.h>


  3. #define MAXWAVECNT 200
  4. #define WAVECNT 100          //波形的阶数,阶数越大波形拟真度越高,频率会越低
  5. u16  wavedatatab[MAXWAVECNT] = {0};   //存储任意的波形数据
  6. /*自定义波形数据生成
  7. Amp为幅值 0~3.3V
  8. offset为偏置  值0~3.3V
  9. wavetype为波形类型:
  10.                     0为正弦波
  11.                     1为三角波
  12.                     2为锯齿波
  13.                     
  14. */
  15. void GEN_WAVE(float Amp,float offset,u8 wavetype)
  16. {
  17.     u16 tempAmp = Amp*4096/3.3;
  18.     u16 tempoffset = offset*4096/3.3;
  19.     u8 i;
  20.     u16 step;
  21.     switch(wavetype)
  22.     {
  23.         case 0:     for(i=0 ;i<WAVECNT;i++)
  24.                             {
  25.                             wavedatatab[i] = (u16)( tempAmp*sin(2*3.14*i/WAVECNT)+tempoffset);
  26.                             }
  27.                             break;
  28.         case 1:    step = tempAmp/(WAVECNT/2);
  29.                     for(i=0 ;i<WAVECNT;i++)  
  30.                             {
  31.                                 if(i<(WAVECNT/2))    wavedatatab[i]= i*step+tempoffset;
  32.                                 else wavedatatab[i] = (WAVECNT-i)*step+tempoffset;
  33.                             }   
  34.                             break;
  35.     case 2:     step = tempAmp/WAVECNT;     
  36.                 for(i=0 ;i<WAVECNT;i++)  
  37.                             {
  38.                                 wavedatatab[i]= i*step+tempoffset;
  39.                             }      
  40.               break;                           
  41.         default:break;      
  42.         }
  43. }   
  44.                                          
  45. void TIM2_Int_Init(u16 arr,u16 psc)
  46. {
  47.     RCC->APB1ENR|=1<<0;    //TIM2时钟使能   
  48.     TIM2->ARR=arr;   //设定计数器自动重装值
  49.     TIM2->PSC=psc;   //预分频器   
  50.     TIM2->CR1|=1<<7;       //ARPE使能
  51.         TIM2->CR2 |=0x2<<4;    //TIMER更新做为TRGO源   
  52.     TIM2->CR1 |=TIM_CR1_CEN;    //使能定时器2
  53. }
  54. void DAC_DMA_init(void)
  55. {
  56.     RCC->AHB1ENR|=1<<21;//DMA1时钟使能
  57.     DMA1_Stream5->PAR=(u32)&(DAC->DHR12R1);       //DMA外设地址
  58.     DMA1_Stream5->M0AR=(u32)wavedatatab;     //DMA 存储器0地址
  59.     DMA1_Stream5->NDTR=WAVECNT;              //DMA 传输数量
  60.     DMA1_Stream5->CR=0;          //先全部复位CR寄存器值
  61.      
  62.     DMA1_Stream5->CR|=1<<6;        //存储器到外设模式
  63.     DMA1_Stream5->CR|=1<<8;        //循环模式
  64.     DMA1_Stream5->CR|=0<<9;        //外设非增量模式
  65.     DMA1_Stream5->CR|=1<<10;       //存储器增量模式
  66.     DMA1_Stream5->CR|=1<<11;       //外设数据长度:16位
  67.     DMA1_Stream5->CR|=1<<13;       //存储器数据长度:16位
  68.     DMA1_Stream5->CR|=1<<16;       //中等优先级
  69.     DMA1_Stream5->CR|=0<<21;       //外设突发单次传输
  70.     DMA1_Stream5->CR|=0<<23;       //存储器突发单次传输
  71.     DMA1_Stream5->CR|= 0x7<<25;//通道选择
  72.     DMA1_Stream5->CR|= 1<< 0;//开DMA
  73. }

  74. //DDS初始化
  75. void Dac1_Init(void)
  76. {   
  77.     RCC->APB1ENR|=1<<29;       //使能DAC时钟      
  78.     RCC->AHB1ENR|=1<<0;    //使能PORTA时钟   
  79.     GPIO_Set(GPIOA,PIN4,GPIO_MODE_AIN,0,0,GPIO_PUPD_PU);//PA4,模拟输入,下拉   

  80.     DAC->CR|=1<<0; //使能DAC1
  81.     DAC->CR|=1<<1; //DAC1输出缓存不使能 BOFF1=1
  82.     DAC->CR|=1<<2; //使用触发功能 TEN1=1
  83.     DAC->CR|=4<<3; //DAC TIM2 TRGO,不过要TEN1=1才行
  84.     DAC->CR|=0<<6; //不使用波形发生
  85.     DAC->CR|=0<<8; //屏蔽、幅值设置
  86.     DAC->CR|=1<<12;    //DAC1 DMA使能   
  87.     DAC->DHR12R1=0;
  88.     DAC_DMA_init();
  89.     TIM2_Int_Init(100,0);
  90. }

  91. void SET_DAC_FRQ(u16 frq)
  92. {
  93.     TIM2->CR1 &=~TIM_CR1_CEN;
  94.     TIM2->ARR = frq;
  95.     TIM2->CR1 |=TIM_CR1_CEN;
  96. }

  97. void DDS_Output_Wave(float Amp,float offset,u8 wavetype,u16 frq)
  98. {
  99.     DMA1_Stream5->CR&= ~(1<< 0);//关DMA
  100.     GEN_WAVE(Amp,offset,wavetype);
  101.     SET_DAC_FRQ(frq);
  102.     DMA1_Stream5->CR|= (1<< 0);//关DMA
  103. }
复制代码


收藏 1 评论4 发布时间:2017-5-22 10:32

举报

4个回答
wolfgang2015 回答时间:2017-5-24 08:20:57
好帖,顶一下
风905067 回答时间:2017-5-26 09:33:54
请问你这个对于的是哪一个MCU啊?
风905067 回答时间:2017-5-26 14:07:02
为什么我把你这个代码复制到我工程里,却只出来高电平?没有正玄波?
xiao风残月 回答时间:2018-11-11 19:05:54
好帖,顶一下

所属标签

STM32团队

意法半导体微控制器和微处理器拥有广泛的产品线,包含低成本的8位单片机和基于ARM® Cortex®-M0、M0+、M3、M4、M33、M7及A7内核并具备丰富外设选择的32位微控制器及微处理器


最新内容

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版