FFT算法实现之fft IP核

发布于:2025-07-25 ⋅ 阅读:(13) ⋅ 点赞:(0)

端口详解

在这里插入图片描述

输入端

data端口组:

  • tdata: 设置16位数据这里会是32位,因为考虑虚部
  • tlast:当输入序列最后一位进入时, 要求tlast拉高,这对于连续的信号处理有必要, 如果只处理一次可以不管
  • tready:代表IP核允许接收第二次数据
  • tvalid: 数据数据有效信号, 代表当前数据有效

config端口组:

  • tdata:1–》正变换;0–》反变换;
  • tready、tvalid 只有在勾选“Run time Configurable Transform Length”时需要设置, 因为此时配置信息(tdata)允许在工作周期中更改

输出端

status端口组:

  • m_axis_status_tready 非必选,外部系统准备好接收状态信号的时候输入高电平。仅用于非实时状态。
  • m_axis_status_tvalid 状态信息有效信号
  • m_axis_status_tdata 携带BLK_EXP以及OVFLO信息,两个信息不能同时通过该输出口显示。当缩放模式选择scaled时m_axis_status_tdata代表OVFLO,代表数据是否溢出。
    当缩放模式选择块浮点时,携带BLK_EXP信息。BLK_EXP代表缩放位数,会自动选择在不溢出的情况下缩放的最大值。比如BLK_EXP的值为00101(二的五次方),意思就是输出的结果为实际结果的32分之一。

data端口组:

  • m_axis_data_tdata 输出数据的实部虚部。
  • m_axis_data_tlast 输出数据的最后一位到来拉高。
  • m_axis_data_tready 非必选,外部系统准备好接收数据信号的时候输入高电平。仅用于非实时状态。
    ----未完待续—

https://www.bilibili.com/video/BV18h4y1k7PZ/?spm_id_from=333.1387.homepage.video_card.click&vd_source=f12f53fed02a66a1da6584b2c947cacf

matlab实验

clc;
clear all;
close all;
%fs=10e6;
fs=50e6  %对应vivado系统时钟50MHZ?
N = 2048;
f1=4e6;
f2=3e6;

n=0:N-1;
t=n/fs;
f=fs*n/N;


s1=sin(2*pi*f1*t);
s2=sin(2*pi*f2*t);
mixsls2=s1.*s2;
mixsls2=mixsls2+0i;
subplot (2,1,1)
plot (mixsls2)
fftsls2=fft (mixsls2);
fftabs=abs (fftsls2);% 
subplot(2,1,2)
plot (fftabs)
%xlim([0, 10e6]);

在这里插入图片描述

vivado实验结果

代码

`timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Company: 
// Engineer: 
// 
// Create Date: 2025/07/22 10:33:56
// Design Name: 
// Module Name: test
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//////////////////////////////////////////////////////////////////////////////////


module test(
    input                               clk                        ,
//    input                               rst                        ,
    
    
    output               [  31: 0]      fft_out                     
    );
//---------------------------------------------------------------------------------------
// 内部端口定义                                                                                    
//---------------------------------------------------------------------------------------      
    wire               [   7: 0]        sin1                        ;
    wire               [   7: 0]        sin2                        ;
    wire    signed     [  15: 0]        sin_mux                     ;


//---------------------------------------------------------------------------------------
// fft端口定义                                                                                    
  
    wire                                s_axis_config_tready,     s_axis_data_tready,m_axis_data_tvalid,m_axis_data_tlast;
    wire               [   7: 0]        m_axis_status_tdata         ;
    wire    signed     [  31: 0]        m_axis_data_tdata           ;// fft输出
    wire                                m_axis_status_tvalid        ;
    wire                                m_axis_status_tready        ;
    wire                                sin_m_axis_data_tvalid      ;
    wire               [  23: 0]        m_axis_data_tuser           ;
    wire                                event_frame_started         ;
    wire                                event_tlast_unexpected      ;
    wire                                event_tlast_missing         ;
    wire                                event_status_channel_halt   ;
    wire                                event_data_in_channel_halt  ;
    wire                                event_data_out_channel_halt  ;
    wire               [  31: 0]        fft_input                   ;
    assign                              fft_input                   = {16'b0,sin_mux};
    assign                              sin1_m_axis_data_tvalid     = 1'b1;// 直接赋值为1,表示数据有效;
    assign                              m_axis_status_tready        = 1'b1;
    assign                              sin_m_axis_data_tvalid      = 1'b1;
//---------------------------------------------------------------------------------------    
    wire    signed     [  15: 0]        a,b                         ;// fft输出的实部和虚部分量  
    wire    signed     [  31: 0]        Pa,                       Pb;//分量平方
    wire               [  10: 0]        index                       ;

    assign                              {a, b}                      = m_axis_data_tdata;
    assign                              fft_out                     = Pa+Pb;
    assign                              index                       = m_axis_data_tuser[10:0];// fft输出的index
//---------------------------------------------------------------------------------------
// IP核调用                                                                                 
//---------------------------------------------------------------------------------------
xfft_0 fft1 (
    .aclk                               (clk                       ),// input wire aclk
    .s_axis_config_tdata                (8'b1                      ),// input wire [7 : 0] s_axis_config_tdata
    .s_axis_config_tvalid               (1                         ),// input wire s_axis_config_tvalid
    .s_axis_config_tready               (s_axis_config_tready      ),// output wire s_axis_config_tready
    .s_axis_data_tdata                  (fft_input                 ),// input wire [31 : 0] s_axis_data_tdata
    .s_axis_data_tvalid                 (sin_m_axis_data_tvalid    ),// input wire s_axis_data_tvalid
    .s_axis_data_tready                 (s_axis_data_tready        ),// output wire s_axis_data_tready
    .s_axis_data_tlast                  (1                         ),// input wire s_axis_data_tlast
    .m_axis_data_tdata                  (m_axis_data_tdata         ),// output wire [31 : 0] m_axis_data_tdata
    .m_axis_data_tuser                  (m_axis_data_tuser         ),// output wire [23 : 0] m_axis_data_tuser
    .m_axis_data_tvalid                 (m_axis_data_tvalid        ),// output wire m_axis_data_tvalid
    .m_axis_data_tready                 (1                         ),// input wire m_axis_data_tready
    .m_axis_data_tlast                  (m_axis_data_tlast         ),// output wire m_axis_data_tlast
    .m_axis_status_tdata                (m_axis_status_tdata       ),// output wire [7 : 0] m_axis_status_tdata
    .m_axis_status_tvalid               (m_axis_status_tvalid      ),// output wire m_axis_status_tvalid
    .m_axis_status_tready               (m_axis_status_tready      ),// input  wire m_axis_status_tready
    .event_frame_started                (event_frame_started       ),// output wire event_frame_started
    .event_tlast_unexpected             (event_tlast_unexpected    ),// output wire event_tlast_unexpected
    .event_tlast_missing                (event_tlast_missing       ),// output wire event_tlast_missing
    .event_status_channel_halt          (event_status_channel_halt ),// output wire event_status_channel_halt
    .event_data_in_channel_halt         (event_data_in_channel_halt),// output wire event_data_in_channel_halt
    .event_data_out_channel_halt        (event_data_out_channel_halt) // output wire event_data_out_channel_halt
);

//---------------------------------------------------------------------------------------
// 计算平方
mult_gen_1 PA (
  .CLK(clk),  // input wire CLK
  .A(a),      // input wire [15 : 0] A
  .B(a),      // input wire [15 : 0] B
  .P(Pa)      // output wire [31 : 0] P
);
mult_gen_1 PB (
  .CLK(clk),  // input wire CLK
  .A(b),      // input wire [15 : 0] A
  .B(b),      // input wire [15 : 0] B
  .P(Pb)      // output wire [31 : 0] P
);
//---------------------------------------------------------------------------------------

DDS u_DDS(
    .clk                                (clk                       ),
    .sin1                               (sin1                      ),
    .sin2                               (sin2                      ),
    .sin_mux                            (sin_mux                   ) 
);

endmodule
`timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Company: 
// Engineer: 
// 
// Create Date: 2025/07/22 10:33:56
// Design Name: 
// Module Name: test
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//////////////////////////////////////////////////////////////////////////////////


module DDS(
    input                               clk                        ,

    output               [   7: 0]      sin1                       ,
    output               [   7: 0]      sin2                       ,
    output       signed  [  15: 0]      sin_mux                    
 
    );
      
    wire sin_m_axis_data_tvalid;

//---------------------------------------------------------------------------------------
// IP核调用                                                                                 
//---------------------------------------------------------------------------------------

mult_gen_0 mult1 (
    .CLK                                (clk                       ),// input wire CLK
    .A                                  (sin1                      ),// input wire [7 : 0] A
    .B                                  (sin2                      ),// input wire [7 : 0] B
    .P                                  (sin_mux                   ) // output wire [15 : 0] P
);


dds_compiler_0 dds1 (
    .aclk                               (clk                       ),// input wire aclk
    .m_axis_data_tvalid                 (sin_m_axis_data_tvalid   ),// output wire m_axis_data_tvalid
    .m_axis_data_tdata                  (sin1                      ) // output wire [7 : 0] m_axis_data_tdata
);
dds_compiler_1 dds2 (
    .aclk                               (clk                       ),// input wire aclk
    .m_axis_data_tvalid                 (sin_m_axis_data_tvalid   ),// output wire m_axis_data_tvalid
    .m_axis_data_tdata                  (sin2                      ) // output wire [7 : 0] m_axis_data_tdata
);

endmodule

ip核配置

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

仿真结果

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
与matlab一致

难点

  1. IP核端口参数以及接线设置,matlab参数与vivado参数对应(fs >>>时钟频率?,N>>>IP核N设置 )
  2. vivado数据位宽设置, 我是跟着教程(B站老乔FPGA)写的代码, 自己写能知道吗。。

网站公告

今日签到

点亮在社区的每一天
去签到