浮点数的复数乘法

参考:Vivado IP核之复数浮点数乘法 Floating-point_vivado ip核 复数求模-CSDN博客

floating point IP核I只有multiple ,没有 complex multiple  

然后 complex multiple 的IP核下面只有定点的,不支持浮点,所以需要写一个浮点数的复数乘法模块。

`timescale 1ns / 1ps

//    计算公式   (a+bi)(c+di)=ac-bd+(ad+bc)i
// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) + i*(a_re*b_im) + i*(a_im*b_re) - (a_im*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)

module float_complex_mul
(
    input clk,               // 输入时钟信号  

    // 我做流水线其实不需要rst_n来复位,
    // 但是我需要一个输入的全局valid来给四个乘法器确认输入数据
    // 这个值的输入到时候可以设置为fixed2float的
    input s_float_complex_valid,
    // input rst_n,             //输入复位信号
    // input start,             //输入开始信号
    input [31:0] a_im,       //输入因数a的虚部
    input [31:0] a_re,       //输入因数a的实部
    input [31:0] b_im,       //输入因数b的虚部
    input [31:0] b_re,       //输入因数b的实部

    // output reg over,           //输出计算完成信号
    output  [31:0] im_res,   //输出计算结果的虚部
    output  [31:0] re_res,  //输出计算结果的实部

    output      m_axis_result_tvalid
);
    // //reg define
    // reg [4:0] cnt;               //过程计数标志
    // reg valid1;                  //乘有效信号 
    // reg valid2;                  //加减有效信号 
    
    // result_valid信号
    wire mul_ip_result_valid_1;
    wire mul_ip_result_valid_2;
    wire mul_ip_result_valid_3;
    wire mul_ip_result_valid_4;


    //wire define
    wire [31:0] result1;      //结果1
    wire [31:0] result2;      //结果2
    wire [31:0] result3;      //结果3
    wire [31:0] result4;      //结果4
    wire [31:0] result5;      //结果5
    wire [31:0] result6;      //结果6

    
    // always @(posedge clk or negedge rst_n)
    //     if(!rst_n)
    //         cnt<=0;
    //     else if(start==1)
    //         begin
    //             if(cnt<5'd27)    
    //                 cnt<=cnt+1;
    //             else
    //                 cnt<=0;
    //         end
    //     else if(start==0)
    //         cnt<=0;
    // always @(posedge clk or negedge rst_n) 
    //     if(!rst_n)  
    //         valid1<=0;
    //     else if(5'd0<cnt<=5'd9)
    //         valid1<=1;
    //     else
    //         valid1<=0;
    
    // always @(posedge clk or negedge rst_n)
    //     if(!rst_n)  
    //            valid2<=0;
    //        else if(5'd12<cnt<=5'd24)
    //            valid2<=1;
    //        else
    //            valid2<=0; 
    // always @(posedge clk or negedge rst_n)
    //      if(!rst_n)  
    //         begin over<=0;re_res<=0;im_res<=0; end
    //      else if(cnt==5'd26)
    //         begin  over<=1;re_res<=result5;im_res<=result6;  end
    //      else
    //         begin over<=0;re_res<=0;im_res<=0; end
        

// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)
// 第一个乘法器,计算(a_re*b_re)
float_mul_ip u1_float_mul_ip
(                    
    .aclk(clk),
    .s_axis_a_tvalid(s_float_complex_valid),
    .s_axis_a_tdata(a_re),
    .s_axis_b_tvalid(s_float_complex_valid),
    .s_axis_b_tdata(b_re),
    .m_axis_result_tvalid(mul_ip_result_valid_1),
    .m_axis_result_tdata(result1)
);

// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)
// 第二个乘法器,计算(a_im*b_im)
float_mul_ip u2_float_mul_ip
(                     
    .aclk(clk),
    .s_axis_a_tvalid(s_float_complex_valid),
    .s_axis_a_tdata(a_im),
    .s_axis_b_tvalid(s_float_complex_valid),
    .s_axis_b_tdata(b_im),
    .m_axis_result_tvalid(mul_ip_result_valid_2),
    .m_axis_result_tdata(result2)
);

// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)
// 第三个乘法器,计算(a_re*b_im)
float_mul_ip u3_float_mul_ip
(                       
    .aclk(clk),
    .s_axis_a_tvalid(s_float_complex_valid),
    .s_axis_a_tdata(a_re),
    .s_axis_b_tvalid(s_float_complex_valid),
    .s_axis_b_tdata(b_im),
    .m_axis_result_tvalid(mul_ip_result_valid_3),
    .m_axis_result_tdata(result3)
);  
// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)
// 第四个乘法器,计算(a_im*b_re)
float_mul_ip u4_float_mul_ip
(                       
    .aclk(clk),
    .s_axis_a_tvalid(s_float_complex_valid),
    .s_axis_a_tdata(a_im),
    .s_axis_b_tvalid(s_float_complex_valid),
    .s_axis_b_tdata(b_re),
    .m_axis_result_tvalid(mul_ip_result_valid_4),
    .m_axis_result_tdata(result4)
);   

wire s_axi_sub_valid;
assign s_axi_sub_valid = mul_ip_result_valid_4 ;
reg s_axi_add_valid;


// 加减法的valid信号可以从乘法器的valid来
// 每个加法的值,来自两个乘法器,我可以拉出四个result_valid信号

// 计算公式(a_re + i*a_im)(b_re + i*b_im)
// =(a_re*b_re) - (a_im*b_im) + i*(a_re*b_im) + i*(a_im*b_re)
// 计算实部,(a_re*b_re) - (a_im*b_im)
float_sub_ip u1_float_sub_ip
(                    //减法器   计算ac-bd
    .aclk(clk),
    .s_axis_a_tvalid(s_axi_sub_valid),
    .s_axis_a_tdata(result1),
    .s_axis_b_tvalid(s_axi_sub_valid),
    .s_axis_b_tdata(result2),
    .m_axis_result_tvalid(m_axis_result_tvalid),
    .m_axis_result_tdata(result5)
);     
float_add_ip u1_float_add_ip
(                  //加法器   计算ad+bc
    .aclk(clk),
    .s_axis_a_tvalid(s_axi_sub_valid),
    .s_axis_a_tdata(result3),
    .s_axis_b_tvalid(s_axi_sub_valid),
    .s_axis_b_tdata(result4),
    .m_axis_result_tvalid(),
    .m_axis_result_tdata(result6)
);

assign re_res = result5;
assign im_res = result6;
// always @(posedge clk) begin
//     if (m_axis_result_tvalid) begin
//         re_res <= result5;
//         im_res <= result6;
//     end
// end      



endmodule

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值