基于 FPGAFIR 滤波器 IP 仿真实例
 
AT7_Xilinx 开发板(USB3.0+LVDS)资料共享
 
腾讯链接:https://share.weiyun.com/5GQyKKc
 
百度网盘链接:https://pan.baidu.com/s/1M7PLzRs-yMJv7NFJE8GVAw 
 
提取码:qr0t
 
 
1 FIR 滤波器简介
FIR(Finite Impulse Response)滤波器,即有限脉冲响应滤波器,又称为非递归型滤波器,是数字信号处理系统中最基本的元件,它可以在保证任意幅频特性的同?#26412;?#26377;严格的线性相频特性,同时其单位抽样响应是有限长的,因而滤波器是稳定的系统。因此,FIR 滤波器在通信、图像处理、模式识别等领域都有着广泛的应用。
 
Vivado 集成的 FIR IP 核可以实现如下公式所示的 N 级卷积运算。
 
 
FIR IP 核可以根据配置实现复用的乘累加单元,以实现面积最优化的设计;当然了,在速度性能要求极高的应用中,也可以配置并行的乘累加单元,以达到最大的 FIR 数据吞吐量。
 
 
2 FIR IP 核配置
FIRIP 配置主页面如图所示。此页面可以配置基本的滤波参数。 
 
 
通道配置页面如下。 
 
 
输入输出的数据位宽可在 Implementation 页面配置。 
 

 

 
实现的资源利用情况,如优化选项、存储器选项和 DSP Slice 选项等,可以在 Detailed Implementation 页面配置。 
 
 
额外的控制接口,可以在 Interface 页面配置。 
 
 
左侧的 Freq.Response 页面可以参考所使用的 FIR 滤波参数最终实现的滤波特性(低通、高通、低阻、高阻或带通、带阻等),这里我们使用的是一组 IP 默?#31995;?#21442;数,低通滤波器。
 
 
而左侧的 Implementation Details 页面,则可以自由利用以及接口等信息。如图所示的 ufix16_0 表示输入数据为 16 位的无符号整数,而 fix25_0 则表示输出结果是 25 位的有符号整数。
 
 
详细配置可参看 pg149-fir-compiler.pdf(at7_img_ex07/matlab 文件夹下)。

 

 
3 FIR IP 核接口时序
我们例化的 FIR IP 核,有如下的接口,其功能和端口方向定义如下。
 
inputaclk;         // 时?#26377;?#21495;
 
input [15 : 0] s_axis_data_tdata;  //unsigned(16.0),输入数据
 
inputs_axis_data_tvalid;                 // 输入数据有效信号,高电平有效
 
outputs_axis_data_tready;            // 准备好接收输入数据,高电平有效
 
output [24 : 0] m_axis_data_tdata;      //signed(25.0),FIR 滤波结果输出
 
outputm_axis_data_tvalid;                     //FIR 滤波结果输出有效,高电平有效
 
 接口时序控制如图所示。图中很多信号本实例不涉及,可以忽略。s_axis_data_tvalid 和 s_axis_data_tready 信号同时拉高?#20445;瑂_axis_data_tdata 被 FIR IP 核接收,进行处理。当 m_axis_data_tvalid 拉高?#20445;?#34920;示输出 FIR 滤波结果 m_axis_data_tdata 有效。 
 
 
4 FIR IP 仿真
使用 at7_img_ex07/matlab 文件夹下的 test_data_generate_for_fir.m 脚本,可以产生一组 1000 个点的余弦数据,存放在 time_domain_cos.txt 文件中,这组数据将作为 FPGA 的仿真输入激励,经过 FIR 滤波器进行滤波处理。
 
clc;clear `all;close all;
 
 
 
format long g
 
 
 
Fs = 1000;                    % Sampling frequency
 
T = 1/Fs;                     % Sampling period
 
L = 1000;                     % Length of signal
 
t = (0-1)*T;                % Time vector
 
 
 
x1 = cos(2*pi*50*t)*(2^13);          % First row wave
 
 
 
%output time domain data
 
x1_fix = round(x1,0);    %convert to fixed signed(3.13)
 
x1_fix(find(x1_fix<0)) = x1_fix(find(x1_fix<0))+(2^16); 
 
fid0 = fopen('time_domain_cos.txt', 'wt');
 
fprintf(fid0, '%16x\n', x1_fix);
 
fid0 = fclose(fid0);
 
         FPGA 工程 at7_img_ex07 的顶层是一个测试脚本,at7_fir_sim.v 文件。该测试脚本将 time_domain_cos.txt 文件的 1000 个数据读入,然后依次送入 FIR 滤波器 IP 核进行处理,输出结果写入 fir_result.txt 文本中。
 
`timescale 1ns/1ps
 
module zstar_fir_sim(
 
    );
 
         
 
reg clk;    
 
 
 
reg [15 : 0] s_axis_data_tdata;      //unsigned(16.0)
 
reg s_axis_data_tvalid;
 
wire s_axis_data_tready;
 
 
 
wire [31 : 25] null;
 
wire [24 : 0] m_axis_data_tdata;  //signed(25.0)
 
wire m_axis_data_tvalid;
 
 
 
parameter DATA_NUM = 1000;
 
         
 
////////////////////////////////////////////////////
 
//FIR IP Core   
 
 
 
fir_compiler_0  uut_fir_compiler_0 (
 
.aclk(clk),                              // input wire aclk
 
.s_axis_data_tvalid(s_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_tdata(s_axis_data_tdata),    // input wire [15 : 0] s_axis_data_tdata
 
  .m_axis_data_tvalid(m_axis_data_tvalid),  // output wire m_axis_data_tvalid
 
  .m_axis_data_tdata({null,m_axis_data_tdata})    // output wire [31 : 0] m_axis_data_tdata
 
);
 
         
 
////////////////////////////////////////////////////     
 
integer i;
 
 
 
reg[15:0] data_mem [DATA_NUM-1:0];
 
 
 
initial #500 $readmemh("../../time_domain_cos.txt",  data_mem);                 
 
 
 
 
 
initial begin
 
         clk = 0;
 
         
 
         s_axis_data_tdata<= 16'd0;
 
         s_axis_data_tvalid<= 1'b0;
 
         
 
         
 
         #1000;
 
         @(posedgeclk);
 
 
 
         i<= 1;
 
         #10000;
 
 
 
         @(posedgeclk);                
 
         
 
         #100_000;
 
         
 
         $fclose(w1_file);
 
         #1000;
 
         $stop;
 
end  
 
 
 
always @(*) begin
 
         if((i>0) && (i<DATA_NUM+1)) s_axis_data_tdata<= data_mem[i-1];
 
         else s_axis_data_tdata<= 16'd0;
 
end  
 
 
 
always @(posedgeclk) begin
 
         if(i == 0) i<= 0;
 
         else if(i<= DATA_NUM) begin         
 
                  if(s_axis_data_tready&&s_axis_data_tvalid) i<= i+1;
 
                  else ;
 
         end
 
         else if(i< DATA_NUM+26) i<= i+1;
 
         else ;
 
end
 
 
 
always @(posedgeclk) begin
 
         if((i>=1) && (i<=DATA_NUM-1)) s_axis_data_tvalid<= 1'b1;        
 
         else s_axis_data_tvalid<= 1'b0;
 
end
 
 
 
 
 
always #10 clk = ~clk;              
 
 
 
 
 
integer w1_file;
 
 
 
initial w1_file = $fopen("./fir_result.txt","w");     
 
                  
 
always @(posedgeclk) begin
 
         if(m_axis_data_tvalid) begin
 
                  $fwrite(w1_file, "%x\n", m_axis_data_tdata);     
 
         end  
 
end  
 
         
endmodule

 

 
如图所示,Vivado 中打开 at7_img_ex07 工程,在 Project Manager à Simulation Sources à sim_1 下,看到 top module 为高亮的 at7_fir_sim.v 模块,点击 Flow Navigator à Simulation à Run Simulation 可以启动仿真。
 
运行仿真如图。
 
 
 
仿真的结果将写入生成的 fir_result.txt 文本(位于 at7_img_ex07\at7.sim 文件夹的子文件夹中),将该文本放置到 matlab 文件夹中,运行 matlab 脚本 draw_wave_from_txt.m,可以查看正弦数据 FIR 滤波前后的波形比对。在时域看来,峰或谷的位置是高频,因此都被 FIR 滤波处理了。 
 
 
AT7_Xilinx 开发板(USB3.0+LVDS)资料共享
 
腾讯链接:https://share.weiyun.com/5GQyKKc
 
百度网盘链接:https://pan.baidu.com/s/1M7PLzRs-yMJv7NFJE8GVAw 
 
提取码:qr0t