单片机和PC通过串口通信
通信协议:每次PC向单片机发送10个字节的数据,第一个字节为0XFA,数据开始标志,后面8个字节为任意数据,最后一个字节为前9个数据和的低字节(高字节忽略),作为校验和。
串口设置:PC串口参数设置
串口号 : COM1(默认,具体视使用情况而定)
波特率 : 9600
数据位 : 8
其他默认
测试方法:可以用串口调试工具的字符串输入框输入:FA FA FA FA FA FA FA FA FA CA,选择HEX发送,HEX显示,如果每发送一次就接收到以上数据,并在单片机开发板上正确显示,则测试成功。
//52单片机串口接收和发送测试程序;
//接收采用中断方式,发送采用查询方式;
//52串口通信,T1做串口波特率发生器;
#include "Port_Config.h" //单片机端口定义
#include "LCD_Driver.h" //单片机LCD显示
#include "52_UART.h" //52串口
#define REC_BUF_LEN 10 //数据长度
#define uchar unsigned char;
#define uint unsigned int;
uchar rec_buf[REC_BUF_LEN]; //接收数据缓冲区
uint check_sum = 0; //接收数据校验和
uchar count = 0; //当前接收数据个数
bit rec_flag = 0; //数据接收完成标志
bit start_flag = 0; //接收数据起始标志
//==================================================
//函数:void Init_UART1(void)
//描述:串口初始化函数,使用T1方式2自重载方式做波特率发生器,
// 串口使用方式1,8位数据,可变波特率
//参数:无
//返回:无
//作者:geoff 日期:2010/11/04
//修改: 日期:
//版本:V1.1
//==================================================
void UART1_Init(void)
{
SCON = 0x50 ; //方式1,8位可变波特率
TMOD = 0x20 ; //定时器1,方式2,8位自重载
PCON = 0x00 ; //倍频禁用
TH1 = 0xfa ; //晶振22.1184MHz,波特率9600;
TL1 = 0xfa ; //9600
IE |= 0x90 ; //开中断
TR1 = 1 ; //启动定时器
}
//==================================================
//函数:uchar UART1_Receive_Char(void)
//描述:单片机从串口接收一个字符
//参数:无
//返回:uchar dat //接收到的数据
//作者:geoff 日期:2010/11/11
//修改: 日期:
//版本:V1.1
//==================================================
uchar UART1_Receive_Char(void)
{
uchar rec_data;
while(!RI); //等待接收完成
RI = 0; //接收完成后,清接收完成中断
rec_data = SBUF;
return rec_data;
}
//==================================================
//函数:void UART1_Send_Char(uchar send_data)
//描述:单片机向串口发送一个字符
//参数:uchar send_data //待发送数据
//返回:无
//作者:geoff 日期:2010/11/09
//修改: 日期:
//版本:V1.1
//==================================================
void UART1_Send_Char(uchar send_data)
{
SBUF = send_data;
while(!TI); //等待发送完成
TI = 0; //发送完成后,清发送完成中断
}
//==================================================
//函数:void UART1_Send_String(uchar *str, uchar len)
//描述:单片机向串口发送一个字符串
//参数:uchar *str //待发送数据
// uchar len //字符串长度
//返回:无
//作者:geoff 日期:2010/11/10
//修改: 日期:
//版本:V1.1
//==================================================
void UART1_Send_String(uchar *str, uchar len)
{
uchar i;
for(i=0; i<len; i++)
{
UART1_Send_Char(*(str+i));
}
}
//==================================================
//函数:void UART1_Intr(void) interrupt 4
//描述:串口中断处理函数,接受串口向单片机发来的数据
//参数:无
//返回:无
//作者:geoff 日期:2010/11/10
//修改:geoff 日期:2010/11/12
//版本:V2.1 注意:第一个数据以0XFA 开始
//==================================================
void UART1_Intr(void) interrupt 4
{
uchar rec_temp;
if(RI) //RI=1,串口接收到数据
{
RI = 0; //清RI
rec_temp = SBUF; //接收数据
if((rec_temp==0xfa)&&(count==0)) //判断数据是否以OXFA开始
{
check_sum = 0; //清校验和
rec_buf[count] = rec_temp; //把接收到的数据存到接收数组里
count++; //
/////测试用
LCD_DataWrite(rec_temp); //在LCD上显示接收数据
check_sum += rec_temp; //计算校验和
start_flag = 1; //数据以OXFA开始,置开始标志
}
else if(start_flag==1) //判断数据是否开始
{
rec_buf[count] = rec_temp; //接收数据
count++; //
/////测试用
LCD_DataWrite(rec_temp); //在LCD上显示接收数据
check_sum += rec_temp; //计算校验和
if(count==REC_BUF_LEN) //判断是否是最后一位数据,第十位
{
count = 0; //从0重新计数
start_flag = 0; //接收数据结束
check_sum -= rec_temp; //计算最终校验和
if((uchar)check_sum==rec_temp) //判断数据接收是否正确,
{ //数据最后一位是校验和的后8位
rec_flag = 1; //置接收完成标志
}
}
}
}
}
//==================================================
//函数:void UART1_Demo(void)
//描述:串口通信测试程序,使用T1方式2自重载方式做波特率发生器,
// 串口使用方式1,8位,可变波特率
// 晶振22.1184MHz,波特率9600;
//参数:无
//返回:无
//作者:geoff 日期:2010/11/08
//修改:geoff 日期:2010/11/09
//版本:V1.1
//==================================================
void UART1_Demo(void)
{
UART1_Init();
TI = 1; //SBUF置空
/////测试用
LCD_RegWrite(0x80);
while(1)
{
if(rec_flag == 1) //把接收到的数据,发送到串口输出
{
rec_flag = 0; //清接收完成标志
UART1_Send_String(rec_buf,REC_BUF_LEN);
}
Rst_WDT(); //喂狗
}
}
//==================================================
//函数:void main(void)
//描述:主函数
//参数:无
//返回:无
//作者:geoff 日期:2010/11/08
//修改: 日期:
//版本:V1.1
//==================================================
void main(void)
{
LCD_Init(); //单片机LCD初始化
UART1_Demo();
}
本文通过约定特定通信协议,实现单片机和PC的通信,经过测试,单片机收发正常;出现不能通信时,可以多发几个非0XFA数据,让单片机准备接收,然后按照约定的格式发送,并保证每次发送字符长度为10个字节。