资源描述
DSP原理及应用实 验 指 导 书杨宣兵 编 写适用专业:电子信息工程 _电子科学与技术 信息工程 通信工程 信息与通信工程学院2011 年 5 月前 言DSP原理与应用是电子信息类专业信号与信息处理方向的一门专业必修课,同时也是其他电类专业的一门重要的选修课。课程以DSP芯片原理及基于DSP芯片的应用系统开发为主要内容,介绍了DSP芯片原理与开发工具及软硬件开发方法。开设必要的课程实验,使学生加深对DSP原理与片上资源应用的掌握,掌握DSP项目开发流程、开发方法、开发平台CCS的基本使用、DSP对外设控制方法以及经典数字信号处理算法的DSP工程实现等。培养学生将数字信号处理理论应用到实际项目中的工程意识与工程开发能力。通过本课程实验,提高学生分析问题、解决问题的能力和基于DSP的嵌入式系统开发的实际动手能力,为学生步入社会奠定工程开发基础。对不同专业根据实验教学大纲进行实验项目选择。实验项目设置与内容提要序号实验项目实验学时每组人数实验类型实验要求内 容 提 要1基本算术运算的DSP实现41验证必修1、CCS基本操作;2、DSP应用程序结构和开发流程;3、基于DSP开发环境(Simulator)完成16位定点加、减、乘、除运算。2数字振荡器的设计与实现41设计必修1、CCS图形工具使用;2、基于C语言和汇编语言混合程序设计;3、定时器等外设资源的应用;4、简单算法(迭代)的实现。3BSP串口通信实现42综合必修1、McBSP串口操作;2、VC54XX片上ROM资源的使用;4FIR数字滤波器设计与实现实现42设计选修1、McBSP串口操作与串口中断服务程序编写;2、AD/DA操作;3、FIR滤波器实现的特殊指令应用;4、CCS高级调试工具使用。5TMS320VC5402的Bootloader设计与实现4510设计必修1、编程完成对外设I/O端口的控制,实现流水灯功能;2、完成从COFF文件到启动表的转换;3、完成程序的固化与脱离上位机控制的独立运行。6快速傅立叶变换实现42综合选修1、辅助寄存器使用,位倒序寻址方式应用等;2、FFT算法的编程实现;3、CCS探针和图形工具使用。7外部设备控制实验41综合任选1、熟悉外部中断使用与中断服务程序编写方法;2、掌握对外设端口的操作方法;3、掌握外设的控制方法(包括键盘、LED、步进电机、LCD等);8双音多频信号编码器设计22设计选修1、 掌握DTMF信号的产生原理;2、 掌握DTMF信号产生的DSP实现方法;9双音多频信号解码器设计42设计选修3、 掌握DTMF信号的解码算法原理;4、 掌握DTMF信号解码算法的DSP实现方法;目 录实验一 基本算术运算的DSP实现1实验二 数字振荡器的设计与实现.9实验三 BSP 串口通信实现16实验四 FIR 数字滤波器设计与实现.25实验五 TMS320VC5402 的Bootloader设计与实现.34实验六 快速傅立叶变换(FFT)的实现.45实验七 外部中断、按键、LED控制实验.67实验八 双音多频DTMF信号产生.70实验九 双音多频DTMF信号解码.76附录一 DES5402PP-U性能介绍82附录二CCS驱动程序的安装83附录三DES5402PP-U功能详细介绍87附录四 DES5402PP-U板上设置、状态显示、跳线一览表93实验一: 基本算术运算的DSP实现 实验学时:4实验类型:验证实验要求:必修一、实验目的1、掌握CCS的配置与基本使用方法;2、掌握C54X汇编语言程序结构,掌握基于CCS开发平台Simulator采用汇编指令完成16位定点加减乘除运算程序设计并对运算结果进行评价;二、实验内容本实验学习使用定点DSP实现16位定点加、减、乘、除运算的基本方法和编程技巧。三、实验原理、方法和手段1定点DSP中数据表示方法 C54X是16位的定点DSP。一个16位的二进制数既可以表示一个整数,也可以表示一个小数。当它表示一个整数时,其最低位(D0)表示,D1位表示,次高位(D14)表示。如果表示一个有符号数时,最高位(D15)为符号位,0表示正数,1表示负数。例如,07FFFH表示最大的正数32767(十进制),而0FFFFH表示最大的负数-1(负数用2的补码方式显示)。当需要表示小数时,小数点的位置始终在最高位后,而最高位(D15)表示符号位。这样次高位(D14)表示,然后是,最低位(D0)表示。所以04000H表示小数0.5,01000H表示小数,而0001H表示16位定点DSP能表示的最小的小数(有符号)=0.000030517578125。在后面的实验中,除非有特别说明,我们指的都是有符号数。在C54X中,将一个小数用16位定点格式来表示的方法是用乘以该小数,然后取整。从上面的分析可以看出,在DSP中一个16进制的数可以表示不同的十进制数,或者是整数,或者是小数(如果表示小数,必定小于1),但仅仅是在做整数乘除或小数乘除时,系统对它们的处理才是有所区别的,而在加减运算时,系统都当成整数来处理。 2实现16定点加法 C54X中提供了多条用于加法的指令,如ADD,ADDC,ADDM和ADDS。其中ADDS用于无符号数的加法运算,ADDC用于带进位的加法运算(如32位扩展精度加法),而ADDM专用于立即数的加法。在本实验中,我们可以使用下列代码来说明加法运算:ldtemp1,a;将变量temp1装入寄存器Aaddtemp2,a;将变量temp2与寄存器A相加,结果放入A中stla,add_result ;将结果(低16位)存入变量add_result中。注意,这里完成计算temp3=temp1+temp2,我们没有特意考虑temp1和temp2是整数还是小数,在加法和下面的减法中整数运算和定点的小数运算都是一样的。3实现16位定点减法C54X中提供了多条用于减法的指令,如SUB,SUBB,SUBC和SUBS。其中SUBS用于无符号数的减法运算,SUBB用于带进位的减法运算(如32位扩展精度的减法),而SUBC为移位减,DSP中的除法就是用该指令来实现的。SUB指令与ADD指令一样,有许多的寻址方式,其详细使用说明请查阅TI文档。在本实验中,我们可以使用下列代码来说明减法运算:stm#temp1,ar3;将变量temp1的地址装入ar3寄存器stm#temp3,ar2;将变量temp3的地址装入ar3寄存器sub*ar2+, *ar3,b ;将变量temp3左移16位同时变量temp1也左移;16位,然后相减,结果放入寄存器B(高16位)中,;同时ar2加1。sthb,sub_result;将相减的结果(高16位)存入变量sub_result。4实现16定点整数乘法 在C54X中提供了大量的乘法运算指令,其结果都是32位,放在A或B寄存器中。乘数在C54X的乘法指令很灵活,可以是T寄存器、立即数、存贮单元和A或B寄存器的高16位。在C54X中,一般对数据的处理都当做有符号数,如果是无符号数乘时,请使用MPYU指令。这是一条专用于无符号数乘法运算的指令,而其它指令都是有符号数的乘法。在本实验中,我们使用下列代码来说明整数乘法运算:rsbx FRCT;清FRCT标志,准备整数乘ldtemp1,T;将变量temp1装入T寄存器mpytemp2,a;完成temp2*temp1,结果放入A寄存器(32位)例如,当temp1=1234H(十进制的4660),temp2=9876H(十进制的-26506),乘法的结果在A寄存器中为0F8A343F8H(十进制的-123517960)。这是一个32位的结果,需要两个内存单元来存放结果:stha,mpy_I_h;将结果(高16位)存入变量mpy_I_hstla,mpy_I_l;将结果(低16位)存入变量mpy_I_l当temp1=10H(十进制的16),temp2=05H(十进制的5),乘法结果在A寄存器中为00000050H(十进制的80)。对于这种情况,仅仅需要保存低16位即可:stla,mpy_I_l;将结果(低16位)存入变量mpy_I_l5实现16定点小数乘法 在C54X中,小数的乘法与整数乘法基本一致,只是由于两个有符号的小数相乘,其结果的小数点的位置在次高的后面,所以必须左移一位,才能得到正确的结果。C54X中提供了一个状态位FRCT,将其设置为1时,系统自动将乘积结果左移移位。但注意整数乘法时不能这样处理,所以上面的实验中一开始便将FRCT清除。两个小数(16位)相乘后结果为32位,如果精度允许的话,可以只存高16位,将低16位丢弃,这样仍可得到16位的结果。在本实验中,我们使用下列代码来说明小数乘法运算:ssbxFRCT;FRCT=1,准备小数乘法ldtemp1,16,a;将变量temp1装入寄存器A的高16位mpyatemp2;完成temp2乘寄存器A的高16位,结果在B中;同时将temp2装入T寄存器sthb,mpy_f;将乘积结果的高16位存入变量mpy_f例如,temp1=temp2=4000H(十进制的0.5),两数相乘后结果为20000000(十进制的=0.25)。再如,temp1=0ccdH(十进制的0.1),temp2=0599aH(十进制的0.7),两数相乘后B寄存器的内容为08f5f0a4H(十进制的0.07000549323857)。如果仅保存结果的高16位08f5H(十进制的0.06997680664063)。有时为了提高精度,可以使用RND或使用MPYR指令对低16位做四舍五入的处理。6实现16定点整数除法 在C54X中没有提供专门的除法指令,一般有两种方法来完成除法。一种是用乘法来代替,除以某个数相当于乘以其倒数,所以先求出其倒数,然后相乘。这种方法对于除以常数特别适用。另一种方法是使用SUBC指令,重复16次减法完成除法运算。下面我们以temp1/temp2为例,说明如何使用SUBC指令实现整数除法。其中变量temp1为被除数,temp2为除数,结果即商存放在变量temp3中。在完成整数除法时,先判断结果的符号。方法是将两数相乘,保存A或B的高16位以便判断结果的符号。然后只做两个正数的除法,最后修正结果的符号。为了实现两个数相除,先将被除数装入A或B的低16位,接着重复执行SUBC指令,用除数重复减16次后,除法运算的商在累加器的低16位,余数在高16位。详细代码如下:ldtemp1,T;将被除数装入T寄存器mpytemp2,A;除数与被除数相乘,结果放入A寄存器ldtemp2,B;将除数temp2装入B寄存器的低16位absB;求绝对值stlB,temp2;将B寄存器的低16位存回temp2ldtemp1,B;将被除数temp1装入B寄存器的低16位absB;求绝对值rpt#15;重复SUBC指令16次subctemp2,b;使用SUBC指令完成除法运算bcddiv_end,agt;延时跳转,先执行下面两条指令,然后判断A,;若A0,则跳转到标号div_end,结束除法运算stlB,quot_i;将商(B寄存器的低16位)存入变量quot_isthB,remain_i;将余数(B寄存器的高16位)存入变量remain_ixorB;若两数相乘的结果为负,则商也应为负。先;将B寄存器清0subquot_i,B;将商反号stlB,quot_i;存回变量quot_i中div_end:上面给出的是整数除法的通用程序,在实际应用中可以根据具体情况做简化。如正数除法可以直接将被除数temp1装入B寄存器的低16位,然后用SUBC指令循环减除数temp2,减完后B寄存器中低16位为商,高16位为余数,不用判断符号,从而节省时间。例如temp1=10H(十进制的16),temp2=5,两数相除后商为3(在B寄存器的低16位),余数为1(在B寄存器的高16位)。7实现16定点小数除法 在C54X中实现16位的小数除法与前面的整数除法基本一致,也是使用循环的SUBC指令来完成。但有两点需要注意:第一,小数除法的结果一定是小数(小于1),所以被除数一定小于除数。这与整数除法正好相反。所以在执行SUBC指令前,应将被除数装入A或B寄存器的高16位,而不是低16位。其结果的格式与整数除法一样,A或B寄存器的高16位为余数,低16位为商。第二,与小数乘法一样,应考虑符号位对结果小数点的影响。所以应对商右移一位,得到正确的有符号数。其详细代码如下:ldtemp1,T;将被除数装入T寄存器mpytemp2,A;除数与被除数相乘,结果放入A寄存器ldtemp2,B;将除数temp2装入B寄存器的低16位absB;求绝对值stlB,temp2;将B寄存器的低16位存回temp2ldtemp1,16,B;将被除数temp1装入B寄存器的高16位absB;求绝对值rpt#15;重复SUBC指令16次subctemp2,b;使用SUBC指令完成除法运算and#0ffffh,B;将B寄存器的高16位清为0。这时余数被;丢弃,仅保留商bcddiv_end,agt;延时跳转,先执行下面两条指令,然后判断A,; 若A0,则跳转到标号div_end,结束除法运算stlB,-1,quot_f;将商右移一位后存入变量quot_f,右移是为了;修正符号位xorB;若两数相乘的结果为负,则商也应为负。先将B;寄存器清0subquot_f,B;将商反号stlB,quot_f;存回变量quot_f中div_end: 注意,上面的C54X的16位定点有符号小数除法通用程序没有保留余数,商保存在变量temp3中。举一个例子,当temp1=2cccH(十进制的0.35),temp2=55c2H(十进制的0.67),两数相除的结果为temp3=42dcH(十进制的0x42dc0.52233)。四、实验条件PC机, DES5402PP-U实验系统(若使用,需要将CCS配置为硬件仿真器)五、实验步骤本实验需要使用C54X汇编语言实现加、减、乘、除的基本运算,并通过DES的存贮器显示窗口观察结果。实验分两步完成:(1).编写实验程序代码本实验的汇编源程序代码主要分为六个部分:加法、减法、整数乘法、小数乘法、整数除法和小数除法。每个部分后面都有一条需要加断点的标志语句:nop 当执行到这条加了断点的语句时,程序将自动暂停。这时你可以通过“存贮器窗口”检查计算结果。当然你看到的结果都是十六进制的数。 (2).在simulator上调试运行,并观察结果 在完成实验程序代码的输入,并在CCS集成开发环境采用编译器对各模块进行编译并连接后,就可以在simulator上调试运行。步骤如下:a. 将CCS配置为C5402 simulator,启动CCS。b. 新建工程exer1.prj,将编写的主程序文件、CMD文件、中断向量表添加到工程,对各模块进行编译,然后rebuild,生成.out输出文件。c.在CCS界面单击菜单栏File下面的“Load”选项,并在弹出的File Name对话框中选择Debug文件夹下面的exer1.out装入基本算术运算实验程序,这时应能在“反汇编”窗口看到程序代码。d. 用鼠标选中“Memory”窗口,并在其中选择要查看的存贮器地址段:0x0800x08e。e. 在反汇编窗口中在每个“nop”指令处都设一个断点,方法有两种:1.用鼠标单击该指令将其点亮即可。2.在菜单栏中选择“Break”Add”,然后在弹出的对话框中键入欲加断点的地址即可。f. 单击菜单栏下的“Run=F5”按钮,启动执行基本算术运算程序,程序在执行完加法运算后自动暂停。通过“CPU”窗口可以看到寄存器AHL的内容为0x46,这正是加法运算的结果。同样,在“Memory”窗口中,可以看到0x81,0x82,0x88的内容为分别为0012,0034,0x46。执行加法运算后,将0x81和0x82的内容相加,结果放在0x88单元。g. 在“Memory”窗口中用鼠标左键双击0x81单元,这时可以修改该内存单元的内容。输入新的数据0x0ffee(十进制的-18),编辑内容时请直接输入FFEE(十六进制),然后回车确认,便完成对0x81单元的修改。h. 在“CPU” 窗口中修改PC值,方法也是鼠标左键双击PC寄存器的内容,输入新的PC值0x1805(编辑内容时直接输入1805),并用回车键确认。i. 单击菜单栏下的“Run=F5”按钮,程序从当前PC继续运行,重新计算0x81和0x82的和,结果在0x88中。当程序再次暂停时,可以看到AHL寄存器和0x88的内容为0x22(十进制的34),这正是我们希望的结果:-18+52=34。 j. 单击“Run=F5”按钮,程序从当前PC继续运行,完成减法运算。当程序再次暂时(断点位于0x1813),可以看到0x83和0x84单元的内容分别为FFEE和0012,B寄存器的内容为ffdc0000,而0x89的内容为ffdc(十进制-36),这正是我们希望的结果:。注意,该减法操作使用了辅助寄存器寻址,所以计算结果在B寄存器的高16位。 k. 单击“Run=F5”按钮,程序从当前PC继续运行,完成整数乘法运算。当程序再次暂时(断点位于0x181d),可以看到0x81和0x82单元的内容分别为0012和0034,A寄存器的内容为000003A8,这正是我们希望的结果:18*52=936(0x3a8)。这时我们可以用1个16位的内容单元来保存结果,如将A寄存器的低16位存入0x8b单元。但如果将0x81的内容修改为0x2000(十进制的8192),在“CPU窗口”中将PC修改为1818,然后继续运行,重新计算乘法。当程序完成乘法暂停时,可以看到A寄存器的内容为00068000,这也是一个正确的结果:8192*52=425984(0x68000)。此时将无法用一个16位的存贮单元来保存A寄存器中的结果。l. 单击“Run=F5”按钮,程序从当前PC继续运行,完成小数乘法运算。当程序再次暂停时(断点位于0x1826),可以看到0x83和0x84单元的内容分别为4000和b548,A寄存器的内容为40000000,乘法的结果在B寄存器中为daa40000,这正是我们希望的结果:0.5*(-0.58374)=-0.29187(0x0daa4)。对于小数乘法,一般情况都可以用1个16位的内容单元将B寄存器的高16保存(如存入0x8c单元)。m. 单击“Run=F5”按钮,程序从当前PC继续运行,完成整数除法运算。当程序再次暂时(断点位于0x183b),可以看到0x81,0x82,0x8d和0x8e单元的内容分别为0034,0012,FFFE和0010,这正是我们希望的结果:52除以-18,商为-2(0xfffe) ,余数为16(0x10)。n. 单击“Run=F5”按钮,程序从当前PC继续运行,完成小数除法运算。当程序再次暂停时(断点位于0x1852),可以看到0x81,0x82和0x8f单元的内容分别为4000,4ab8和6da3,这正是我们希望的结果:0.5/0.58374=0.8565457(0x6da3)。o. 如果以上程序运行不正确,请检查代码是否输入正确,还可以在源代码中插入断点调试,注意对中间结果的观察。六、实验报告要求1、实验前进行预习,初步编写相应实验程序代码2实验时对实验代码进行调试,并不断修改达到正确结果;3写出本次实验的心得体会。七、思考题1、对直接寻址用法有什么体会?如果在直接寻址前遗漏对DP初始化,对结果有什么影响?2、在小数乘法中使用了置FRCT标志为1的指令。如果将该语句取消,那么B寄存器的结果是多少?想想什么时候应该设置FRCT标志?实验_2_:数字振荡器的设计与实现实验学时: 4实验类型:设计实验要求:必修一、实验目的通过本实验的学习,让学生掌握多模块程序设计方法,掌握定时器使用,掌握简单算法的DSP实现以及CCS环境下图形工具的简单应用。二、预习和参考(1)数字振荡器原理设一个传递函数为正弦序列sinkT,其z变换为 H(z)=其中,A=2cosT, B=-1, C=sinT。设初始条件为0,求出上式的反Z变换得: yk=Ayk-1+Byk-2+Cxk-1这是一个二阶差分方程,其单位冲击响应即为sinkT。利用单位冲击函数xk-1的性质,即仅当k=1时,xk-1=1,代入上式得: k=0 y0 = Ay-1 + By-2 + 0 = 0 k=1 y1 = Ay0 + By-2 + c = c k=2 y2 = Ay1 + By0 + 0 = Ay1 k=3 y3 = Ay2 + By1 . k=n yn= Ayn-1 + Byn-2在k2以后,yk能用yk-1和yk-2算出,这是一个递归的差分方程。 根据上面的说明,我们可以开始数字振荡器的设计。设该振荡器的频率为2kHz,采样率为40kHz(通过定时器设置,每隔25us中断一次,即产生一个yn),则递归的差分方程系数为: A=2cosT=2cos (2 x PI x 2000 / 40000)=2 x 0.95105652 B=-1 C=sinT=sin (2 x PI x 2000 / 40000)=0.30901699为了便于定点DSP处理,我们将所有的系数除以2,然后用16位定点格式表示为:这便是本实验中产生2KHz正弦信号的三个系数。在本实验中,主程序在初始化时先计算出y1和y2,然后开放定时器中断。以后每次进入定时器中断服务程序时,利用前面的y1和y2,计算出新的有y0,通过CCS提供的图形显示工具,我们将在图形窗口中看到一个正弦信号波形。下面是初始化和中断服务程序代码片段:初始化y1和y2:ssbxFRCT;置FRCT=1,准备进行小数乘法运算st#INIT_A,AA;将常数A装入变量AAst#INIT_B,BB;将常数B装入变量BBst#INIT_C,CC;将常数C装入变量CCpshdCC;将变量CC压入堆栈popdy2;初始化y2=CCldAA,T;装AA到T寄存器mpyy2,a;y2乘系数A,结果放入A寄存器stha,y1;将A寄存器的高16位存入变量Y1中断服务程序片段:ldBB,T;将系数B装入T寄存器mpyy2,a;y2乘系数B,结果放入A寄存器ltdy1;将y1装入T寄存器,同时复制到y2macAA,a;完成新正弦数据的计算,a寄存器中为; y1*AA+y2*BBstha,1,y1;将新数据存入y1,因所有系数都除过2,;所以在保存结果时转移一位,恢复数据正常大小。stha,1,y0;将新正弦数据存入y0 (2)C54X的定时器操作 C54X的片内定时器利用CLKOUT时钟计数,用户使用三个寄存器(TIM,PRD,TCR)来控制定时器,参见表2-1。在表2-2中列出了定时器控制寄存器的各个比特位的具体定义。VC5402的另一个定时器(定时器1)的控制寄存器分别为:0x30(TIM1),0x31(PRD1),0x32(TCR1)。 表2-1 VC5402定时器0的相关寄存器寄存器地址名称用途0024hTIM定时器寄存器,每计数一次自动减10025hPRD定时器周期寄存器,当TIM减为0后,CPU自动将PRD的值装入TIM0026hTCR定时器控制寄存器表2-2 定时器控制寄存器(TCR)bit概要比特 名称 功 能15-12 保留 读出时为011 Soft 该比特位与10位配合使用以决定定时器在使用仿真调试时状态。 Soft=0 当进入仿真调试时,定时器立即停止工作。 Soft=1 当计数器被减为0后,停止工作。10 Free 该位与11位配合使用以决定定时器在使用仿真调试时状态。 Free=0 根据11比特位决定定时器状态。 Free=1 忽略11比特位,定时器不受影响。9-6 PSC 定时器预置计数器。当PSC减为0后,CPU自动将TDDR装入,然后TIM开始减1。5 TRB 定时器复位。当TRB=1时,CPU将PRD寄存器的值装入TIM寄存器,将TDDR的值装入PSC4 TSS 定时器启停控制位。当系统复位时,TSS被清除,定时器立刻开始工作。 TSS=0 表示启动定时器 TSS=1 表示停止定时器0-3 TDDR 定时器扩展周期。当PSC减到0后,CPU自动将TDDR的值装入PSC,然后TIM减 1。所以整个定时器的周期寄存器可以有20个比特(PRD+TDDR)。 从上面的介绍可以看到定时器实际上可以有20个比特的周期寄存器。它对CLKOUT信号计数,先将PSC减1,直到PSC为0,然后用TDDR重新装入PSC,同时将TIM减1,直到TIM减为0。这时CPU发出TINT中断,同时在TOUT引脚输出一个脉冲信号,脉冲宽度为CLKOUT一致。然后用PRD重新装入TIM,重复下去直到系统或定时器复位。因而定时器中断的频率由下面的公式决定: TINT的频率= 其中tc表示CLKOUT的周期。定时器当前的值可以通过读取TIM寄存器和TCR寄存器的PSC比特位得到。下面是本实验中初始化定时器的程序片段: stm#10h,TCR;停止定时器stm#2499,PRD;设置PRD寄存器值为2499,TINT中断频率为 ; Foutclk /(2499+1)= 100MHz/2500 = 40 KHzstm#20h,TCR; 重新装入TIM和PSC,然后启动定时器 (3)C54X中断的使用 在C54X中用户可以通过中断屏蔽寄存器IMR来决定开放或关闭一个中断请求。图2-1给出了C5402的IMR寄存器的各个比特位的定义。 图2-1 C5402的IMR寄存器其中,HPINT表示HPI接口中断,INT3-INT0为外部引脚产生的中断,TXINT和TRINT为TDM串口的发送和接收中断,BXINT0和BRINT0为BSP串口的发送和接收中断,TINT0为定时器0中断。在中断屏蔽寄存器IMR中,1表示允许CPU响应对应的中断,0表示禁止。当然要CPU响应中断,ST1寄存器中的INTM还应该为0(允许所有的中断)。当DSP响应中断时,PC指针指向中断向量表中对应中断的地址,进入中断服务子程序。中断向量表是C54X存放中断服务程序的一段内存区域,大小为80H。在中断向量表中,每一个中断占用4个字的空间,一般情况是将一条跳转或延时跳转指令存放于此。当然,如果中断服务程序很短(小于或等于4个字),可以直接放入该向量表。中断向量表的位置可以通过修改基地址来改变,其基地址由PMST寄存器中的IPTR(15-7 bits)决定。中断向量表的各中断的偏移说明以及中断向量地址的形成请参考教材以及教材附录部分。例如C54x复位后其IPTR全为1,复位中断的偏移量为0,所以中断向量表起始位置在0FF80H,因而复位后程序从0FF80H开始运行。本实验的初始化程序读取中断向量表的启始地址,然后设置PMST的高9位,以便DSP能正确响应中断,代码如下: ld #0,dp;设置DP页指针 ssbx intm;关闭所有中断 ld #vector, a;读出中断向量(地址vector在中断向量表程序中定义) and #0FF80h, a;保留高9位(IPTR) andm #007Fh, pmst;保留PMST的低7位 or pmst, a; stlm a, pmst;设置PMST(其中包括IPTR)三、实验要求基于DSP的定时器产生2KHz正弦波(采样率为40KHz或者自定义,但必须满足采样定理),采样CCS图形查看工具查看产生波形及其频谱图。四、实验条件PC机, DES5402PP-U实验系统五、调试及结果测试本实验需要使用C54X汇编语言或C语言实现数字振荡器,并通过CCS提供的图形显示窗口观察输出信号波形以及频谱。实验分下面几步完成: (1).根据确定数字振荡器的频率,计算并确定系数。 (2)启动CCS,新建工程文件,如文件名为sinewave.prj。选择Project菜单中的Add File to Project选项,将所编写的汇编源程序exer2.asm、vec_table.asm和连接命令sinewave.cmd文件依次添加到工程文件中。注意,你可以在添加文件对话框中选择显示不同的文件类型来加快文件选择速度。你也可以使用鼠标右键单击工程文件名(如sinewave.prj)并选择Add Files项来添加需要的文件。其中,exer2.asm包括初始化代码和中断服务程序,而vec_talbe.asm包含中断向量表。 (3)选择Project菜单中的Options选项,或使用鼠标右键单击工程文件名(如sinewave.prj)并选择Options项来修改或添加编译、连接中使用的参数。例如,选择Assembler窗口,选择“Enable Symbolic Debug Infomation”以便使用汇编源代码级调试(你可以在汇编源程序设置断点等等)。选择Linker窗口,在“Output Filename”栏中写入输出OUT文件的名字,如sine.out,你还可以设置生成的MAP文件名。 (4)完成编译、连接,正确生成OUT文件。然后使用File菜单的“Load Program”选项,将生成的OUT文件(如sine.out)装入DSP的片内存储器。这时CCS将显示程序的启始地址_c_int00。 (5)选ViewGraphTime/Frequency打开图形显示设置窗口。在弹出的对话框中按图2-2设置所示,主要修改“Start Address”为y0(y0为生成的正弦波输出变量);“Acquisition Buffer Size”为1,“DSP Data Type”为“16-bit signed integer”。图2-2 CCS图形查看工具设置(6)在汇编源程序的中断服务程序(_tint)中的“nop”语句处设置断点。该行被加亮为洋红色。选择DebugAnimate,运行程序,观察输出波形。数一数一个周期的正弦波有多少个点?算算频率是否是2kHz?另外,想想Run和Animate两种运行方式的区别? (7)用右键单击图形显示窗口,并选择“Proporties”项以便修改显示属性。将“Display Type”项改为“FFT Magnitude”以便显示信号频谱。修改“Sampling Rate(Hz)”项为40000,然后退出。注意观察生成的正弦波频率。 (8)清除所有断点,关闭除波形显示窗口外的所有窗口,并关闭工程文件。(9)下面我们使用C语言完成本实验。新建一个工程文件,如sinewave_c.prj,并添加所编写的timer.c,vec_table.asm源程序,再添加timer.cmd,再添加C使用的标准库rts.lib。该文件应该在CCS安装目录中。例如,若CCS安装在d:ti下,则rts.lib应该在d:tic5400cgtoolslib下。修改编译、连接选项,加入符号调试选项,修改生成的OUT文件名,如timer.out。 (10).完成编译、连接,正确生成OUT文件。然后使用File菜单的“Load Program”选项,将生成的OUT文件(如timer.out)装入DSP的片内存储器。这时CCS将显示程序的启始地址_c_int00。 (11). 打开C源程序(timer.c)窗口,在中断服务程序(函数tint())的“con_buf=0;”语句处增加一个断点。同样打开图形显示窗口,并将“Start Address”改为buf;“Acquisition Buffer Size”改为128,“Display Data Size”改为128,“DSP Data Type”为“32-bit floating point”。(12)选择DebugAnimate,运行程序,观察输出波形。数一数一个周期的正弦波有多少个点?算算频率是否是2kHz?同样用右键单击图形显示窗口,显示信号频谱。注意修改“Sampling Rate(Hz)”项为40000,然后退出。注意观察生成的正弦波频率。六、实验报告要求1、预习报告分析采用数字信号处理方法产生正弦波原理,复习定时器工作原理及中断控制方法,考虑主程序、中断向量表以及CMD模块的编写。2、实习记录根据实习步骤,记录实验结果图形,考虑显示图形的设置。3、实验报告(1)汇出实验结果信号曲线图及其频谱图。(2)进行本次实验总结。七、思考题(1)本实验程序产生了一个2kHz的正弦信号,请修改程序,产生一个频率相同的余弦信号。为了验证产生的COS信号,可以同时生成SIN和COS信号,然后在两个图形窗口中显示波形。它们应该正好相差p/2相位。(1) 重新设计和实现一个数字振荡器,采样频率改为为20KHz,输出正弦信号的频率为4KHz。(2) 使用探针工具,用文件保存产生的正弦波数据。(4)在(1)题的基础上,新建一个工程文件,使用VC5402的定时器1产生COS信号,同时使用定时器0产生SIN信号。(5)在CCS中打开连接定位文件sinewave.cmd,看看中断向量表是如何安排的?并使用MAP文件验证中断向量表的具体地址。实验三: BSP串口通信实现 实验学时: 4实验类型:综合实验要求:必修一、实验目的1、本实验的主要目的是学习C54xx的McBSP串口的控制和使用,并利用VC5402的McBSP1串口实现数据的收发。2、学会编写串口通信程序,包括串口的初始化和发、送中断服务程序的编写。二、相关知识点串口结构与工作原理、包括串口的初始化和发、送中断服务程序的编写三、实验原理、方法和手段(1)McBSP概述 McBSP与外设进行数据传输是通过(DX)脚来发送,(RX)脚来接收,通信的时钟与帧信号是由CLKX, CLKR, FSX, and FSR脚来控制。DSP的CPU或DMA从数据接收寄存器(DRR1,2)读取接收数据,发送时向数据发送寄存器(DXR1,2)写数据。数据写入(DXR1,2)后通过传输移位寄存器(XSR1,2) 移位输出到DX上,同样,从DR上接收的数据移位存储到接收移位寄存器(RSR1,2) 并拷贝到接收缓存寄存器(RBR1,2) ,然后,再由(RBR1,2)拷贝到DRR1,2,DRR1,2就可以由CPU或DMA来读出。多级寄存器允许在通信时内部和外部数据同时传输。C54XX对McBSP的控制由16位的控制寄存器实现。(2) McBSP控制寄存器 在图3-1中给出了McBSP串口的所有控制寄存器。本实验使用VC5402的McBSP1串口,下面的说明以McBSP1为例。McBSP每个串口实际占用6个物理地址空间,例如McBSP1串口中数据发送寄存器为两个(32bit),地址分别为0x42和0x43。本实验通过0x43发送数据(16bit)。数据接收寄存器为两个(32bit),地址分别为0x40和0x41。本实验通过0x41读取串口接收数据(16bit)。控制寄存器占用两个地址:0x48和0x49,而McBSP串口控制寄存器总共有14个,所以在访问这些控制寄存器时,先将要访问的寄存器编号(子地址)写入地址寄存器寄存器0x48,然后在将数据写入0x49或从0x49读出相应的数据。若要访问另一个控制寄存器,又得些修改地址寄存器。串口控制寄存器1的详细说明(SPCR1):子地址 - 0x0 SPCR1设置McBSP串口的数字环回模式、 接收符号扩展和校验模式、Clock Stop模式、DX是否允许、A-bis 模式、接收中断模式等,并给出接收同步错误、接收移位寄存器(RSR1,2)空、接收准备好等状态。本实验RJUST = 01 ,即接收数据不足16BIT时采用右对齐且符号位扩展方式,另外接收中断由RRDY信号RINTM=00。DLB = 0表示不使用数字环路。CLKSTP = 0X 表示时钟停止模式,用于非SPI模式。DXENA = 0 表示禁止延时发送。ABIS = 0表示不使用A-bis模式。RSYNCERR = 0 表示不检测同步错误。该寄存器初始化值为0x2000。在启动串口接收工作前应将RRST为置1,即该寄存器为0x2001。图3-1 McBSP串口控制寄存器图3-2 串口控制寄存器1(3) 串口控制寄存器2的详细说明(SPCR2):子地址 - 0x1 SPCR2设置McBSP自由运行模式、SOFT 模式、发送中断模式,并给出发送同步错误、发送移位寄存器(XSR1,2)空、发送准备好等状态。此外可以进行发送复位、采样率发生器复位、帧同步发生电路复位。本实验中FREE = 0 ,SOFT = 1 表示若使用仿真器调试时串口在发送完当前字后暂停工作。若连续运行,这两个BIT位没有影响。FRST = 0表示帧同步发生器复位,该BIT位工作时应设为1。GRST =0表示采样率发生器(即串口工作的时钟)电路复位,工作中若该串口需要提供时钟信号时,应设置为1。XINTM = 00表示串口的发送中断由XRDY产生。XSYNCERR = 0表示不检测同步错。该寄存器初始化值为0x100。当串口工作时,应将XRST为置1,即该寄存器为0x1c1。图3-3 串口控制寄存器2(5) 引脚控制寄存器的详细说明(PCR):子地址 - 0x0e PCR设置McBSP传输帧同步模式、接收帧同步模式、发送时钟模式、接收时钟模式、发送帧同步信号的极性、接收帧同步信号的极性、发送时钟极性、接收时钟极性,并给出CLKS、DX、DR脚的状态。此外PCR还定义发送和接收部分在复位时相应引脚是否配置为通用 I/O。本实验中,XIOEN和RIOEN = 0表示DX,FSX,CLKX,DR,FSR,CLKR,CLKS都配置为串口而非通用I/O引脚。FSXM = 1表示发送帧同步由采样率发生器产生(请参考SRGR2寄存器的FSGM位)。FSRM = 0 表示接收帧同步由外部提供,因为DES5402PP实验板的FSXM与FSRM相连。CLKXM = 1 表示发送时钟由内部采样率发生器产生。CLKRM = 0 表示接收时钟由外部提供,同样因为CLKRM与CLKXM连在一起。FSXP = 1 表示发送帧同步低有效。FSRP = 1 表示接收帧同步低有效。CLKXP = 1 表示CLKX的上升沿发送数据, CLKRP = 0 表示CLKR的下降沿接收数据。该寄存器初始化值为0x0a0e。图3-4 串口引脚控制寄存器PCR(6) 接收控制寄存器1(RCR1)说明:子地址 - 0x02RCR1设置McBSP接收时第一相(FIRST PHASE)的接收帧长度(从1个字到128个字、接收字长度(8、12、16、20、24、32bits)。本实验中设置位每帧1个字,字长16 bits。初始值为0x0040。图3-5 串口接收控制寄存器1(7) 接收控制寄存器2(RCR2)说明:子地址 - 0x03 RCR2设置McBSP接收时是否允许第二相(RPHASE=1)。如果允许,设置McBSP接收时第二相的接收帧长度(从1个字到128个字、接收字长度(8、12、16、20、24、32bits)。此外, RCR2设置McBSP接收时的接收压缩模式、接收同步帧忽略模式、接收数据延迟。在本实验中,RPHASE = 0 表示只使用单相帧,RCOMPAND = 00表示接收数据不压扩,且高位在前,RFIG = 0 表示不忽略接收帧同步信号。该寄存器初始化设置为0x0040或0x0。图3-6 串口接收控制寄存器2 (8) 发送控制寄存器1(XCR1)说明:子地址 - 0x04 XCR1设置McBSP发送时第一相(FIRST PHASE)的发送帧长度(从1个字到128个字、发送字长度(8、12、16、20、24、32bits)。本实验中设置位每帧1个字,字长16 bits。初始值为0x0040。图3-7 串口发送控制寄存器1(9) 发送控制寄存器2(XCR2)说明:子地址 - 0x05 XCR2设置McBSP发送时是否允许第二相(XPHASE=1)。如果允许,设置McBSP时第二相的发送帧长度(从1个字到128个字、发送字长度(8、12、16、20、24、32bits)。此外, XCR2设置McBSP发送时的发送压缩模式、发送同步帧忽略模式、发送数据延迟。本实验不允许使用第二相(XPHASE=0),初始设置为 0x0。图3-8 串口发送控制寄存器2(10)采样率发生器(串口时钟产生)寄存器SRGR1:子地址 - 0x06 采样率发生器寄存器1(SRGR1)设置帧正脉冲宽度和数据位时钟分频( CLKG与输入CLK频率之比,约定值为1)。本实验中虽然将FWID设置为1,即帧同步脉冲宽度=2,但被忽略了(参见后面帧同步发生控制寄存器设置)。时钟分频寄存器=200(0xC8),表示设置串口时钟为CLKG=100M /200=500K Hz。本实验中设置为0x1c8。图3-9 串口采样率控制寄存器1(11) 采样率发生器(帧同步信号产生)控制寄存器SRGR2:子地址 - 0x07 采样率发生器寄存器2(SRGR2)设置采样率发生器时钟同步模式、CLKS的极性、采样率发生器输入时钟选择、帧周期分频。本实验中,GSYNC=0 表示采样率发生器是否同步,因CLKSM=1,固该bit不用。CLKSP = 0表示 CLKS的上升沿产生CLKG和FSG。因CLKSM=1该BIT也不用。CLKSM = 1表示采样率发生器由CPU时钟驱动。FSGM = 0表示帧同步信号由发送位移寄存器自动产生,忽略FPER和FWID,固FPER =0。所以该寄存器初始化值为0x2000。图3-10 串口采样率控制寄存器2(12)串口的初始化 本实验的串口初始化包括两个部分:串口收发中断的设置和串口寄存器的初始化。根据前面的介绍,DES5402PP实验板的串口1设置为单相帧,字长为16bit,发送CLOCK由内部CPU时钟产生,频率为500KHz,并输出。同时串口接收时钟也使用该信号。发送帧同步信号由发送位移寄存器自动产生,同时也提供给串口接收电路。具体设置参见下面的代码:;*; The following codes are used to initalize McBSP1 !; When Transmit, this DES5402PP makes CLK,FS ! the other; DES5402PP receives the CLK,FS ! ;* stm #0,MCBSP1_SPSA ; choose SPCR11 stm #2000h,MCBSP1_SPSD; re
展开阅读全文