C8051F021 单片机串口通信问题

我想用C8051F021做串口通信,使用的晶振是11.0592MHz,波特率设置为4800Kbps,代码如下,问题是用串口助手无法收取数据。
#include "c8051f020.h"

unsigned char data1;
void SYSCLK_Init();
void PORT_Init();
void UART0_Init();

void SYSCLK_Init()
{
unsigned int i;
OSCXCN=0x67; //0X67=0110,0111
for(i=0;i<256;i++); //等待>1ms
while(!(OSCXCN&0x80)); //等待XTLVLD变为1
OSCICN=0x88; //时钟失效监测器,选择外部时钟源作为系统时钟
}
void PORT_Init()
{
XBR0 = 0x04; //URAT总线TX0置到P0.0口,RX0置到P0.1口
XBR1 = 0x00;
XBR2 = 0x40; //允许功能选择开关有效
P0MDOUT = 0x01; //P0.0(Tx)推挽方式 P0.1(Rx)和P0上的其余端口设置为漏极开路
}
void UART0_Init()
{
SCON0=0x50; //串口方式1 ,允许接收
TMOD =0x20; //选用定时器1作为波特率发生器
PCON =0x80; //SMOD0=1
TH1=0xF4; //时钟频率11.0592MHz,波特率为4800
TL1=0xF4;
TR1=1; //定时器1启动
ES0=1; //开启串口0中断
TI0=1; //声明TX0就绪,可以发送

}

void UART0_ISR() interrupt 4
{
if(RI0) //接收数据
{
RI0=0; //中断接收标志清零
data1=SBUF0; //接收数据,暂时存储在data1
SBUF0=data1; //发送数据
while(TI0==0);
TI0=0; //发送标志清零
}
}

main()
{ EA=0; //关 全局中断
WDTCN=0xDE; //禁用看门狗
WDTCN=0xAD;
SYSCLK_Init();
PORT_Init();
UART0_Init();
EA=1; //开全局中断

while(1);
}

在if(RI0)设置中断后,下一步直接就跳出了函数,RI0的值始终是0。请教大家是什么问题,解决后我会再加分。
我按照大家的方法试了,没有起作用。我想是不是串口0坏了,就直接用串口1吧,Tx接P2.0,Rx接P2.1。但向SBUF1里送0x50,数据还是会从P0.0口出来,我都没有使能Uart0EN,而且还把ES0=0。请帮我看下代码有问题吗?
void main (void)
{ ...
while(1)
{SBUF1=0x50;}
}
void PORT_Init (void)
{ XBR0 = 0x00;
XBR1 = 0x00;
XBR2 = 0x44;
P2MDOUT |= 0x01; }
void UART1_Init (void)
{
TR1=0;
EIE2&=~0x40; //清ES1为0
EIP2&=~0x40; //清PS1为0,Uart1中断为低优先级
SCON1 = 0x52; // SCON1: mode 1, 8-bit UART, enable RX
TMOD |= 0x20; // TMOD: timer 1, mode 2, 8-bit reload
TH1=0xF4;
TL1=0xF4; // init Timer1
PCON|=0x10;
// CKCON|=0x10; //TIM=1,使用系统时钟
EIE2= 0x40; // Enable UART1 interrupts
EIP2= 0x40; // Make UART high priority
TR1 = 1; // START Timer1

}

keil软仿串口无问题,查你的硬件吧。

如图:发68,回68。

你不会是没有电平转换就直连电脑了吧? 

修改:貌似图的分辨率太大了,看不到大图。

然后,这里有问题:

SBUF0=data1;  //发送数据

while(TI0==0);

TI0=0;   //发送标志清零

你这时刚刚把数据送到SBUF0里,TI0还是1(TI0上一次发送完,没有清0),而就算TI0是1,但你刚把数据送到SBUF0里,怎么可能为1呢?(TI0是发送“完成”中断标志),程序退出中断后,过一会(按4800波特率发完一个字节的时间)TI0才是1,然后你中断里又没有处理TI0为1的情况,所以程序会一直进中断,但不会有什么动作,除非是RI0为1.

温馨提示:答案为网友推荐,仅供参考
第1个回答  2010-12-08
建议发送程序不要放在中断里,如果在中断里现执行程序,又是发送完又进中断,容易出错
void sendchar(uchar ch)
{
SBUF=ch;
while(TI==0);
TI=0;
}
///////////送字符串///////
void sendstring(uchar *p)
{
while(*p)
{
sendchar(*p);
p++;
}
sendchar(0x0D);
sendchar(0x0A);
}
////////////串口中断,只是接收产生的,////////

void receive() interrupt 4 using 1
{
if(RI)
{
if(rx<rxin)
{
systembuf[rx]=SBUF;
rx++;
}
RI=0;
}
}
void main()
{
---------
sendstring(字符串)
-----------
}
第2个回答  2010-12-08
中断只接收数据
void UART0_ISR() interrupt 4
{
if(RI0) //接收数据
{
RI0=0; //中断接收标志清零
data1=SBUF0; //接收数据,暂时存储在data1
// SBUF0=data1; //发送数据
cansenddata=1;
// while(TI0==0);
// TI0=0; //发送标志清零
}
}
在主函数中发数据
while(1)
{
if(cansenddata)
{
cansenddata=0;
SBUF=ch;
while(TI==0);
TI=0;
}
}
第3个回答  2010-12-10
晶振分有源晶振和无源晶振,无源的晶振(crystal:晶体的意思)是两个脚的,接在单片机的晶振XTAL1,XTAL2上,并且在这两个脚上分别得接上起振电容,电容的另一端接地。
有源的晶振是四个脚的,有1:VCC 2:GND 3:NC(不连接) 4:输出,具体怎么排的忘记了,不要接起振电容,有源的比较贵,无源的一半都是1元,有源的要好几快呢。输出接到XTAL2上,XTAL1悬空

相关了解……

你可能感兴趣的内容

本站内容来自于网友发表,不代表本站立场,仅表示其个人看法,不对其真实性、正确性、有效性作任何的担保
相关事宜请发邮件给我们
© 非常风气网