DSP5416的串口通信的设计.docx
《DSP5416的串口通信的设计.docx》由会员分享,可在线阅读,更多相关《DSP5416的串口通信的设计.docx(17页珍藏版)》请在冰豆网上搜索。
DSP5416的串口通信的设计
摘要:
本实验采用美国TI公司TMS320C5416DSP芯片和MAXIM公司的MAX3111异步串行收发器,以SPI方式进行直接接口,实现同步到异步RS-232数据的传输的转换。
给出硬件连接原理图和相关的软件编程方法。
关键词:
MAX3111串口通信 DSP5416
一序言:
本次设计题目主要是进一步掌握同步串口McBSP的结构及工作原理,学习DSP实现RS232串口通讯的程序设计,学习MAX3111与DSP的接口设计。
近年来,DSP在电子、通信和控制领域得到了非常广泛的应用,在DSP应用系统设计中与上位机和下位机的通信必不可少。
串口通信作为重要的通信方式之一,优点就是接口需要的引脚少,结构简单易于实现。
本文介绍了TMS320C5416多通道缓冲口,并通过具体的实例介绍说明利用串口进行DSP通信的具体实现。
二McBSP的接口信号及工作过程
McBSP由一个数据通道和一个控制通道组成,如图1所示。
不同的接受和发送引脚实现和外部器件之间的通信。
McBSP的接收操作采用三级缓冲方式,发送操作采用两级缓冲方式。
数据发送引脚(DX)负责数据的发送,数据接受引脚负责数据的接受,另外五个引脚(CLKS,CLKX,CLKR,FSX和FSR)提供了控制信号(时钟和帧同步)接口。
C5416CPU通过片内的外设总线访问串口的32位控制寄存器,从而实现与McBSP间的通信与控制。
接受的数据到达DR引脚后移位到RSR,一旦整个数据单元接受完毕,如果RBR寄存器未满,则RSR被复制到RBR中。
如果DRR中的数据已经被CPU/DMA控制器读取,则RSR被将被复制到DRR中。
发送数据首先由CPU或DMA控制器写入DXR中。
如果XSR寄存器为空,则DXR中的值被复制到XSR并准备移位输出,否则,DXR会等待XSR中旧数据的最后一位被移位输出到DX引脚后,才将数据复制到XSR中。
三McBSP与SPI设备的接口
SPI(SeriesProtocolInterface)是一个利用4根信号线的串行接口协议,包括主从两种模式。
4个接口信号分别是:
串行数据输入(MISO,设备输入,从设备输出)、串行数据输出(MOSI,主设备输出,从设备输出),移位时钟(SCK)、低电平有效的从设备使能信号(SS)。
SPI的最大特点是由主设备时钟信号的出现与否来确定主从设备间的通信。
一旦检测到主设备时钟信号,数据开始传送,时钟信号无效后,传输结束。
在这期间,要求从设备必须被使能(SS信号保持有效
)。
1McBSP为SPI主设备的接口
图1:
McBSP为SPI主设备时的接口
当McBSP为SPI的主设备时,由McBSP内部的采样发生器产生时钟CLKX和从设备使能信号FSX。
3.2McBSP为从设备接口
图2McBSP为从设备时的接口
当McBSP作为SPI从设备时,由外部的主设备产生所需要的主控时钟信号和从设备使能信号。
四McBSP为主设备时的串口通信电路设计
1MAX3111功能特点
MAX3111是MAX3100的改进类型,它包括一个振荡器和一个可编程波特率发生器;具有一个可屏蔽的中断源;另具有一个8字节的接收FIFO(先入先出)缓冲器。
其应用SPI/MICROWIRE接口技术直接与控制器之间进行通信,通信速率可达230kbps,还包括两个RS-232电平转换器,这样无需再接入电平转换器,而使应用一个芯片即可实现具有SPI/MI-CROWIRE接口的微控器与PC或是其他设备进行异步数据传输。
2TMS320C5416与MAX3111硬件接口设计
TMS320C5416DSP的McBSP串行接口工作于SPI模式时可直接与MAX3111进行连接(MAX3111为3.3V器件的特性方便了于C5400系列DSP芯片进行接口),从而实现与RS-232设备进行异步数据传输,此时TMS320C5416作为SPI协议的主设备,其接口电路如图3所示。
图3:
DSP串口通信电路图
DSP的发送时钟信号(CLKX)作为MAX3111的串行时钟输入,发送帧同步脉冲信号(FSX)作为MAX3111的片选信号(CS)。
DX与DIN连接作为发送数据线,DR与DOUT连接为接收数据线。
MAX3111的DX与DIN连接,DX与DOUT连接,从而利用其片内的转换器实现UART到RS-232电平的转换。
由于SPI模式下的MCBSP并不能产生接受中断,因此MAX3111的中断信号(IRQ)与DSP的外部中断相连。
五软件流程图(附程序)
主程序软件流程图如下图所示。
图4:
主程序流程图
六软件硬件联调
把程序烧录到DSP芯片内,然后运行机房电脑里的串口调试工具,设置好端口和参数。
运行程序结果:
(1)按下键2,PC机向DSP处理器发送数据
(2)按下键1,DSP处理器向PC机发送数据,连续递增加1显示
经分析:
实验结果与我们理论设计结果相同,本实验圆满完成。
七总结与展望
课程设计是培养学生综合运用所学知识,发现,提出,分析和解决实际问题,锻炼实践能力的重要环节,是对学生实际工作能力的具体训练和考察过程.回顾起此次DSP原理及应用的课程设计,至今我仍感慨颇多,从理论到实践,在整个实验的过程中,可以说得是苦多于甜,但是可以学到很多很多的的东西,同时不仅可以巩固了以前所学过的知识,而且学到了很多在书本上所没有学到过的知识。
通过这次课程设计使我懂得了理论与实际相结合是很重要的,只有理论知识是远远不够的,只有把所学的理论知识与实践相结合起来,从理论中得出结论,才能真正为社会服务,从而提高自己的实际动手能力和独立思考的能力。
在设计的过程中遇到问题,可以说得是困难重重,这毕竟是第一次综合应用DSP技术来做设计,难免会遇到过各种各样的问题,同时在设计的过程中发现了自己的不足之处,对以前所学过的知识理解得不够深刻,掌握得不够牢固……通过这次毕业设计之后,可以把以前所学过的知识重新温故。
这次毕业设计终于顺利完成了,在设计中遇到了很多问题,最后在老师的辛勤指导下,同学的帮助下终于迎刃而解。
在此我表示感谢!
八参考文献
[1]DSP原理及应用[M],邹彦:
电子工业出版社.
[2]张雄伟,曹铁男.DSP芯片的原理与开发应用(第2版)[M].北京:
电子工业出版社,2000.
[3]张毅刚,赵光权,孙宁,等.TMS320LF2812DSP原理,开发与应用[M].哈尔滨:
哈尔滨工业大学出版社,2006.
附录
附录一:
串口中断软件流程图
图5:
串口中断软件流程图
附录二:
定时器中断软件流程图
图6:
定时器中断软件流程图
附录三:
外部中断2软件流程图
图7:
外部中断2中断软件流程图
附录四:
源程序
#include
#pragmaCODE_SECTION(vect,"vect")
unsignedint*pmem=0;
#define IMR *(pmem+0x0000)
#define IFR *(pmem+0x0001)
#define PMST *(pmem+0x001d)
#define SWCR *(pmem+0x002b)
#define SWWSR *(pmem+0x0028)
#define CLKMD *(pmem+0x0058)
#define PRD0 *(pmem+0x0025) //timer0periodregister
#define TCR0 *(pmem+0x0026) //timer0controlregister
/*mcbsp1*/
#defineSPSA1 *(pmem+0x0048) //子地址寄存器
#defineSPSD1 *(pmem+0x0049) //
#defineDRR11 *(pmem+0x0041) //接收数据寄存器1
#defineDRR21 *(pmem+0x0040) //接收数据寄存器2
#defineDXR11 *(pmem+0x0043) //发送数据寄存器1
#defineDXR21 *(pmem+0x0042) //发送数据寄存器2
/*mcbsp1subadress*/
#defineSPCR11 0x0000 //串行口控制寄存器1
#defineSPCR21 0x0001 //串行口控制寄存器2
#defineRCR11 0x0002 //接收控制寄存器1
#defineRCR21 0x0003 //接收控制寄存器2
#defineXCR11 0x0004 //发送控制寄存器1
#defineXCR21 0x0005 //发送控制寄存器2
#defineSRGR1 0x0006 //采样率发生寄存器1
#defineSRGR2 0x0007 //采样率发生寄存器1
#definePCR1 0x000e //引脚控制寄存器
ioportunsignedportc000; //数码管地址
ioportunsignedportc001; //键盘地址
ioportunsignedportc002; //发光二极管地址
intnum=0;
intn=0;
staticintTmcounter;
staticconstchartable[10]={"1234567890"};
staticintweima[8]=
{0x0100/*1*/,0x0200/*2*/,0x0400/*3*/,0x0800/*4*/,
0x1000/*5*/,0x2000/*6*/,0x4000/*7*/,0x8000/*8*/};
staticintduanma[16]=
{0x003f/*0*/,0x0006/*1*/,0x005b/*2*/,0x004f/*3*/,
0x0066/*4*/,0x006d/*5*/,0x007d/*6*/,0x0007/*7*/,
0x007f/*8*/,0x006f/*9*/,0x0077/*a*/,0x007c/*b*/,
0x0039/*c*/,0x005e/*d*/,0x0079/*e*/,0x0071/*f*/};
voiddelay() //WAIT
{
asm("STM#0008h,AR0");
asm("RPT*AR0");
asm("NOP");
}
voiddelay10ms()
{
int i,j,k;
for(i=0;i<2;i++)
for(j=0;j<2;j++)
for(k=0;k<2;k++);
}
voiddelay100ms()
{
int i,j,k;
for(i=0;i<14;i++)
for(j=0;j<12;j++)
for(k=0;k<20;k++);
}
voidcpu_init() //初始化DSP
{
asm("ssbxintm");
asm("ssbxxf");
PMST=0xe8;
SWWSR=0x7fff;
SWCR=0x0000;
CLKMD=0x1000;
TCR0=0x0a59;
PRD0=0xf9f;
IMR=0x0c0c; //开放mcbsp1发送中断、mcbsp1接收中断、外部中断2、定时器0中断
IFR=0xffff;
asm("rsbxintm");
asm("rsbxxf");
}
voidmcbsp_init()
{
SPSA1=SPCR11; //SerialPortControlRegister1
SPSD1=0x1800; //1800
SPSA1=SPCR21; //SerialPortControlRegister2
SPSD1=0x0000; //0000
SPSA1=RCR11; //ReceiveControlRegister1
SPSD1=0X40; //0040
SPSA1=RCR21; //ReceiveControlRegister2
SPSD1=0x01; //0001
SPSA1=XCR11; //TransmitControlRegister1
SPSD1=0x40; //0040
SPSA1=XCR21; //TransmitControlRegister2
SPSD1=0x01; //01
SPSA1=SRGR1; //SampleRateGeneratorRegister1
SPSD1=0x0000; //0000
SPSA1=SRGR2; //SampleRateGeneratorRegister2
SPSD1=0x2000; //2000
SPSA1=PCR1; //PinControlRegister
SPSD1=0x0a08;
DXR11=0x000;
SPSA1=SPCR11; //SerialPortControlRegister1
SPSD1=0x1801; //1800
SPSA1=SPCR21; //SerialPortControlRegister2
SPSD1=0x0041; //0000
}
voidaic_init()
{
DXR11=0xcc0b; //9600enablereceiveddatainterrupt
//低四位决定波特率
}
voidmain(void)
{
cpu_init();
mcbsp_init();
aic_init();
Tmcounter=0;
for(;;){}
}
interruptvoidrs232()
{
intrxdata;
intvalue;
DXR11=0x00; //向MAX3111写入0x00,即最高两位为00,表示DSP要从MAX3111读数据
rxdata=DRR11; //从数据接收寄存器DRR读出数据
if(rxdata&0x8000) //若读到的数据最高位R为1,则表示数据信息可被读取
{
value=rxdata&0x00ff; //传送的数据存放在16位数的低八位
if(value>15)
value=15;
portc000=weima[n]|duanma[value];
n++;
if(n>7)n=0;
}
}
interruptvoidtint0()
{
intrxdata,txdata,value;
if(Tmcounter==250)
{
Tmcounter=0;
DXR11=0x00;
rxdata=DRR11;
if(rxdata&0x4000) //若读到的数据?
,则表示?
,已准备好接收数据
{
value=table[num];
txdata=value&0x00ff; //
DXR11=0x8000|txdata; //写数据
num++;
if(num==10)
{
num=0x0;
DXR11=0xc40b; //写控制字,且TM为0,表示禁止MAX3111发送缓冲器的空中断
}
}
}
Tmcounter++;
}
interruptvoidKeyDown()
{
inta;
a=portc001;
a=a&0xff00;
if(a!
=0xff00)
{
delay10ms();
a=portc001;
a=a&0xff00;
if(a==0xfe00) //当按键1按下时,开始定时,关mcbsp1接收中断
{
IMR=0x080c;
TCR0=0x0a69;
}
elseif(a==0xfd00) //按键2按下时,停止定时,开mcbsp1接收中断
{
TCR0=0x0a59;
IMR=0x0c0c;
}
else;
}
}
void vect()
{
asm(".ref_c_int00");
asm(".ref_rs232");
asm(".ref_tint0");
asm("b_c_int00"); /*reset*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); //nmi
asm("nop");
asm("nop");
asm("nop");
asm("rete"); //
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete");
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*int0*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*int1*/
asm("nop");
asm("nop");
asm("nop");
asm("b_KeyDown");/*int2*/
asm("nop");
asm("nop");
asm("b_tint0");
asm("nop"); /*tint0*/
asm("nop");
asm("nop");
asm("rete"); /*brint0*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*bxint0*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*dmac2*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*tint1*/
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop"); /*int3*/
asm("nop");
asm("nop");
asm("rete"); /*hpint*/
asm("nop");
asm("nop");
asm("nop");
asm("b_rs232"); /*brint1*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*bxint1*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*dmac4*/
asm("nop");
asm("nop");
asm("nop");
asm("rete"); /*dmac5*/
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm("nop");
asm(".space29*4*16");
}