您好,欢迎访问三七文档
#includereg52.h#includestdio.h#includeintrins.h#defineR_Buf_Len10//设置接收缓冲器长度10个字节unsignedchardataR_Buf[R_Buf_Len]=;//环形接收数据缓冲区unsignedchardataR_I_Ptr;//环形接收缓冲区输入、输出指针unsignedcharbdataFlag;//可进行位操作的变量定义/**************************************串行口初始化***************************************/voidInit_Service_Port(void){PCON=0x80;//SMOD=1,通信波特率*2RCAP2L=0xec;//波特率为38400RCAP2H=0xff;//T2CON=0x34;//定时器2的工作方式SCON=0x42;//串行口工作方式TR2=1;//启动定时器2REN=1;//串行口允许接收TI=0;//清除发送中断标志TIRI=0;//清除接收中断标志RIEA=1;//总中断允许控制位打开ES=1;//串行口中断允许控制位打开EX0=1;//外部中断0允许打开IT0=1;//以下降沿作为外部中断0的触发方式R_I_Ptr=0;//接收缓冲区输入、输出指针IP=0x10;}voidT1_init(void)//定时器T1的初始化函数{TMOD=0x20;//设定T1的工作模式为2TH1=0x98;//每104us溢出一次。晶振频率为12Mhz,经12分频后为1Mhz,所以计一次数为1us。//(2的8次方-104)再转换为16进制即为0x98.TL1=0x98;//模式2为自动重新装入初值的8位计数器,溢出后自动将TH1的值赋给TL1.EA=1;//开中断ET1=1;//定时器0允许中断TR1=1;//启动定时器0}/********************************串口单个字符发送函数*******************************///串口发送,只有调用了此函数后才能进如中断函数的if(_testbit_(TI))中,当T_Buf[]中只有一个数据时,//运行此函数就能完成发送,当有2个及其以上的字符时,第2,及其之后的字符的发送则是通过if(_testbit_(TI))中的//SBUF=T_Buf[T_O_Ptr];来完成发送的。voidsend_str(unsignedcharT_Data){SBUF=T_Data;//这里数据的发送要一定的时间delay(1);//这里需要有一定延时,以便数据发送完全}/*************************************串口字符串发送函数*************************************/voidsend_strs(unsignedchar*strings_point){while(1){if(*strings_point!=0x00)//表示所指的地址有数据{send_str(*strings_point);//发送单个的字符,在这里进行连续的发送strings_point++;//指向下一个地址}else{break;}}//send_str(0x0d);//换行//send_str(0x0a);//这里不用换行输出,因为它和VB中的程序代码不相兼容,VB中用的是文本输入和输出}/****************************************串行口接收发送测试主程序*************************************************///串行口接收发送测试主程序voidmain(void){Init_Service_Port();//串口初始化data1=1;//先置高,启动之前要保证有足够的置高时间data_temp&=0x00;flag_i=0;//flag_j=0;flag_k=0;while(1){if(lomot_start==1){if(forward==1)//前向,加减速运行{forw_spe_cont();}if(backward==1)//后向,加减速运行{back_spe_cont();}//char_trans('F');//用‘’括起来的为字符;用括起来的为字符串}record_function();play_function();}}/**************************************串行口中断**************************************//********************串行中断标志RI和TI没有置0时,不会再次触发串行口中断*****************/voidcom_ser_int(void)interrupt4using3{if(RI)//接收中断{R_Buf[R_I_Ptr]=SBUF;//将接收数据存入环形接收缓冲区if(R_Buf[R_I_Ptr]==video_open[R_I_Ptr])//成立,表示接收区没有数据了{video_con[0]++;//视频开}if(R_Buf[R_I_Ptr]==video_clos[R_I_Ptr])//成立,表示接收区没有数据了{video_con[1]++;//视频关}if(R_Buf[R_I_Ptr]==volume_inc[R_I_Ptr]){volum_con[0]++;//音量+}if(R_Buf[R_I_Ptr]==volume_dec[R_I_Ptr]){volum_con[1]++;//音量-}if(R_Buf[R_I_Ptr]==locomot_on[R_I_Ptr]){locom_con[0]++;//机车启动}if(R_Buf[R_I_Ptr]==locomo_off[R_I_Ptr]){locom_con[1]++;//机车停止}if(R_Buf[R_I_Ptr]==forwar_run[R_I_Ptr]){direc_con[0]++;//正方向运行}if(R_Buf[R_I_Ptr]==backwa_run[R_I_Ptr]){direc_con[1]++;//反方向运行}if(R_Buf[R_I_Ptr]==incr_speed[R_I_Ptr]){speed_con[0]++;//加速运行}if(R_Buf[R_I_Ptr]==decr_speed[R_I_Ptr]){speed_con[1]++;//减速运行}if(R_Buf[R_I_Ptr]==receiv_add[R_I_Ptr]){Flag_addr[0]++;//前6位相同,后4位不同}else{if(Flag_addr[0]==6)//确保前面收到了6个*字符{if((R_Buf[R_I_Ptr]=0x30)&&(R_Buf[R_I_Ptr]=0x39))//取字符0~9的ASCII值//里面加括号,逻辑性强些,有助于理解代码{receiv_add[R_I_Ptr]=R_Buf[R_I_Ptr]-0x30;}if((R_Buf[R_I_Ptr]=0x41)&&(R_Buf[R_I_Ptr]=0x46))//取字符A~F的ASCII值{receiv_add[R_I_Ptr]=R_Buf[R_I_Ptr]-0x37;}if((R_Buf[R_I_Ptr]=0x61)&&(R_Buf[R_I_Ptr]=0x66))//取字符a~f的ASCII值{receiv_add[R_I_Ptr]=R_Buf[R_I_Ptr]-0x57;}Flag_addr[1]++;if(Flag_addr[1]==1)//将第一个字符转换为高位{receiv_add[R_I_Ptr]=receiv_add[R_I_Ptr]4;}if(Flag_addr[1]==2)//将前两个字符组合成一个字节{receiv_add[R_I_Ptr]=receiv_add[R_I_Ptr];Flag_addr[2]=receiv_add[6]+receiv_add[7];}if(Flag_addr[1]==3)//将第三个字符转换为高位{receiv_add[R_I_Ptr]=receiv_add[R_I_Ptr]4;}if(Flag_addr[1]==4)//将后两个字符组合成一个字节{Flag_addr[3]=receiv_add[8]+receiv_add[9];}}}if(R_Buf[R_I_Ptr]==recor_mode[R_I_Ptr]){vmode_con[0]++;//录音模式}if(R_Buf[R_I_Ptr]==vplay_mode[R_I_Ptr]){vmode_con[1]++;//放音模式}if(R_Buf[R_I_Ptr]==pla_rec_st[R_I_Ptr]){pl_re_stop++;//放音模式}R_I_Ptr=(R_I_Ptr+1)%10;//接收区指针加1if(video_con[0]==10)//视频开标识满足{all_clear();send_strs(video_open);video=1;//置1时打开视频电源}if(video_con[1]==10)//视频关标识满足{all_clear();send_strs(video_clos);video=0;//置0时关闭视频电源}if(volum_con[0]==10)//音量+标识满足{all_clear();vol_increment();//调用音量+函数send_strs(volume_inc);}if(volum_con[1]==10)//音量-标识满足{all_clear();//调用音量-函数vol_decrement();send_strs(volume_dec);}if(locom_con[0]==10)//机车启动{all_clear();lomot_start=1;//将启动标志置1lomot_stop=0;send_strs(locomot_on);}if(locom_con[1]==10)//机车停止{all_clear();lomot_start=0;lomot_stop=1;//将停止标志置1spe_rank=0;send_strs(locomo_off);}if(direc_con[0]==10)//正方向运行{all_clear();forward=1;//用来标识前向运行backward=0;spe_rank=0;//换向后从0速度开始send_strs(forwar_run);}if(direc_con[1]==10)//反方向运行{all_clear();forward=0;//用来标识后向运行backward=1;spe_rank=0;//换向后从0速度开始send_strs(backwa_run);}if(speed_con[0]==10)//加速运行{all_clear();speed_increment();//调用加速等级函数send_strs(incr_speed);if(spe_rank10){send_str(spe_rank+0x30);}else{send_strs(A);}}if(speed_con[1]==10)//减速运行{all_clear();speed_decrement();//调用减速等级函数send_strs(decr_speed);if(spe_rank10){send_str(spe_rank+0x30);}else{send_strs(A);}}if((Flag_addr[0]==6)&&(Flag_addr[1]==4))//接收录音和播放地址{all_clear();receive_flag=1;send_strs(******)
本文标题:单片机串口通信程序
链接地址:https://www.777doc.com/doc-7088104 .html