前言

本文介绍了设计滤波器的FPGA实现步骤,并结合杜勇老师的书籍中的串行FIR滤波器部分进行一步步实现硬件设计,对书中的架构做了简单的优化,并进行了仿真验证。

FIR滤波器的FPGA实现步骤

从工程角度分析FIR滤波器的FPGA实现步骤如下:

  1. 分析设计需求,根据设计需求确定FIR滤波器的仿真算法设计。

  2. 编写仿真代码或利用工具生成相关设计文件(包括但不局限与c++、MATLAB、python等语言或者相关滤波器设计工具)

  3. 量化滤波器系数,防止运算时数据溢出造成错误。

  4. 根据实际工程需求确定硬件实现架构并编写代码。

量化滤波器系数的影响

量化位数对滤波器的阻带纹波有较大的影响,且量化位数越高,则影响越小。下面给出两个之前设计的FIR IP工程中量化效果的截图,从图中可以很清楚看出,当量化位数不够,也就是量化精度不够时,对阻带影响较大,使用量化效果不好的滤波器可能造成滤波效果不能达到预期效果。

量化精度不够

正常量化

串行FIR滤波器FPGA实现

FIR滤波器的结构形式时,介绍了直接型、级联型、频率取样型和快速卷积型4种。在FPGA实现时,最常用的是最简单的直接型结构。FPGA实现直接型结构的FIR滤波器,可以采用串行结构、并行结构等不同中的结构设计,本节主要介绍在vivado环境下进行串行FIR滤波器设计的结构实现,同样仿造杜勇老师的《数字滤波器的MATLAB与FPGA实现》的书中的设计需求去一步步搭建工程并实现。

实现串行FIR滤波器滤波器需求

设计一个15阶(长度为16)的低通线性相位FIR滤波器,采用窗函数设计,截止频率为500 Hz,采样频率为2 000 Hz;采用FPGA实现全串行结构的滤波器,系数的量化位数为12比特,输入数据位宽为12比特,输出数据位宽为29比特,系统时钟为16 kHz。

滤波器系数确定与量化

确定滤波器的结构后,就根据滤波器进行设计代码仿真,这里引用书中的仿真设计,并将滤波器参数系数量化。确定滤波器系数的方法有很多,可以使用MATLAB中丰富的函数实现,或者使用相关滤波器设计的软件工具,定制满足当前需求的窗函数的滤波器系数。

N=16;      %滤波器长度
fs=2000;   %采样频率
fc=500;    %低通滤波器的截止频率
B=12;      %量化位数
%生成各种窗函数
w_kais=blackman(N)';
%采用fir1函数设计FIR滤波器
b_kais=fir1(N-1,fc*2/fs,w_kais);
%量化滤波器系数
Q_kais=round(b_kais/max(abs(b_kais))*(2^(B-1)-1))
hn=Q_kais;
%转化成16进制数补码
Q_h=dec2hex(Q_kais+2^B*(Q_kais<0))
%求滤波器的幅频响应
m_kais=20*log(abs(fft(b_kais,1024)))/log(10); m_kais=m_kais-max(m_kais);
Q_kais=20*log(abs(fft(Q_kais,1024)))/log(10); Q_kais=Q_kais-max(Q_kais);
%设置幅频响应的横坐标单位为Hz
x_f=[0:(fs/length(m_kais)):fs/2];
%只显示正频率部分的幅频响应
m5=m_kais(1:length(x_f));
m6=Q_kais(1:length(x_f));
%绘制幅频响应曲线
plot(x_f,m5,'-',x_f,m6,'--');
xlabel('频率(Hz)');ylabel('幅度(dB)');
legend('未量化','12bit量化');
grid;

硬件架构

下图为杜勇老师的《数字滤波器的MATLAB与FPGA实现》实现的串行FIR滤波器的结构图。因为FIR滤波器参数对称,所以同时计算相应的对称结构的值,所以针对长度为16的滤波器只需要计算8次即可出结果,图中的8个时钟周期可以替换成N/2;这样就得到了一个通用化的串行FIR滤波器结构图。

串行FIR滤波器结构

串行实现FIR滤波器,可以节约加法器资源,同时牺牲了整个滤波器实现的性能,缺点也就很明显了,当滤波器的系数长度N增大时,该数据吞吐的速率也将对应变成1/N。

根据架构描述电路

杜勇老师书中提供的代码相当繁琐,而且不具有通用化的使用价值(串行FIR使用价值确实不大,可能只用于学习),我根据上述的硬件设计的架构对代码进行了重写配置,使得代码更具有通用意义,可根据参数输入来适配不同滤波器长度的设计。

前言

本文介绍了设计滤波器的FPGA实现步骤,并结合杜勇老师的书籍中的串行FIR滤波器部分进行一步步实现硬件设计,对书中的架构做了简单的优化,并进行了仿真验证。

FIR滤波器的FPGA实现步骤

从工程角度分析FIR滤波器的FPGA实现步骤如下:

  1. 分析设计需求,根据设计需求确定FIR滤波器的仿真算法设计。

  2. 编写仿真代码或利用工具生成相关设计文件(包括但不局限与c++、MATLAB、python等语言或者相关滤波器设计工具)

  3. 量化滤波器系数,防止运算时数据溢出造成错误。

  4. 根据实际工程需求确定硬件实现架构并编写代码。

量化滤波器系数的影响

量化位数对滤波器的阻带纹波有较大的影响,且量化位数越高,则影响越小。下面给出两个之前设计的FIR IP工程中量化效果的截图,从图中可以很清楚看出,当量化位数不够,也就是量化精度不够时,对阻带影响较大,使用量化效果不好的滤波器可能造成滤波效果不能达到预期效果。

量化精度不够

正常量化

串行FIR滤波器FPGA实现

FIR滤波器的结构形式时,介绍了直接型、级联型、频率取样型和快速卷积型4种。在FPGA实现时,最常用的是最简单的直接型结构。FPGA实现直接型结构的FIR滤波器,可以采用串行结构、并行结构等不同中的结构设计,本节主要介绍在vivado环境下进行串行FIR滤波器设计的结构实现,同样仿造杜勇老师的《数字滤波器的MATLAB与FPGA实现》的书中的设计需求去一步步搭建工程并实现。

实现串行FIR滤波器滤波器需求

设计一个15阶(长度为16)的低通线性相位FIR滤波器,采用窗函数设计,截止频率为500 Hz,采样频率为2 000 Hz;采用FPGA实现全串行结构的滤波器,系数的量化位数为12比特,输入数据位宽为12比特,输出数据位宽为29比特,系统时钟为16 kHz。

滤波器系数确定与量化

确定滤波器的结构后,就根据滤波器进行设计代码仿真,这里引用书中的仿真设计,并将滤波器参数系数量化。确定滤波器系数的方法有很多,可以使用MATLAB中丰富的函数实现,或者使用相关滤波器设计的软件工具,定制满足当前需求的窗函数的滤波器系数。

N=16;      %滤波器长度
fs=2000;   %采样频率
fc=500;    %低通滤波器的截止频率
B=12;      %量化位数
%生成各种窗函数
w_kais=blackman(N)';
%采用fir1函数设计FIR滤波器
b_kais=fir1(N-1,fc*2/fs,w_kais);
%量化滤波器系数
Q_kais=round(b_kais/max(abs(b_kais))*(2^(B-1)-1))
hn=Q_kais;
%转化成16进制数补码
Q_h=dec2hex(Q_kais+2^B*(Q_kais<0))
%求滤波器的幅频响应
m_kais=20*log(abs(fft(b_kais,1024)))/log(10); m_kais=m_kais-max(m_kais);
Q_kais=20*log(abs(fft(Q_kais,1024)))/log(10); Q_kais=Q_kais-max(Q_kais);
%设置幅频响应的横坐标单位为Hz
x_f=[0:(fs/length(m_kais)):fs/2];
%只显示正频率部分的幅频响应
m5=m_kais(1:length(x_f));
m6=Q_kais(1:length(x_f));
%绘制幅频响应曲线
plot(x_f,m5,'-',x_f,m6,'--');
xlabel('频率(Hz)');ylabel('幅度(dB)');
legend('未量化','12bit量化');
grid;

硬件架构

下图为杜勇老师的《数字滤波器的MATLAB与FPGA实现》实现的串行FIR滤波器的结构图。因为FIR滤波器参数对称,所以同时计算相应的对称结构的值,所以针对长度为16的滤波器只需要计算8次即可出结果,图中的8个时钟周期可以替换成N/2;这样就得到了一个通用化的串行FIR滤波器结构图。

串行FIR滤波器结构

串行实现FIR滤波器,可以节约加法器资源,同时牺牲了整个滤波器实现的性能,缺点也就很明显了,当滤波器的系数长度N增大时,该数据吞吐的速率也将对应变成1/N。

根据架构描述电路

杜勇老师书中提供的代码相当繁琐,而且不具有通用化的使用价值(串行FIR使用价值确实不大,可能只用于学习),我根据上述的硬件设计的架构对代码进行了重写配置,使得代码更具有通用意义,可根据参数输入来适配不同滤波器长度的设计。

实现模块框图

接口描述如下:

接口描述

参数描述如下:

参数描述

代码如下:

`timescale 1ns / 1ps
module Fir_FullSerial(input clk,//!系统时钟input rst,//!复位信号input signed [SIGN_IN_WIDTH-1:0] signal_in,//!信号输入output signed [SIGN_OUT_WIDTH-1:0] signal_out//!信号输出,信号输出速度为CLK/FIR_COE_NUM);//parameter  integer SIGN_IN_WIDTH    = 12   ;//!信号输入位宽parameter  integer SIGN_OUT_WIDTH = 29   ;//!信号输出位宽parameter  integer FIR_COE_WIDTH = 12   ;//!滤波器系数位宽parameter  integer FIR_COE_NUM = 16   ;//!滤波器长度localparam integer FIR_WIDTH_DIV_2 = FIR_COE_NUM/2 ;function [FIR_COE_WIDTH-1:0] coe_data;input [FIR_WIDTH_DIV_2-1:0] index;begincase(index)'d0:coe_data='h000;'d1:coe_data='hffd;'d2:coe_data='h00f;'d3:coe_data='h02e;'d4:coe_data='hf8b;'d5:coe_data='hef9;'d6:coe_data='h24e;'d7:coe_data='h7ff;endcaseendendfunction//!寄存输入信号reg [SIGN_IN_WIDTH-1:0] Sign_in_Reg[FIR_COE_NUM-1:0];//!计数器逻辑reg [FIR_WIDTH_DIV_2-1:0] cnt;always @(posedge clk ) beginif (rst=='b1) begincnt<='d0;endelse beginif (cnt==FIR_WIDTH_DIV_2-'b1) begincnt <= 0;endelse begincnt <= cnt + 1;endendend//将数据存入移位寄存器sign_in_Reg中integer i;always @(posedge clk)beginif (rst=='b1)begin//初始化寄存器值为0for (i=0; i<FIR_COE_NUM; i=i+1)Sign_in_Reg[i]=12'd0;endelse beginif (cnt==FIR_WIDTH_DIV_2-'b1)beginfor (i=0; i<FIR_COE_NUM-1; i=i+1)Sign_in_Reg[i+1] <= Sign_in_Reg[i];Sign_in_Reg[0] <= signal_in;endendendreg signed [SIGN_IN_WIDTH:0] add_a=0;reg signed [SIGN_IN_WIDTH:0] add_b;reg  signed [FIR_COE_WIDTH-1:0] coe; //为了保证加法运算不溢出,输入输出数据均扩展为SIGN_IN_WIDTH+1比特。//对称结构只需要计算FIR_WIDTH_DIV_2次//一级流水always @(posedge clk) beginif (rst=='b1)beginadd_a <= 'd0;add_b <= 'd0;coe <=   'd0;endelse beginadd_a <= {Sign_in_Reg[cnt][SIGN_IN_WIDTH-1],Sign_in_Reg[cnt]};add_b <= {Sign_in_Reg[FIR_COE_NUM-1-cnt][SIGN_IN_WIDTH-1],Sign_in_Reg[FIR_COE_NUM-1-cnt]};coe <= coe_data(cnt);endend(*use_dsp48="yes"*) reg signed [SIGN_IN_WIDTH+FIR_COE_WIDTH:0] mult_out;//always @(posedge clk ) beginif (rst=='b1)beginmult_out <= 'd0;endelse beginmult_out <= (add_a + add_b) * coe;endendassign signal_out = sign_out;reg signed [SIGN_OUT_WIDTH-1:0] sum;reg signed [SIGN_OUT_WIDTH-1:0] sign_out;//完成标志信号。wire finish_flag = (cnt==FIR_WIDTH_DIV_2-'b1);reg [2:0] finish_flag_r;always @(posedge clk ) beginfinish_flag_r<={finish_flag_r[1:0],finish_flag};endalways @(posedge clk)beginif (rst==1)begin sum <= 'd0; sign_out <= 'd0;endelse beginif (finish_flag_r[2]==1)beginsign_out <= sum;sum <= mult_out;endelse beginsum <= sum + mult_out;endendendendmodule

其中,代码增加了一个信号输出标志,该标志信号为传输8次数据后延时三拍的数据,为什么是三拍?因为读取信号后首先做了一级位宽拓展,第二级做了乘加运算,第三级为累加输出。所以输出信号相比传输数据完成的位置延迟三拍。

针对乘累加运算,这里没有使用IP,但是为了加速信号传输该信号的运算使用dsp48,所以在信号声明时前面加了(*use_dsp48="yes"*)

仿真数据设计

为了验证串行设计代码的正确性。这里使用MATLAB脚本产生了一个混频信号,然后将混频信号进行量化处理并导出txt文件以供仿真文件读取。

clc;close all;clear all;Fs = 2000; %采样频率
N = 2^10; %采样点数
f1=300; %正弦波1频率
f2=400; %正弦波1频率
t=[0:N-1]/Fs; %时间序列
s1 = sin(2*pi*f1*t) ;
s2 = sin(2*pi*f2*t) ;
s = s1 .* s2;
figure(1);
subplot(1,2,1);
plot(t,s,'r','LineWidth',1.2);
title('时域波形');
axis([0,100/Fs,-3,3]);
set(gca,'LineWidth',1.2);
%转化为位宽12bit数据
s_12bit=s./max(s).*(2.^11 - 1); % DA输入波形,量化到16bit
s_12bit(find(s_12bit<0) ) = s_12bit(find(s_12bit<0) ) + 2^12 - 1;
s_12bit = fix(s_12bit);
s_12bit = dec2hex(s_12bit);
% %生成文件
fid= fopen('sin_data.txt','w+');
%生成十六进制
for i=1:Nfprintf(fid,'%s',s_12bit(i,:));fprintf(fid,'\r\n');
end
fclose(fid);%% 设计验证
N=16;      %滤波器长度
fs=2000;   %采样频率
fc=500;    %低通滤波器的截止频率
B=12;      %量化位数
%生成各种窗函数
w_kais=blackman(N)';
%采用fir1函数设计FIR滤波器
b_kais=fir1(N-1,fc*2/fs,w_kais);
ss=conv(b_kais,s);
subplot(1,2,2);
plot(t(20:1000),ss(20:1000));
title('滤波后信号');
axis([0,100/Fs,-1,1]);
set(gca,'LineWidth',1.2);

运行仿真后,根据设计的滤波器系数进行仿真,发现可以正常滤波除去高频分量。

滤波仿真效果

仿真激励文件编写

`timescale 1ns / 1ps
module Fir_FullSerial_tb;// Parameterslocalparam integer SIGN_IN_WIDTH = 12;localparam integer SIGN_OUT_WIDTH = 29;localparam integer FIR_COE_WIDTH = 12;localparam integer FIR_COE_NUM = 16;// Portsreg clk = 1;reg rst = 1;reg [SIGN_IN_WIDTH-1:0] signal_in;wire [SIGN_OUT_WIDTH-1:0] signal_out;Fir_FullSerial #(.SIGN_IN_WIDTH(SIGN_IN_WIDTH ),.SIGN_OUT_WIDTH(SIGN_OUT_WIDTH ),.FIR_COE_WIDTH(FIR_COE_WIDTH ),.FIR_COE_NUM (FIR_COE_NUM ))Fir_FullSerial_dut (.clk (clk ),.rst (rst ),.signal_in (signal_in ),.signal_out  ( signal_out));reg  [11:0] mem [0:99];reg  [9:0] addr ;reg  [11:0]data_out ;always #(10*8)beginif(rst==0)addr = addr + 10'd1;signal_in  =  mem[addr][11:0];endalways#5  clk = ! clk ;initialbeginsignal_in =0;$readmemh("sin_data.txt",mem);addr  = 10'd0;#10;rst   = 0;end
endmodule

运行仿真,查看波形可见,滤波效果和仿真结果一致。

仿真波形

关于之前提到的延迟三拍的问题可以在波形输出这里查看,7ff为滤波器系数上次运算的最后一个数据,此数据运算结果在下一拍,乘加运算的结果为0,下一拍进行累加输出给sign_out输出。

延迟分析

实现模块框图

接口描述如下:

接口描述

参数描述如下:

参数描述

代码如下:

`timescale 1ns / 1ps
module Fir_FullSerial(input clk,//!系统时钟input rst,//!复位信号input signed [SIGN_IN_WIDTH-1:0] signal_in,//!信号输入output signed [SIGN_OUT_WIDTH-1:0] signal_out//!信号输出,信号输出速度为CLK/FIR_COE_NUM);//parameter  integer SIGN_IN_WIDTH    = 12   ;//!信号输入位宽parameter  integer SIGN_OUT_WIDTH = 29   ;//!信号输出位宽parameter  integer FIR_COE_WIDTH = 12   ;//!滤波器系数位宽parameter  integer FIR_COE_NUM = 16   ;//!滤波器长度localparam integer FIR_WIDTH_DIV_2 = FIR_COE_NUM/2 ;function [FIR_COE_WIDTH-1:0] coe_data;input [FIR_WIDTH_DIV_2-1:0] index;begincase(index)'d0:coe_data='h000;'d1:coe_data='hffd;'d2:coe_data='h00f;'d3:coe_data='h02e;'d4:coe_data='hf8b;'d5:coe_data='hef9;'d6:coe_data='h24e;'d7:coe_data='h7ff;endcaseendendfunction//!寄存输入信号reg [SIGN_IN_WIDTH-1:0] Sign_in_Reg[FIR_COE_NUM-1:0];//!计数器逻辑reg [FIR_WIDTH_DIV_2-1:0] cnt;always @(posedge clk ) beginif (rst=='b1) begincnt<='d0;endelse beginif (cnt==FIR_WIDTH_DIV_2-'b1) begincnt <= 0;endelse begincnt <= cnt + 1;endendend//将数据存入移位寄存器sign_in_Reg中integer i;always @(posedge clk)beginif (rst=='b1)begin//初始化寄存器值为0for (i=0; i<FIR_COE_NUM; i=i+1)Sign_in_Reg[i]=12'd0;endelse beginif (cnt==FIR_WIDTH_DIV_2-'b1)beginfor (i=0; i<FIR_COE_NUM-1; i=i+1)Sign_in_Reg[i+1] <= Sign_in_Reg[i];Sign_in_Reg[0] <= signal_in;endendendreg signed [SIGN_IN_WIDTH:0] add_a=0;reg signed [SIGN_IN_WIDTH:0] add_b;reg  signed [FIR_COE_WIDTH-1:0] coe; //为了保证加法运算不溢出,输入输出数据均扩展为SIGN_IN_WIDTH+1比特。//对称结构只需要计算FIR_WIDTH_DIV_2次//一级流水always @(posedge clk) beginif (rst=='b1)beginadd_a <= 'd0;add_b <= 'd0;coe <=   'd0;endelse beginadd_a <= {Sign_in_Reg[cnt][SIGN_IN_WIDTH-1],Sign_in_Reg[cnt]};add_b <= {Sign_in_Reg[FIR_COE_NUM-1-cnt][SIGN_IN_WIDTH-1],Sign_in_Reg[FIR_COE_NUM-1-cnt]};coe <= coe_data(cnt);endend(*use_dsp48="yes"*) reg signed [SIGN_IN_WIDTH+FIR_COE_WIDTH:0] mult_out;//always @(posedge clk ) beginif (rst=='b1)beginmult_out <= 'd0;endelse beginmult_out <= (add_a + add_b) * coe;endendassign signal_out = sign_out;reg signed [SIGN_OUT_WIDTH-1:0] sum;reg signed [SIGN_OUT_WIDTH-1:0] sign_out;//完成标志信号。wire finish_flag = (cnt==FIR_WIDTH_DIV_2-'b1);reg [2:0] finish_flag_r;always @(posedge clk ) beginfinish_flag_r<={finish_flag_r[1:0],finish_flag};endalways @(posedge clk)beginif (rst==1)begin sum <= 'd0; sign_out <= 'd0;endelse beginif (finish_flag_r[2]==1)beginsign_out <= sum;sum <= mult_out;endelse beginsum <= sum + mult_out;endendendendmodule

其中,代码增加了一个信号输出标志,该标志信号为传输8次数据后延时三拍的数据,为什么是三拍?因为读取信号后首先做了一级位宽拓展,第二级做了乘加运算,第三级为累加输出。所以输出信号相比传输数据完成的位置延迟三拍。

针对乘累加运算,这里没有使用IP,但是为了加速信号传输该信号的运算使用dsp48,所以在信号声明时前面加了(*use_dsp48="yes"*)

仿真数据设计

为了验证串行设计代码的正确性。这里使用MATLAB脚本产生了一个混频信号,然后将混频信号进行量化处理并导出txt文件以供仿真文件读取。

clc;close all;clear all;Fs = 2000; %采样频率
N = 2^10; %采样点数
f1=300; %正弦波1频率
f2=400; %正弦波1频率
t=[0:N-1]/Fs; %时间序列
s1 = sin(2*pi*f1*t) ;
s2 = sin(2*pi*f2*t) ;
s = s1 .* s2;
figure(1);
subplot(1,2,1);
plot(t,s,'r','LineWidth',1.2);
title('时域波形');
axis([0,100/Fs,-3,3]);
set(gca,'LineWidth',1.2);
%转化为位宽12bit数据
s_12bit=s./max(s).*(2.^11 - 1); % DA输入波形,量化到16bit
s_12bit(find(s_12bit<0) ) = s_12bit(find(s_12bit<0) ) + 2^12 - 1;
s_12bit = fix(s_12bit);
s_12bit = dec2hex(s_12bit);
% %生成文件
fid= fopen('sin_data.txt','w+');
%生成十六进制
for i=1:Nfprintf(fid,'%s',s_12bit(i,:));fprintf(fid,'\r\n');
end
fclose(fid);%% 设计验证
N=16;      %滤波器长度
fs=2000;   %采样频率
fc=500;    %低通滤波器的截止频率
B=12;      %量化位数
%生成各种窗函数
w_kais=blackman(N)';
%采用fir1函数设计FIR滤波器
b_kais=fir1(N-1,fc*2/fs,w_kais);
ss=conv(b_kais,s);
subplot(1,2,2);
plot(t(20:1000),ss(20:1000));
title('滤波后信号');
axis([0,100/Fs,-1,1]);
set(gca,'LineWidth',1.2);

运行仿真后,根据设计的滤波器系数进行仿真,发现可以正常滤波除去高频分量。

滤波仿真效果

仿真激励文件编写

`timescale 1ns / 1ps
module Fir_FullSerial_tb;// Parameterslocalparam integer SIGN_IN_WIDTH = 12;localparam integer SIGN_OUT_WIDTH = 29;localparam integer FIR_COE_WIDTH = 12;localparam integer FIR_COE_NUM = 16;// Portsreg clk = 1;reg rst = 1;reg [SIGN_IN_WIDTH-1:0] signal_in;wire [SIGN_OUT_WIDTH-1:0] signal_out;Fir_FullSerial #(.SIGN_IN_WIDTH(SIGN_IN_WIDTH ),.SIGN_OUT_WIDTH(SIGN_OUT_WIDTH ),.FIR_COE_WIDTH(FIR_COE_WIDTH ),.FIR_COE_NUM (FIR_COE_NUM ))Fir_FullSerial_dut (.clk (clk ),.rst (rst ),.signal_in (signal_in ),.signal_out  ( signal_out));reg  [11:0] mem [0:99];reg  [9:0] addr ;reg  [11:0]data_out ;always #(10*8)beginif(rst==0)addr = addr + 10'd1;signal_in  =  mem[addr][11:0];endalways#5  clk = ! clk ;initialbeginsignal_in =0;$readmemh("sin_data.txt",mem);addr  = 10'd0;#10;rst   = 0;end
endmodule

运行仿真,查看波形可见,滤波效果和仿真结果一致。

仿真波形

关于之前提到的延迟三拍的问题可以在波形输出这里查看,7ff为滤波器系数上次运算的最后一个数据,此数据运算结果在下一拍,乘加运算的结果为0,下一拍进行累加输出给sign_out输出。

延迟分析

数字信号处理——串行FIR滤波器MATLAB与FPGA实现相关推荐

  1. FPGA数字信号处理(三)串行FIR滤波器Verilog设计

    该篇是FPGA数字信号处理的第三篇,选题为DSP系统中极其常用的FIR滤波器.本文将在上一篇"FPGA数字信号处理(二)并行FIR滤波器Verilog设计" https://blo ...

  2. FIR数字滤波器的FPGA实现(二)-串行FIR滤波器设计(1)

    (二)FIR数字滤波器的FPGA实现-串行FIR滤波器设计 文章目录 (二)FIR数字滤波器的FPGA实现-串行FIR滤波器设计 0 串行FIR滤波器基本原理 1 基于移位寄存器的串行 FIR 滤波器 ...

  3. FIR数字滤波器的FPGA实现(二)-串行FIR滤波器设计(2)

    (二)FIR数字滤波器的FPGA实现-串行FIR滤波器设计 文章目录 (二)FIR数字滤波器的FPGA实现-串行FIR滤波器设计 0 串行FIR滤波器基本原理 1 基于移位寄存器的串行 FIR 滤波器 ...

  4. 数字信号处理5:FIR滤波器设计

    文章目录 1. 滤波器初识 2. 最直观的滤波方式:频域滤波 3. 傅里叶变换中的加窗 4. FIR滤波器设计 5. 总结 之前的一系列博客中,详细分解了从卷积到FFT的相关知识,不过那些属于理论,是 ...

  5. Verilog 串行FIR滤波器、并行FIR滤波器设计、FIR IP核实现

    fpga设计 使用MATLAB设计一个2kHz采样,500Hz截止的15阶低通滤波器(h(n)长度为16),量化位数为12bit,输入信号位宽也为12bit. 根据FIR直接型结构可知,滤波器实际上就 ...

  6. 【FPGA教程案例1】基于FPGA的串行FIR滤波器设计与实现

    FPGA教程目录 MATLAB教程目录 -------------------------------------------------------------------------------- ...

  7. 数字信号处理_只有FIR滤波器才能做到线性相位,对于IIR滤波器做不到线性相位?

    错误的,IIR滤波器加上一个相位矫正滤波器后,也可以实现线性相位. 对于线性相位滤波器,经常使用FIR滤波器.可以证明,FIR滤波器的单位脉冲响应满足一定条件时,其相位特性在整个频带是严格线性的,这是 ...

  8. matlab滤波器设计工具箱带阻滤波器,用matlab信号处理工具箱进行fir滤波器设计的三种方法...

    用matlab信号处理工具箱进行fir滤波器设计的三种方法 摘 要 介绍了利用 MATLAB 信号处理工具箱进行 FIR 滤波器设计的三种方法:程序设计法. FDATool 设计法和 SPTool 设 ...

  9. 用matlab仿真导航信号,北斗卫星导航信号串行捕获算法MATLAB仿真报告(附MATLAB程序)[互联网+]...

    <北斗卫星导航信号串行捕获算法MATLAB仿真报告(附MATLAB程序)[互联网+]>由会员分享,可在线阅读,更多相关<北斗卫星导航信号串行捕获算法MATLAB仿真报告(附MATLA ...

最新文章

  1. 直播 NO.5 | Facebook 田渊栋:用深度(强化)学习为组合优化寻找更好的启发式搜索策略...
  2. React学习:ref调用、组件封装调用-学习笔记
  3. 盘点2021年Linux界的12件大事
  4. 跨部门不配合工作_跨部门协作,队友总是“甩锅”,这三个方法教你快速避坑!...
  5. knime二次开发节点的项目结构
  6. Spring Security 教程
  7. iOS 开发-单元测试
  8. php导出csv插件,PHP导出CSV,EXCEL
  9. vscode替换文字快捷键_这 21 个VSCode 快捷键,能让你的代码飞起来
  10. pandas 索引去重_pandas(一)
  11. uigetfile使用方法
  12. python 爬虫 运用urlopen() 和urlretrieve()方法傻瓜操作 爬取虎牙直播主播头像
  13. Vj程序设计作业H5
  14. BlackBerry不能上网问题解决方案
  15. s8 android 8.0变化,等待很长时间!三星S8系列手机现在可以升级到Android 8.0系统的稳定版本!...
  16. 什么是DDL?其含义及其常用命令解析
  17. vivo手机便签app下载,vivo自带便签软件下载
  18. Python实现选择排序算法
  19. mysql删除重复记录语句的方法 作者: 字体:[增加 减小] 类型:转载 时间:2010-06-21 我要评论 查询及删除重复记录的SQL语句,虽然有点乱,但内容还是不错的。 . .
  20. ip库下载 mysql_IP地址库最新下载(最详细准确的ip数据库)

热门文章

  1. C++类和对象——友元部分
  2. 叮当快药:8090后养生报告
  3. 木偶娃娃的伤感日志推荐:只是一场赢不了的游戏
  4. Deep Graph-neighbor Coherence Preserving Network for Unsupervised Cross-modal Hashing
  5. Android studio 升级问题
  6. [Android 12 CameraITS环境搭建]
  7. 帆软FineReport 动态获取行的数值
  8. 数据结构与算法——知识点总结
  9. 星梦邮轮成为全球首家复航的邮轮公司
  10. JavaScript歌词解析算法