当前位置:网站首页 > 技术博客 > 正文

dds信号发生器vhdl



DDS(Direct Digital Synthesis)是一种把一系列数字信号通过D/A转换器转换成模拟信号的数字合成技术。

它有查表法和计算法两种基本合成方法。在这里主要记录DDS查表法的fpga实现。

查表法:由于ROM查询法结构简单,只需要在ROM中存放不同相位对应的幅度序列,然后通过相位累加器的输出对其寻址,经过数/模转换和低通滤波(LPF)输出便可以得到所需要的模拟信号。

查表法示意图:

 

设计:

  输入:频率控制字f,相位控制字,系统时钟Fclk,复位信号reset

  输出:幅度数据dout。

  关系:Tout = M * Tclk 即 Fout = Fclk / M 。其中,M为一个波形的离散点数。

简单解释一下:比如我们把一个正弦波形分为16个点,而ROM容量为8,那么我们的点数间隔就要取16 / 8 = 2 ,即频率控制字为 2 。

细节:由于在设计时点数间隔不一定为1,即相位累加器的值可能大于ROM容量,所以我们要取它的高位到ROM中取相位对应的幅度点。如:频率控制字=4,则相位累加器的值为:0(00000),4(00100),8(01000),12(010100) .......  也就是说因为步进4(100),后两位将一直保持不变,高位每次加1(1个4),可以类比十进制理解:每次加10:000,010,020,030...最后一位不变。

 代码实现:

module DDS_Module( clk , reset , f_ctrl , p_ctrl , dout ); input clk ; input reset ; input [2:0]f_ctrl ;//(取值限制为2的倍数) input [9:0]p_ctrl ; output [9:0]dout ; //频率控制字寄存器(频率)(大于1的时候,后面相位累加器输出到实时相位时要砍掉它的位宽) reg [2:0]f_regist ;//(取值限制为2的倍数) always @ (posedge clk) f_regist <= f_ctrl ; //相位累加器 (f * t) reg [12:0]p_add ; always@(posedge clk or negedge reset ) if(!reset ) p_add <= 0 ; else p_add <= p_add + f_regist ; //相位控制字寄存器(初始相位)(相位偏移量) reg [9:0]p_regist ; always @ (posedge clk) p_regist <= p_ctrl ; //实时相位 reg [9:0]p_now ; always@(posedge clk or negedge reset ) if(!reset ) p_now <= 0 ; else p_now <= p_add[12:3] + p_regist ; //取相位累加器的前10位,因为f每次+4,后三位是不变的 DDS_ROM DDS_ROM( .clka(clk), .addra(p_now), .douta(dout) ); endmodule

这里是需要引用ROM的IP核的,上节内容。

`timescale 1ns / 1ps module DDS_tb( ); reg clk ; reg reset ; reg [2:0]f_ctrl1 ; reg [2:0]f_ctrl2 ; reg [9:0]p_ctrl1 ; reg [9:0]p_ctrl2 ; wire [9:0]dout1 ; wire [9:0]dout2 ; DDS_Module DDS_Module1( .clk(clk) , .reset(reset) , .f_ctrl(f_ctrl1) , .p_ctrl(p_ctrl1) , .dout(dout1) ); DDS_Module DDS_Module2( .clk(clk) , .reset(reset) , .f_ctrl(f_ctrl2) , .p_ctrl(p_ctrl2) , .dout(dout2) ); initial clk = 1 ; always #10 clk = !clk ; initial begin reset = 0 ; f_ctrl1 = 0 ; p_ctrl1 = 0 ; f_ctrl2 = 0 ; p_ctrl2 = 0 ; #201 ; reset = 1 ; #201 ; f_ctrl1 = 3'd4; p_ctrl1 = 10'd0 ; f_ctrl2 = 3'd4; p_ctrl2 = 10'd0 ; #90000 ; #90000 ; #90000 ; #90000 ; f_ctrl1 = 3'd4; p_ctrl1 = 10'd0 ; f_ctrl2 = 3'd4; p_ctrl2 = 10'd256 ; #90000 ; #90000 ; #90000 ; f_ctrl1 = 3'd4; p_ctrl1 = 10'd0 ; f_ctrl2 = 3'd4; p_ctrl2 = 10'd512 ; #90000 ; #90000 ; #90000 ; $stop; end endmodule

效果:分别是相位差  0° ,90 °,180°

版权声明


相关文章:

  • 计算机组成原理华中科技大学课后题2025-05-28 20:30:01
  • pylucene安装2025-05-28 20:30:01
  • 深度信念网络基本原理2025-05-28 20:30:01
  • html5中不支持哪个标签2025-05-28 20:30:01
  • 武汉电信的ip地址是多少2025-05-28 20:30:01
  • vlan互通配置2025-05-28 20:30:01
  • selenium自动化测试报告2025-05-28 20:30:01
  • 移动端主流框架2025-05-28 20:30:01
  • debug stack trace for2025-05-28 20:30:01
  • 多目标优化定义2025-05-28 20:30:01