FIR滤波器程序的编写.docx
- 文档编号:29347359
- 上传时间:2023-07-22
- 格式:DOCX
- 页数:16
- 大小:103.40KB
FIR滤波器程序的编写.docx
《FIR滤波器程序的编写.docx》由会员分享,可在线阅读,更多相关《FIR滤波器程序的编写.docx(16页珍藏版)》请在冰豆网上搜索。
FIR滤波器程序的编写
目录
1.引言1
2.FIR滤波器基本原理1
2.1两种FIR滤波器的框图及原理1
2.2用DSP实现的数字FIR滤波器的优点2
3.FIR滤波器的设计方法3
4.FIR滤波器的c54x实现4
5.FIR滤波器的实例设计7
5.1编写滤波器序列7
5.2汇编源程序主程序的编写8
5.3中断向量表的编写10
5.4相关的连接命令文件12
5.5程序在CCSC5000中编译12
6.设计心得13
7.参考文献14
1.引言
在数字信号处理中,滤波占有及其重要的地位。
数字滤波是谱分析、雷达信号处理、通信信号处理等应用中的基本处理算法,它能够满足滤波器对幅度和相位的严格要求,解决了模拟滤波器所无法克服的电压漂移、温度漂移和噪声等问题,同时有很高的可编程性和灵活性。
数字滤波是DSP最基本的应用领域,一个DSP芯片执行数字滤波算法的能力反应了这种芯片的功能强弱,用DSP实现的数字滤波器可以十分方便地改变滤波器的特性。
2.FIR滤波器基本原理
2.1两种FIR滤波器的框图及原理
对于FIR数字滤波器来说,它的实现一般采用非递归的算法,图2.1给出的是直接型和转置型FIR滤波器的机构图。
(a)直接型横向滤波器
(b)转置型横向滤波器
图2.1直接型和转置型FIR滤波器结构图
FIR数字滤波器的差分方程表达式为:
y(n)=∑Nh(i)x(n-i)
其中N为FIR滤波器的阶数,FIR滤波器的单位脉冲响应h(n)是一个有限长序列。
在数字信号处理应用中往往需要设计线性相位的滤波器,FIR滤波器在保证幅度特性满足技术要求的同时,很容易做到严格的线性相位特性。
为了是滤波器满足线性相位条件,要求其单位脉冲响应h(n)为实序列,且满足偶对称或奇对称条件,即h(n)=h(N-1-n)或h(n)=-h(N-1-n)。
这样,当N为偶数时,偶对称线性相位FIR滤波器的差分方程表达式为:
y(n)=∑N/2-1h(i)(x(n-i)+x(N-1-n-i))
由上可见,FIR滤波器不断地对输入样本x(n)延时后,再作乘法累加运算,将滤波结果y(n)输出,因此,FIR实际上是一种乘法累加运算。
而对于线性相位FIR而言,利用线性相位FIR滤波器系数的对称特性,可以采用结构精简的FIR结构将乘法器数目减少一半,但加法器数目不变,这时乘法操作数和加法操作次数是1:
2。
事实上,线性相位FIR滤波器是用得最多的FIR滤波器。
2.2用DSP实现的数字FIR滤波器的优点
在数字滤波器中,FIR滤波器的最主要的特点是没有反馈回路,故不存在不稳定的问题;同时,可以在幅度特性随意设置的同时,保证精度、严格的线性相位。
稳定和线性相位特性是FIR滤波器的突出优点。
FIR滤波器常表示为直接型和转置型两种结构,其功能是等效的。
在用专用DSP或FPGA等硬件设计长阶数FIR滤波器时,常采用转置型结构,因为这种结构便于设计成大量规则排列、形式相同的乘法/累加器阵列,避免了直接型中的多输入加法器在长阶数时的实现困难。
在用通用定点DSP实现FIR滤波器时,更多的是采用直接型结构,对于C54X来说,其单乘法器、双累加器结构更适合于对称FIR实现;如果采用转置结构,因为定点DSP仅乘法/累加器是32位或40位的,数据存储器都是16位的,用16位存储器保证FIR滤波器每级乘法/累加器输出的中间结果比较麻烦,程序效率也降低了。
3.FIR滤波器的设计方法
FIR滤波器的设计方法主要有窗函数法和频率采样法,其中,窗函数法是最基本的方法。
窗函数法的过程是:
设期望的滤波器理想响应为Hd(ejω),需要寻找一个传递函数H(ejω)=ΣN-1h(n)e-jω去逼近Hd(ejω),其中最直接的方法就是将Hd(ejω)的时域响应hd(n)用一个矩形窗RN(n)进行截断,从而得到一个长度为N的序列h(n),即令
h(n)=hd(n)RN(n)
理想响应Hd(ejω)与其时域响应hd(n)也有Hd(ejω)=Σ∞hd(n)e-jω的关系,通常hd(n)是一个关于原点n=0对称的无限长序列,截断后的h(n)还应进行右移以形成一个因果的FIR滤波器,即在n<0时,h(n)=0。
为了保证h(n)的线性相位,还应使h(n)关于中心点对称或反对称。
很明显,h(n)与期望的响应之间的误差随着窗长的增加而减小。
利用上述各种窗函数,DSP设计者可以利用Matlab工具很方便地设计出逼近理想特性的FIR滤波器,然后将此FIR系数放入DSP程序中。
如下例:
设计一个FIR低通滤波器,其设计参数:
滤波器阶数为40,截至频率ωp=0.35π,Ωs=0.4π。
根据给定的设计参数,滤波器系数可由Matlab中的fir2函数生成,函数调用格式为
f=[00.350.41]
m=[1100]
b=fir2(39,f,m)
求得的系数如图3.1所示
图3.1Matlab求得滤波器系数
4.FIR滤波器的c54x实现
FIR是将待滤波的数据序列与滤波系数序列相乘后再相加运算,同时要模仿FIR结构中的延迟线将数据在存储器中滑动。
C54x用寻址I/O单元的指令实现序列x(n)的输入和序列y(n)的输出:
PORTRPA1,Smem;从PA1口中输入数据;
PORTWSmen,PA2;从PA2口输出数据。
这两条指令至少要2个字和2个机器周期。
如果I/O设备是慢速器件,则需要插入等待状态。
此外,当利用长偏移间接寻址或绝对寻址Smen是还要增加1个字和1个机器周期。
为了实现FIR滤波器的延迟线z-1,可以通过循环缓冲方法实现。
用循环缓冲区方法实现N阶FIR滤波器时,需要在数据存储器中开盘批一个称为滑窗为N个单元的缓冲区,滑窗中存放最新的N个输入样本。
当每次输入新的样本时,以新样本改写滑窗中的最老
图4.1线性缓冲区实现延时
的数据,而滑窗中的其它数据不需要移动。
因此,在循环缓冲区中新老数据不很直接明了,但它不需要移动数据,不存在在一个机器周期中要求进行一次读和一次写的数据存储器,因此,可以将循环缓冲区定位在数据存储器的任何位置。
图4.1是N=5,线性缓冲区实现延时的图示。
实现循环缓冲区间接寻址的关键问题死:
如何是N个循环缓冲区单元首尾单元相邻?
这需要采用c54x所提供的循环寻址方式来实现。
采用循环寻址,需注意以下两点:
(1)必须利用循环缓冲区长度(BK)寄存器来实现按模间接寻址。
可用的指令包括:
*ARx+%;加1、按模修正ARx
*ARx-%;减1、按模修正ARx
*ARx+0%;加AR0、按模修正ARx
*ARx-0%;减AR0、按模修正ARx
*+ARx(lk)%;加(lk)、按模修正ARx
其中,每一条指令均按照BK寄存器中的值,分别对(ARx+1)、(ARx-1)、(ARx+AR0)、(ARx-AR0)、
(ARx+lk)值取模。
在实现N阶FIR时,通过STM#lk,BK指令设定BK的值为FIR的阶数,就能保证循环缓冲区的指针ARx始终指向循环缓冲区,实现循环缓冲区顶部和底部单元相邻。
(2)为了使循环寻址正常进行,所开辟的循环还小红分区的长度必须是2k>N,其中k是整数,N是FIR滤波器的级数,而且循环缓冲区的起始地址必须对准2k边界,即循环缓冲区基地址的k个最低有效位必须为0,如N=31是,循环缓冲区必须从二进制地址xxxxxxxxxxx000002开始。
可见,在循环寻址实现FIR滤波器时,首先将N值加载到BK寄存器中,然后指定一个辅助寄存器ARx指向循环缓冲区,并根据ARx的低k位作为循环缓冲区的偏移量进行所规定的寻址操作。
寻址完成后,根据循环寻址算法修正这个偏移量,并返回ARx的低k为。
下面是利用循环缓冲区和双操作数寻址方法实现的FIR滤波器程序。
设N=5,y(n)=a0x(n)+a1(n-1)+a2(n-2)+a3(n-3)+a4(n-4),且存放a0~a4的系数表在ROM中,存放数据的循环缓冲区在DARAM中。
程序如下:
.mmregs
.defstart
.bssy,1
Xn.usect“xn”,5
A0.usect“a0”,5
PA0.set0
PA1.set1
.data
Table:
.word1*32786/10;a0=0.1=0x0ccc
.word2*32786/10;a1=0.2=0x1999
.word3*32786/10;a2=0.3=0x2666
.word4*32786/10;a3=0.4=0x3333
.word5*32786/10;a4=0.5=0x4000
.text
Start:
SSBXFRCT;小数乘法
STM#a0,AR1;AR1指向a0
RPT#4;传送5个系数至数据空间
MVPDtable.*AR1+
STM#xn+4,AR3;AR3指向x(n-4)
STM#a0+4,AR4;AR4指向a4
STM#5,BK;循环缓冲区长度BK=5
STM#-1,AR0;AR0=-1,双操作数减量
LD#xn,DP
PORTRPA1,@xn;输入x(n)
FIR:
RPTZA,#4;A清零,共迭代5次
MAC*AR3+0%,*AR4+0%,A;双操作数乘法累加
STHA,@y;保存y(n)
PORTW@y,PA0;输出y(n)
BDFIR;循环
PORTRPA1,*AR3+0%;输入新数据
END
5.FIR滤波器的实例设计
5.1编写滤波器序列
由已知的滤波器的系数可得滤波器的序列为:
.data
htab:
.word-10*32768/1000
.word-10*32768/1000
.word40*32768/1000
.word60*32768/1000
.word80*32768/1000
.word-50*32768/1000
.word-60*32768/1000
.word70*32768/1000
.word-80*32768/1000
.word-90*32768/1000
.word98*32768/1000
.word-90*32768/1000
.word80*32768/1000
.word-70*32768/1000
.word60*32768/1000
.word-50*32768/1000
.word-80*32768/1000
.word60*32768/1000
.word40*32768/1000
.word-10*32768/1000
.word-10*32768/1000
.word00*32768/1000
.word00*32768/1000
.word00*32768/1000
.word00*32768/1000
.word00*32768/1000
.word00*32768/1000
.word00*32768/1000
5.2汇编源程序主程序的编写
采用循环缓冲区实现FIR滤波器的程序如下:
.mmregs
.include"htable.inc"
.include"xtable.inc"
.defstart
htabcnt.set20
xtabcnt.set80
STACK.usect".stack",30H
.bssncnt,1
.bssx_tab,80H,1
.bssh_tab,80H,1
.bssr_tab,80H,1
.bssdb_tab,80H,1
.asg0+FRAME_SZ,SAVE_AR1
.asg0+REG_SAVE_SZ+FRAME_SZ,RETURN_ADDR
.asg0+PARAM_OFFSET,h
.asg1+PARAM_OFFSET,r
.asg2+PARAM_OFFSET,db
.asg3+PARAM_OFFSET,nh
.asg4+PARAM_OFFSET,nx
.asg0,nc
.asgAR2,r_ptr;结果连续
.asgAR3,h_ptr;h连续滤波
.asgAR4,x_ptr;x连续输入
.asgAR5,db_ptr;中值连续
.asgBRC,rptb_cnt;记数
start:
SSBXSXM
SSBXFRCT;设置小数乘法
STM#x_tab,x_ptr;AR1指向b0单元
RPT#(xtabcnt-1);设置传输次数
MVPDxtab,*x_ptr+;系数bi传输至数据区
STM#h_tab,h_ptr;h_tab缓冲区清零
RPT#(htabcnt-1)
MVPDhtab,*h_ptr+
STM#x_tab,x_ptr
STM#h_tab,h_ptr
STM#r_tab,r_ptr
STM#db_tab,db_ptr;设置双操作数减量
LD#xtabcnt,A;设置页指针
STLMA,rptb_cnt
LD#htabcnt,A
STLMA,BK
SUB#3,A
STLA,*(ncnt)
RPTBDEND_LOOP-1;存贮0到AR0
STM#1,AR0
MVDD*x_ptr+,*db_ptr;h*x的和相加送入下一个y值
MPY*h_ptr+0%,*db_ptr+0%,A
RPT*(ncnt)
MAC*h_ptr+0%,*db_ptr+0%,A
MACR*h_ptr+0%,*db_ptr,A;存贮结果
STHA,*r_ptr+
END_LOOP:
_end:
RETURN:
LDMdb_ptr,B
LD#0,A
XC1,AOV
LD#1,A
5.3中断向量表的编写
.sect".vectors"
.refstart
.align0x80
RESET:
BDstart;branchtoCentrypoint
STM#200,SP;设置堆栈初植为200
nmi:
RETE;中断返回
NOP
NOP
NOP;软件中断
sint17.space4*16
sint18.space4*16
sint19.space4*16
sint20.space4*16
sint21.space4*16
sint22.space4*16
sint23.space4*16
sint24.space4*16
sint25.space4*16
sint26.space4*16
sint27.space4*16
sint28.space4*16
sint29.space4*16
sint30.space4*16
int0:
RETE
NOP
NOP
NOP
int1:
RETE
NOP
NOP
NOP
int2:
RETE
NOP
NOP
NOP
tint:
RETE
NOP
NOP
NOP
rint0:
RETE
NOP
NOP
NOP
xint0:
RETE
NOP
NOP
NOP
rint1:
RETE
NOP
NOP
NOP
xint1:
RETE
NOP
NOP
NOP
int3:
RETE
NOP
NOP
NOP
.end
5.4相关的连接命令文件
vectors.obj
abc.obj
-oa1.out
-ma1.map
-estart
MEMORY
{
PAGE0:
EPROG:
origin=0x1400,len=0x7c00
VECT:
origin=0xff80,len=0x80
PAGE1:
USERREGS:
origin=0x60,len=0x1c
BIOSREGS:
origin=0x7c,len=0x4
IDATA:
origin=0x80,len=0x1380
EDATA:
origin=0x1400,len=0x8000
EDATA1:
origin=0x9400,len=0x4c00
}
SECTIONS
{
.vectors:
{}>VECTPAGE0
.sysregs:
{}>BIOSREGSPAGE1
.data:
{}>EPROGPAGE0
.text:
{}>EPROGPAGE0
.cinit:
{}>EPROGPAGE0
.pinit:
{}>EPROGPAGE0
.sysinit:
{}>EPROGPAGE0
.stack:
{}>IDATAPAGE1
.bss:
{}>IDATAPAGE1
.sin_vars:
{}>IDATAPAGE1
}
5.5程序在CCSC5000中编译
将编写的源文件加载到CCSC5000中,通过编译检查所编写的程序是否正确。
再连接编译得输入波形、滤波器波形、输出波形。
如图5.1所示:
图5.1编译得到的输入波形、滤波器波形、输出波形
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- FIR 滤波器 程序 编写