FPGA数字信号处理(六)直接型IIR滤波器Verilog设计

版权声明:本文为CSDN博主「FPGADesigner」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/FPGADesigner/article/details/80652480

该篇是FPGA数字信号处理的第六篇,2-5篇介绍了DSP系统中极其常用的FIR滤波器。本文将简单介绍另一种数字滤波器——IIR滤波器的原理,详细介绍使用Verilog HDL设计直接型IIR滤波器的方法,下一篇会介绍如何用Verilog HDL设计级联型IIR滤波器。

数字滤波器
数字滤波器从实现结构上划分,有FIR和IIR两种。FIR的特点是:线性相位、消耗资源多;IIR的特点是:非线性相位、消耗资源少。由于FIR系统的线性相位特点,设计中绝大多数情况都采用FIR滤波器。

线性相位系统的意义,这里的线性相位指的是在设计者关心的通带范围内,LTI系统满足线性相位要求:
(1)从延时的角度看:保证了输入信号的相位响应是线性的,即保证了输入信号的延时特性。
(2)从相位的角度看:输入的各频率成分的信号之间,相对相位是固定的。通过线性相位系统后,相对相位关系保持不变。

对于关心相位的系统,比如调制解调系统,需要使用FIR滤波器;对于只关心频率成分的系统,比如只是提取某一频率分量,为了节省资源,使用IIR滤波器即可。

IIR滤波器
IIR滤波器的系统函数与差分方程如下所示:

这里写图片描述

由差分方程可知IIR滤波器存在反馈,因此在FPGA设计时要考虑到有限字长效应带来的影响。差分方程中包括两个部分:输入信号x(n)的M节延时网络,相当于FIR的网络结构,实现系统的零点;输出信号y(n)的N节延时网络,作为系统的反馈,实现系统的极点。

直接由差分方程得到的IIR滤波器称为直接I型结构,如下图所示,左边为零点部分,右边为极点部分:

这里写图片描述

如果由IIR的系统函数出发,视作两个系统的级联,并且合并公共的延时支路,得到的IIR滤波器称为直接II型结构,如下图所示:

这里写图片描述

很明显,直接I型结构需要2N个延时单元;直接II型结构仅需要N个延时单元,使用FPGA设计时采用直接II型结构可以节省一些资源。IIR滤波器还有级联型和并联型两种结构,在下一篇的设计中再做介绍。

IIR滤波器在本质上是以模拟滤波器的设计理论为基础的,包括巴特沃斯滤波器、切比雪夫滤波器(I型和II型)、椭圆滤波器等。先设计好模拟滤波器,然后按一定的规则转换成数字滤波器,这种设计方法称为“原型转换设计法”,另外还有“直接设计法”。这两种方法都很繁琐,因此在工程中会借助MATLAB工具来设计IIR滤波器。

MATLAB设计
MATLAB提供了基于原型转换设计法的butter、cheby1、cheby2、ellip函数,分别对应巴特沃斯滤波器、切比雪夫I型/II型滤波器、椭圆滤波器;在频域采用最小均方法设计的yulewalk函数;以及两个应用程序包“Filter Builder”和“Filter Design&Analysis”,后者通常也被称作FDATOOL。现在最受欢迎的设计方式恐怕就是使用FDATOOL工具,功能强大、界面便捷。之前用于设计FIR滤波器,这两个工具也可以用于设计IIR滤波器。

本系列主要是讲述FPGA设计,不详细讨论上述函数及工具的使用,具体情况可以的MATLAB的help中查询。(Ps:博主目前的几个系列都处于开篇阶段,篇幅不多,暂未成体系,目前不再开新坑,等后期应该会出一个“MATLAB数字信号处理系列”)

FPGA设计
从MATLAB到FPGA最重要的工作便是滤波器系数的量化。在MATLAB中将滤波器系数量化为指定位宽,会改变滤波器的频率特性,尤其IIR滤波器存在反馈结构,量化效应和运算时的有限字长效应的影响比FIR滤波器大很多,因此需要做好仿真,确定量化后的系数也能满足IIR的设计需求。

设计一个切比雪夫II型滤波器cheby(7,60,0.5),进行12bit量化,量化前和量化后的系数如下表所示:

这里写图片描述

使用MATLAB多设计几个滤波器,就会发现一定的规律:(1).b和a两个向量的长度相同。(2).向量b(输入信号x(n)的延迟)具有对称性。(3).向量a的第一个元素总为1,即y(n)的系数总是1。

值得注意的是,量化后的向量Qa的第一个元素已经不是1,即y(n)多了一个加权系数。IIR中存在反馈结构,输出部分应该除掉这个加权系数,才能保证后续的计算正确。参考IIR滤波器的差分方程和直接I型结构,FPGA整体设计框图如下图所示:

这里写图片描述
Verilog HDL设计
由于IIR滤波器在DSP系统中不常用,Quartus和Vivado都没有提供相关的IP核,因此只能自己进行Verilog设计。本文设计参考自杜勇老师的《数字滤波器的MATLAB与FPGA实现》。本设计将在Vivado环境下完成并仿真。

零点系数部分可以完全视作一个FIR滤波器结构,设计接口与代码完全相同;极点系数部分也可以视作一个FIR滤波器结构,区别在于:(1).对反馈回来的信号y(n)做延迟;(2).系数不对称,不能利用对称性减少乘法器。

上述两个模块设计可以参考“FPGA数字信号处理(二)并行FIR滤波器Verilog设计” https://blog.csdn.net/fpgadesigner/article/details/80594627,也可以下载文末的工程,本文不再赘述。

顶层模块实例化零点和极点两个子模块,并按照设计框图设计减法器和除法器,完成IIR滤波数据的反馈和输出:

`timescale 1ns/1ps
//-------------------------------------------------------
//   IIR滤波器顶层模块
//-------------------------------------------------------
module DirectIIR_liuqi
(
    input rst,                 //高电平有效复位信号
    input clk,                 //系统时钟2kHz
    input signed [11:0] Din,   //采样数据输入2kHz
    output signed [11:0] Dout  //IIR滤波输出
);

//-------------------------------------------------------
//   实例化零点系数模块、极点系数模块
//-------------------------------------------------------
wire signed [20:0] Xout;
wire signed [11:0] Yin;
wire signed [25:0] Yout;

zero U0
(
    .rst   (rst),             
    .clk   (clk),              
    .Xin   (Din),  
    .Xout  (Xout)  
);

pole U1
(
    .rst   (rst),             
    .clk   (clk),              
    .Yin   (Yin),  
    .Yout  (Yout)  
);

//-------------------------------------------------------
//   反馈结构,右移实现除法
//-------------------------------------------------------
wire signed [25:0] Ysum = {{5{Xout[20]}},Xout} - Yout; //减法器
wire signed [25:0] Ydiv = {{9{Ysum[25]}},Ysum[25:9]};  //除法器
assign Yin = rst ? 'd0 : Ydiv[11:0];   //反馈
assign Dout = Yin;  //输出

endmodule


输出部分需要进行截取,截取时可以先进行仿真,只保留一位符号位即可。综合没有问题之后,打开Vivado中的RTL ANALYSIS,直接型IIR滤波器系统原理图如下所示,与预期设计相同:

这里写图片描述
仿真与工程下载
使用MATLAB生成一个200khz+800kHz的混合频率信号,写入txt文件。编写Testbench读取txt文件对信号滤波,文件操作方法参考“Testbench编写指南(一)文件的读写操作”https://blog.csdn.net/fpgadesigner/article/details/80470972。

对正弦信号的滤波如下图所示:

这里写图片描述

明显看到经过500Hz低通滤波器滤波后,输入的200+800Hz信号只剩下200Hz的频率分量。
完整的Vivado工程(含testbench仿真)可以在这里下载:https://download.csdn.net/download/fpgadesigner/10471904
————————————————

你可能感兴趣的:(FPGA,信号处理,IIR)