FFT仿真过程
第一步、创建工程
1、在ccs安装位置下ccsstudio_v3.3Myprojects文件夹创建一个文件夹命名为FFT.
![988503a8084a2f4a79e77bd78e928862.png](https://i-blog.csdnimg.cn/blog_migrate/47fcbabc114e636d0ec0dc57c6a2e50f.png)
2、将编写的程序文件保存在FFT中
3、打开ccs软件
![b55ffbe3d9e671fd88cd33b0227d1d3b.png](https://i-blog.csdnimg.cn/blog_migrate/e1f88f0f0965b8f91f606175b9d8776d.png)
4、在ccs中新建一个工程,从project菜单中选择New
![b7a54063bddf2eafa7f4cdfed00487a1.png](https://i-blog.csdnimg.cn/blog_migrate/c0f79bd7cbdb0b265bb17a93652971fa.png)
5、在Project Name中输入“FFT”
![6da683dd6190803dfcee158c5cebb147.png](https://i-blog.csdnimg.cn/blog_migrate/2482d43b2e7466bed4e49acccc70f546.png)
然后点击Finish,ccs就创建了一个名为FFT.pjt的工程。
![8ca0a41fcb98402da3806dba70046b60.png](https://i-blog.csdnimg.cn/blog_migrate/8a4e9899c0bfcf636c7342ab5f6ab699.png)
第二步、添加文件到工程中
1选择Project--Add Files to Project 添加FFT.c等文件
![1a2ffe63fece20a962134fc52757b132.png](https://i-blog.csdnimg.cn/blog_migrate/3d57e5685238e71a0c09122f6a8ed243.png)
2、选择Project--Add Files Project,找到.ccstudio_v3.3c2000cgtoolslib,选择与c55xx CA Simulators对应的库文件.
![a02d8689a2966883bd9dcd88c522c66d.png](https://i-blog.csdnimg.cn/blog_migrate/ef450f12db28a16ea9d8429b894584ab.png)
3、在FFT.pjt上右击,选择Scan All File Dependencies,系统会添加相关的头文件。
![f88189c3110a25230e3f9d4f66f473ea.png](https://i-blog.csdnimg.cn/blog_migrate/252a1eeeb84edf50fcd4847721367a33.png)
第三步、查看程序,并编译运行
1、选择Project-Rebuild All,程序将编译、综合、连接。
![18cb3dbf144e2b554cbb4cd605d53e79.png](https://i-blog.csdnimg.cn/blog_migrate/64fe5fd57644d1838365bdda984d82b0.png)
也可以选择工具栏中的按钮;默认情况下,工程文件的debug文件夹中将生成.out文件。
2、选择File-Load Program,选择刚才生成的FFT.out,点击OPen
![223e36f805b41a627b2ca75f618ce672.png](https://i-blog.csdnimg.cn/blog_migrate/0bc68e7cddd86a87c55920dce2c85c3d.png)
![9b3c7bc02aa5ba273f973feae9171da8.png](https://i-blog.csdnimg.cn/blog_migrate/4f762e3bf9fe6108e1f21b3996e3468d.jpeg)
第四步、观察图形
1、选择View-Graph-Time/Frequency
2、在对话框中修改参数如下图
![3078b3aff781a3aa48c83501652673a4.png](https://i-blog.csdnimg.cn/blog_migrate/18afa0569fd126736540285c91854dfb.jpeg)
3、点击ok,运行后将会出现一个图形窗口,运行程序得到输入信号的功率图谱如下
![2e1f04ccc7c6263a260a8114abf45c64.png](https://i-blog.csdnimg.cn/blog_migrate/db1814c65596f7f095bf8b5616a4392d.jpeg)
4、再次选择View-Graph-Time/Frequency 修改参数如下:
![ef1ff4992f437e1fdcbab48d088a188f.png](https://i-blog.csdnimg.cn/blog_migrate/004b64ad473076e87a82a83a799b44f6.jpeg)
FFT变换结果如下
![717f420106dab670d510132910150781.png](https://i-blog.csdnimg.cn/blog_migrate/d686c77f5f03ebaf51e60cee7cc014ee.png)
三、总结
FFT 对信号作频谱分析是学习数字信号处理的重要内容。经常需要进行谱分析的信号是模拟信号和时域离散信号。对信号进行谱分析的重要问题是频谱分辨率 D 和分析误差。频谱分辨率直接和 FFT 的变换区间 N 有关,因为 FFT 能够实现的频率分辨率是 2л/N≤D。可以根据此式选择 FFT 的变换区间 N。误差主要来自于用 FFT 作频谱分析时, 得到的是离散谱, 而信号(周期信号除外)是连续谱,只有当 N 较大时,离散谱的包络才能逼近于连续谱,因此 N 要适当选择大一些。
周期信号的频谱是离散谱,只有用整数倍周期的长度作 FFT,得到的离散谱才能代表周期信号的频谱。如果不知道信号周期,可以尽量选择信号的观察时间长一些。对模拟信号进行频谱分析时,首先要按照采样定理将其变成时域离散信号。如果是模拟周期信号,也应该选取整数倍周期的长度,经过采样后形成周期序列,按照周期序列的
普分析进行。
附:程序代码
FFT.c
#include "math.h"
#define sample_1 256
#define signal_1_f 60
#define signal_2_f 200
#define signal_sample_f 512
#define pi 3.1415926int input[sample_1];float fwaver[sample_1],fwavei[sample_1],w[sample_1];float sin_tab[sample_1];float cos_tab[sample_1];void init_fft_tab();void input_data();void fft(float datar[sample_1],float datai[sample_1]);void main()
{int i;init_fft_tab();input_data();for (i=0;i<sample_1;i++)
{
fwaver[i]=input[i];
fwavei[i]=0.0f;
w[i]=0.0f;
}fft(fwaver,fwavei);while(1);
}void init_fft_tab()
{float wt1;float wt2;int i;for (i=0;i<sample_1;i++)
{
wt1=2*pi*i*signal_1_f;
wt1=wt1/signal_sample_f;
wt2=2*pi*i*signal_2_f;
wt2=wt2/signal_sample_f;
input[i]=(cos(wt1)+cos(wt2))/2*32768;
}
}void input_data()
{int i;for(i=0;i<sample_1;i++)
{
sin_tab[i]=sin(2*pi*i/sample_1);
cos_tab[i]=cos(2*pi*i/sample_1);
}
}void fft(float datar[sample_1],float datai[sample_1])
{int x0,x1,x2,x3,x4,x5,x6,x7,xx;int i,j,k,b,p,L;float TR,TI,temp;for(i=0;i<sample_1;i++)
{
x0=x1=x2=x3=x4=x5=x6=0;
x0=i&0x01;x1=(i/2)&0x01;x2=(i/4)&0x01;x3=(i/8)&0x01;
x4=(i/16)&0x01;x5=(i/32)&0x01;x6=(i/64)&0x01;x7=(i/128)&0x01;
xx=x0*128+x1*64+x2*32+x3*16+x4*8+x5*4+x6*2+x7;
datai[xx]=datar[i];
}for(i=0;i<sample_1;i++)
{
datar[i]=datai[i];datai[i]=0;
}for(L=1;L<=8;L++)
{
b=1;i=L-1;while(i>0)
{
b=b*2;i--;
}for(j=0;j<=b-1;j++)
{
p=1;i=8-L;while(i>0)
{
p=p*2;i--;
}
p=p*j;for(k=j;k<256;k=k+2*b)
{
TR=datar[k];TI=datai[k];temp=datar[k+b];
datar[k]=datar[k]+datar[k+b]*cos_tab[p]+datai[k+b]*sin_tab[p];
datai[k]=datai[k]-datar[k+b]*sin_tab[p]+datai[k+b]*cos_tab[p];
datar[k+b]=TR-datar[k+b]*cos_tab[p]-datai[k+b]*sin_tab[p];
datai[k+b]=TI+temp*sin_tab[p]-datai[k+b]*cos_tab[p];
}
}
}for(i=0;i<sample_1/2;i++)
{
w[i]=sqrt(datar[i]*datar[i]+datai[i]*datai[i]);
}
}
FFT.cmd
-f 0-w-stack 500-sysstack 500-l rts55.lib
MEMORY
{
DARAM: o=0x100, l=0x7f00
VECT:o=0x8000, l=0x100
DARAM2:o=0x8100,l=0x7f00
SARAM: o=0x10000,l=0x30000
SDRAM:o=0x40000,l=0x3e0000
}
SECTIONS
{.text: {}>DARAM.vectors: {}>VECT.trcinit:{}>DARAM.gblinit:{}>DARAM.frt:{}>DARAM.cinit:{}>DARAM.pinit:{}>DARAM.sysinit:{}>DARAM2.far:{}>DARAM2.const:{}>DARAM2.switch:{}>DARAM2.sysmem:{}>DARAM2.cio:{}>DARAM2.MEM$obj:{}>DARAM2.sysheap:{}>DARAM2.sysstack:{}>DARAM2.stack:{}>DARAM2.input:{}>DARAM2.fftcode:{}>DARAM2
}