zoukankan      html  css  js  c++  java
  • 基于FPGA的通信信号源的设计

    通信信号源设计原理

        通过设计一个DDS信号源,然后将该信号作为载波信号,再对基带信号进行2ASK、2FSK、2PSK、2DPSK调制,进而产生多种通信信号。

        设计框图如下:

        将PN序列进行2ASK、2FSK、2PSK、2DPSK调制,其中载波发生器提供三种不同的载波信号,按键设置用来选择当前DAC输出的最终调制信号,DAC输出模块将调制好的数字化波形转换为模拟信号。

        PN序列采用的设计方法是m序列,采用3级寄存器生成7序列基带信号。

        调制模块分别包含:2ASK、2FSK、2PSK、2DPSK这四种调制方式,可以通过按键选择所要输出的调制信号。

        按键设置,主要分为按键消抖和按键编码,用来切换输出信号。

        载波发生器,采用DDS的方法进行生成三种载波信号,分别为:500Hz(起始相位为0度),1K(起始相位为0度),1K(起始相位为180度)。

        DAC输出模块,这是驱动TLC5615的硬件接口,用于将数字信号转换位模拟信号。

    硬件原理图说明

    按键操作:

    波形输出:

    示波器要接LVOUT这个排针的引脚,旁边那个就是地;输出的是经过调制的正弦信号!

    136是输出PN序列,135是输出pdsk调制。

    将这两个信号接入示波器可以和前面的DAC输出进行对比。

    实验代码

    • 顶层接口模块:

    /********************************版权声明**************************************

    ** 大西瓜团队

    **

    **----------------------------文件信息--------------------------

    ** 文件名称: DDS_top.v

    ** 创建日期:

    ** 功能描述:顶层设计

    ** 硬件平台:大西瓜第3代开发板 http://daxiguafpga.taobao.com

    ** 版权声明:本代码属个人知识产权,本代码仅供交流学习.

    **---------------------------修改文件的相关信息----------------

    ** 修改人:

    ** 修改日期:        

    ** 描述:PN序列频率为500HZ

            载波1频率为500HZ

            载波2频率为1000Hz

            载波3频率为1000Hz相位相差180

    *******************************************************************************/

    module DDS_top(clk,//内部时钟

    reset,//复位

    sclk,//DAC时钟输入

    din,//DAC数据输入

    cs,//DAC片选

    m_ser_out,//PN序列输出,25引脚

    set_ask,//设置输出为ask

    set_fsk,//设置输出为fsk

    set_psk,//设置输出为psk

    set_dpsk,//设置输出为pdsk

    dpsk_code_out //pdsk调制输出,27引脚

    );

    input clk;

    input reset;

    output sclk;

    output din;

    output cs;

    input set_ask;

    input     set_fsk;

    input     set_psk;

    input     set_dpsk;

    output m_ser_out;

    output dpsk_code_out;

    wire clk;

    wire reset;

    wire set_ask_line;

    wire     set_fsk_line;

    wire     set_psk_line;

    wire     set_dpsk_line;

    wire clk_div;

    wire[9:0] data_line1;

    wire[9:0] data_line2;

    wire[9:0] data_line3;

    wire[9:0] ask_code_sin_out;

    wire[9:0] fsk_code_sin_out;

    wire[9:0] psk_code_sin_out;

    wire[9:0] dpsk_code_sin_out;

    wire[9:0] dac_data_in;

    DDS u4(.clk(clk),

    .reset_n(reset),

    .dds_data_out1(data_line1),

    .dds_data_out2(data_line2),

    .dds_data_out3(data_line3));

    m_ser u5(

    .clk(clk),//sys clk

    .reset_n(reset),//sys reset_n

    .clk_div(clk_div),

    .m_ser_out(m_ser_out)//PN ser_code out

    );

    ask_code u6(

    .clk(clk),

    .m_ser_code_in(m_ser_out),

    .dds_sin_data_in(data_line2),//10k正弦波

    .ask_code_sin_out(ask_code_sin_out)

    );

    fsk_code u7(

    .clk(clk),

    .m_ser_code_in(m_ser_out),

    .dds_sin_data_in1(data_line1),//1k正弦波

    .dds_sin_data_in2(data_line2),//10k正弦波

    .fsk_code_sin_out(fsk_code_sin_out)

    );

    psk_code u8(

    .clk(clk),

    .m_ser_code_in(m_ser_out),

    .dds_sin_data_in2(data_line2),//10k正弦波

    .dds_sin_data_in3(data_line3),//10k正弦波

    .psk_code_sin_out(psk_code_sin_out)

    );

    dpsk_code u9(

    .clk(clk_div),//sys 500Hz

    .reset_n(reset),//

    .m_ser_code_in(m_ser_out),//PN序列输入

    .dpsk_code_out(dpsk_code_out),//dpsk调制输出

    .dds_sin_data_in2(data_line2),//10k正弦波

    .dds_sin_data_in3(data_line3),//10k正弦波,相位相差180

    .dpsk_code_sin_out(dpsk_code_sin_out)//

    );

    key u10(.clk(clk),.key(set_ask),.key_out(set_ask_line));

    key u11(.clk(clk),.key(set_fsk),.key_out(set_fsk_line));

    key u12(.clk(clk),.key(set_psk),.key_out(set_psk_line));

    key u13(.clk(clk),.key(set_dpsk),.key_out(set_dpsk_line));

    key_coding u14(

    .clk(clk),

    .reset_n(reset),

    .set_ask(set_ask_line),

    .set_fsk(set_fsk_line),

    .set_psk(set_psk_line),

    .set_dpsk(set_dpsk_line),

    .ask_code_sin_out(ask_code_sin_out),//

    .fsk_code_sin_out(fsk_code_sin_out),//

    .psk_code_sin_out(psk_code_sin_out),//

    .dpsk_code_sin_out(dpsk_code_sin_out),//

    .code_data_out(dac_data_in));//

    TLC5615 u15(

    .clk(clk),

    .sclk(sclk),

    .din(din),

    .cs(cs),

    .din_in(dac_data_in));

    endmodule

    • 按键编码模块:

    /********************************版权声明**************************************

    ** 大西瓜团队

    **

    **----------------------------文件信息--------------------------

    ** 文件名称: key_coding.v

    ** 创建日期:

    ** 功能描述:按键编码

    ** 硬件平台:大西瓜第3代开发板 http://daxiguafpga.taobao.com

    ** 版权声明:本代码属个人知识产权,本代码仅供交流学习.

    **---------------------------修改文件的相关信息----------------

    ** 修改人:

    ** 修改日期:        

    ** 修改内容:

    *******************************************************************************/

    module key_coding(

    clk,

    reset_n,

    set_ask,

    set_fsk,

    set_psk,

    set_dpsk,

    ask_code_sin_out,//

    fsk_code_sin_out,//

    psk_code_sin_out,//

    dpsk_code_sin_out,//

    code_data_out //

    );

    input clk;

    input reset_n;

    input set_ask;

    input set_fsk;

    input set_psk;

    input set_dpsk;

    input[9:0] ask_code_sin_out;//

    input[9:0] fsk_code_sin_out;//

    input[9:0] psk_code_sin_out;//

    input[9:0] dpsk_code_sin_out;//

    output[9:0] code_data_out;

    wire reset;

    wire set_ask;

    wire set_fsk;

    wire set_psk;

    wire set_dpsk;

    wire[9:0] ask_code_sin_out;//

    wire[9:0] fsk_code_sin_out;//

    wire[9:0] psk_code_sin_out;//

    wire[9:0] dpsk_code_sin_out;//

    reg[9:0] code_data_out;

    wire[3:0] set_mode_code;

    /******************调制模式选择****************************************/

    assign set_mode_code={set_ask,set_fsk,set_psk,set_dpsk};

    always@(posedge clk ornegedge reset_n)

    begin

    if(!reset_n)

    begin

    code_data_out<=10'd0;

    end

    else

    case(set_mode_code)

    4'b0111:code_data_out<=ask_code_sin_out;

    4'b1011:code_data_out<=fsk_code_sin_out;

    4'b1101:code_data_out<=psk_code_sin_out;

    4'b1110:code_data_out<=dpsk_code_sin_out;

    default:code_data_out<=ask_code_sin_out;

    endcase

    end

    endmodule

    • 按键消抖模块:

    /********************************版权声明**************************************

    ** 大西瓜团队

    **

    **----------------------------文件信息--------------------------

    ** 文件名称: key.v

    ** 创建日期:

    ** 功能描述:按键消抖

    ** 硬件平台:大西瓜第3代开发板 http://daxiguafpga.taobao.com

    ** 版权声明:本代码属个人知识产权,本代码仅供交流学习.

    **---------------------------修改文件的相关信息----------------

    ** 修改人:

    ** 修改日期:        

    ** 修改内容:

    *******************************************************************************/

    module key(

    clk,

    key,

    key_out);

    input clk;

    input key;//时钟输入,按键输入

    output key_out;//经消抖后的按键信号输出

    wire clk;

    wire key;

    reg key_out;

    parameter s0=2'b00,s1=2'b01,s2=2'b10,s3=2'b11;

    reg[1:0] state;

    always@(posedge clk)

    begin

    case(state)

    s0:

    begin

    key_out<=1'b1;

         if(key==1'b0)

             state<=s1;

         else

         state<=s0;

         end

         s1:

         begin

         if(key==1'b0)

             state<=s2;

         else

         state<=s0;

         end

         s2:

         begin

         if(key==1'b0)

             state<=s3;

         else

         state<=s0;

         end

         s3:

         begin

         if(key==1'b0)

         begin

             key_out<=1'b0;

             state<=s3;

             end

            else

             begin

             key_out<=1'b1;

             state<=s0;

         end

         end

         default:

         state<=s0;

    endcase

    end

    endmodule

    • DDS模块:

    /********************************版权声明**************************************

    ** 大西瓜团队

    **

    **----------------------------文件信息--------------------------

    ** 文件名称: DDS.v

    ** 创建日期:

    ** 功能描述:DDS信号发生与嵌入式逻辑分析仪的调用

    ** 硬件平台:大西瓜第3代开发板 http://daxiguafpga.taobao.com

    ** 版权声明:本代码属个人知识产权,本代码仅供交流学习.

    **---------------------------修改文件的相关信息----------------

    ** 修改人:

    ** 修改日期:        

    ** 修改内容:

    *******************************************************************************/

    module DDS(

    clk,

    reset_n,

    dds_data_out1,

    dds_data_out2,

    dds_data_out3

    );

    input clk;//时钟输入

    input reset_n;

    output[9:0] dds_data_out1;

    output[9:0] dds_data_out2;

    output[9:0] dds_data_out3;

    wire clk;

    wire reset_n;

    wire[9:0] dds_data_out1;

    wire[9:0] dds_data_out2;

    wire[9:0] dds_data_out3;

    //**************************************************//

    //******************产生载波1(500)**********************//

    //**************************************************//

    /**************连接线***************/

    wire[31:0] f32_bus1;//AC频率控制字输入

    wire[9:0] p_bus1;

    wire[31:0] reg32_out1;//32位寄存器输出

    wire[31:0] reg32_in1;//32位寄存器输入

    wire[9:0] reg10_in1;

    wire[9:0] reg10_out_address1;

    /************************************/

    parameter[11:0] f32_bus_init1=12'd0;

    parameter[9:0] p10_bus_init1=10'd0;//设置初始相位

    assign f32_bus1[31:20]=f32_bus_init1;//初始化,高位置低

    assign f32_bus1[19:0]=20'd42950;//低位可以设置DDS的输出频率

    assign p_bus1=p10_bus_init1;

    /*********************元件例化************************************/

    adder_32 u1(.data1(f32_bus1),.data2(reg32_out1),.sum(reg32_in1));

    reg32 u2(.clk(clk),.reset_n(reset_n),.data_in(reg32_in1),.data_out(reg32_out1));

    adder_10 u3(.data1(p_bus1),.data2(reg32_out1[31:22]),.sum(reg10_in1));

    reg_10 u4(.clk(clk),.reset_n(reset_n),.data_in(reg10_in1),.data_out(reg10_out_address1));

    sin_rom u5(.address(reg10_out_address1),.clock(clk),.q(dds_data_out1));//正弦

    //**************************************************//

    //******************产生载波2(1K)**********************//

    //**************************************************//

    /**************连接线***************/

    wire[31:0] f32_bus2;//AC频率控制字输入

    wire[9:0] p_bus2;

    wire[31:0] reg32_out2;//32位寄存器输出

    wire[31:0] reg32_in2;//32位寄存器输入

    wire[9:0] reg10_in2;

    wire[9:0] reg10_out_address2;

    /************************************/

    parameter[11:0] f32_bus_init2=12'd0;//

    parameter[9:0] p10_bus_init2=10'd0;//设置初始相位

    assign f32_bus2[31:20]=f32_bus_init2;//初始化,高位置低

    assign f32_bus2[19:0]=20'd85899;//低位可以设置DDS的输出频率

    assign p_bus2=p10_bus_init2;

    /*********************元件例化************************************/

    adder_32 u6(.data1(f32_bus2),.data2(reg32_out2),.sum(reg32_in2));

    reg32 u7(.clk(clk),.reset_n(reset_n),.data_in(reg32_in2),.data_out(reg32_out2));

    adder_10 u8(.data1(p_bus2),.data2(reg32_out2[31:22]),.sum(reg10_in2));

    reg_10 u9(.clk(clk),.reset_n(reset_n),.data_in(reg10_in2),.data_out(reg10_out_address2));

    sin_rom u10(.address(reg10_out_address2),.clock(clk),.q(dds_data_out2));//正弦

    //**************************************************//

    //******************产生载波3(1K,相位与2相反)**********************//

    //**************************************************//

    /**************连接线***************/

    wire[31:0] f32_bus3;//AC频率控制字输入

    wire[9:0] p_bus3;

    wire[31:0] reg32_out3;//32位寄存器输出

    wire[31:0] reg32_in3;//32位寄存器输入

    wire[9:0] reg10_in3;

    wire[9:0] reg10_out_address3;

    /************************************/

    parameter[11:0] f32_bus_init3=12'd0;//

    parameter[9:0] p10_bus_init3=10'd512;//设置初始相位

    assign f32_bus3[31:20]=f32_bus_init3;//初始化,高位置低

    assign f32_bus3[19:0]=20'd85899;//低位可以设置DDS的输出频率

    assign p_bus3=p10_bus_init3;

    /*********************元件例化************************************/

    adder_32 u11(.data1(f32_bus3),.data2(reg32_out3),.sum(reg32_in3));

    reg32 u12(.clk(clk),.reset_n(reset_n),.data_in(reg32_in3),.data_out(reg32_out3));

    adder_10 u13(.data1(p_bus3),.data2(reg32_out3[31:22]),.sum(reg10_in3));

    reg_10 u14(.clk(clk),.reset_n(reset_n),.data_in(reg10_in3),.data_out(reg10_out_address3));

    sin_rom u15(.address(reg10_out_address3),.clock(clk),.q(dds_data_out3));//正弦

    endmodule

    • m序列生成模块

    module m_ser(

    clk,//sys clk

    reset_n,//sys reset_n

    clk_div,

    m_ser_out //PN ser_code out

    );

    input clk;

    input reset_n;

    output clk_div;

    output m_ser_out;

    wire clk;

    wire reset_n;

    reg m_ser_out;

    reg[2:0] m_code;

    reg clk_div;

    reg[17:0]clk_cnt;

    always@(posedge clk ornegedge reset_n)

    begin

    if(!reset_n)

    begin

    clk_div<=1'b0;

    clk_cnt<=18'd0;

    end

    else

    if(clk_cnt==18'd49999)//500Hz PNcode

    begin

    clk_cnt<=18'd0;

    clk_div<=~clk_div;

    end

    else

    clk_cnt<=clk_cnt+1'b1;

    end

    always@(posedge clk_div ornegedge reset_n)

    begin

    if(!reset_n)

    begin

    m_code<=3'b001;//置数初始化

    m_ser_out<=1'b0;

    end

    else

    begin

    m_code[2:1]<=m_code[1:0];

    m_code[0]<=m_code[2]^ m_code[0];//20进行异或然后放到0

    m_ser_out<=m_code[2];//2进行输出

    end

    end

    endmodule

    ModelSim仿真过程

    安装ModelSim软件之后,打开该文件夹

    打开红色那个文件

    点击project出现了仿真的文件

    点击:start simulation

    选择work

    选择这个文件,然后点击OK

    按住ctrl,选择这几个信号,然后右击:ADD TO WAVEàSELECTED SIGNAL.

    点击红圈,放大窗口

    选择这几个信号

    右击,radixàunsigned

    然后再右击:formatàanalog:

    选择那四个信号,再右击properties,

    实验效果

    2ASK

    2FSK

    2PSK

    PN序列和DPSK序列

    2DPSK

    大西瓜FPGA-->https://daxiguafpga.taobao.com

    博客资料、代码、图片、文字等属大西瓜FPGA所有,切勿用于商业! 若引用资料、代码、图片、文字等等请注明出处,谢谢!

    每日推送不同科技解读,原创深耕解读当下科技,敬请关注微信公众号“科乎”。

  • 相关阅读:
    php扩展开发函数
    python里面的引用
    apk的包名修改
    python3.3中print换行
    Project Euler Problem4
    Project Euler Problem5
    Project Euler Problem3
    通过电脑来访问手机站点——UserAgent和UserDataDir的应用
    LJX的校园:社会实践的任务
    连续和最大
  • 原文地址:https://www.cnblogs.com/logic3/p/5303600.html
Copyright © 2011-2022 走看看