|
请教各位高手,我的程序2为什么从机接受数据遇到0x00后,后面的数据接受不到了?急!急!急! void main() { uint i = 0; //定时器0初始化 // 调整输入函数的加载值可以改变串口波特率 Uart1Init(0,1,253);//初始化串口1,设置波特率115200 Uart2Init(1,0,1,220);//初始化串口2,设置波特率9600 Uart2SendStr("AT1#/r"); //主机发送AT1#,测距仪从机应答:ATD+3字节距离数据+校验和+结束符# //例如:测距距离6692.4mm,距离大于6553.6mm接受正常 //主机发送Hex:41 54 31 23,从机应答Hex:41 54 44 011A 03 1E 23 //41 54 44 01 05 6C 72 23 // A T D 6692.4mm 校验和 # 十六进制数:1056c = 66924 结束符:# // 校验和(只取后2位):01+05+6c=72 //当距离小于6553.6mm接受不正常,即3字节高位为00时就不正常只能显示4154 44 //比如5763.1mm测距仪直接接串口调试助手程序1显示41 54 44 00 E1 1F 00 23 //程序2显示41 54 44 //以下是相关联程序: /*------------------------------------------------------------------*/ /*----------------------程序1-------------------------*/ #include "reg51.h" #include "intrins.h" typedef unsigned char BYTE; typedef unsigned int WORD; #define FOSC 11059200L //System frequency #define BAUD 9600 //UART baudrate /*Define UART parity mode*/ #define NONE_PARITY 0 //None parity #define ODD_PARITY 1 //Odd parity #define EVEN_PARITY 2 //Even parity #define MARK_PARITY 3 //Mark parity #define SPACE_PARITY 4 //Space parity #define PARITYBIT EVEN_PARITY //Testing even parity /*Declare SFR associated with the UART2 */ sfr AUXR = 0x8e; //Auxiliaryregister sfr S2CON = 0x9a; //UART2 control register sfr S2BUF = 0x9b; //UART2 data buffer sfr BRT = 0x9c; //Baudrate generator sfr IE2 = 0xaf; //Interruptcontrol 2 #define S2RI 0x01 //S2CON.0 #define S2TI 0x02 //S2CON.1 #define S2RB8 0x04 //S2CON.2 #define S2TB8 0x08 //S2CON.3 bit busy; void SendData(BYTE dat); void SendString(char *s); void main() { #if (PARITYBIT == NONE_PARITY) S2CON = 0x50; //8-bitvariable UART #elif (PARITYBIT == ODD_PARITY) ||(PARITYBIT == EVEN_PARITY) || (PARITYBIT == MARK_PARITY) S2CON = 0xda; //9-bitvariable UART, parity bit initial to 1 #elif (PARITYBIT == SPACE_PARITY) S2CON = 0xd2; //9-bitvariable UART, parity bit initial to 0 #endif BRT = -(FOSC/32/BAUD); //Setauto-reload vaule of baudrate generator AUXR = 0x14; //Baudrategenerator work in 1T mode IE2 = 0x01; //EnableUART2 interrupt EA = 1; //Openmaster interrupt switch SendString("STC12C5A60S2rnUart2 Test !rn"); while(1); } /*---------------------------- UART2 interrupt service routine ----------------------------*/ void Uart2() interrupt 8 using 1 { if (S2CON & S2RI) { S2CON &= ~S2RI; //Clearreceive interrupt flag P0 = S2BUF; //P0 show UARTdata P2 = (S2CON & S2RB8);//P2.2 show parity bit } if (S2CON & S2TI) { S2CON &= ~S2TI; //Cleartransmit interrupt flag busy = 0; //Cleartransmit busy flag } } /*---------------------------- Send a byte data to UART Input: dat (data to be sent) Output:None ----------------------------*/ void SendData(BYTE dat) { while (busy); //Wait forthe completion of the previous data is sent ACC = dat; //Calculate the even parity bit P (PSW.0) if (P) //Set theparity bit according to P { #if (PARITYBIT == ODD_PARITY) S2CON &= ~S2TB8; //Setparity bit to 0 #elif (PARITYBIT == EVEN_PARITY) S2CON |= S2TB8; //Set paritybit to 1 #endif } else { #if (PARITYBIT == ODD_PARITY) S2CON |= S2TB8; //Set paritybit to 1 #elif (PARITYBIT == EVEN_PARITY) S2CON &= ~S2TB8; //Setparity bit to 0 #endif } busy = 1; S2BUF = ACC; //Senddata to UART2 buffer } /*---------------------------- Send a string to UART Input: s (address of string) Output:None ----------------------------*/ Void Uart2SendStr (char *s) { while (*s) //Checkthe end of the string { SendData(*s++); //Send currentchar and increment string ptr } } /********************程序1结束****************/ /********************程序段2开始****************/ #include "systerm.h" uchar GsmRcv[MAXRCV] = {0}; uchar DebugBuf_U2[MAXBUF] = {0}; uchar DebugBuf_U1[MAXBUF] = {0}; uchar GsmRcvCnt = 0; uchar GsmAtFlag = 0; uchar GsmAtFlag2 = 0; uchar Debug2RcvCnt = 0; uchar Debug1RcvCnt = 0; bit uart2Sending = 0; bit uart1Sending = 0; uchar receive_number[13]={0};//接收串口发送来的数据的数组 uchar i=0; uchar j; /***************************串口2初始化函数函数*****************************/ /*函数原型:charUart2Init(char s2smod,char brtx12,unsigned char reload) /*函数功能:初始化用于连接gprs的串口2 ,串口2只能设置为独立波特率提供波特率 并打开串口2中断和全局中断 /*输入参数: S2_P4 S2_P4位 0/1 0:RXD2(P1.2)TXD2(P1.3) 1:RXD2(P4.2)TXD2(P4.3) smod s2smod位 0/1 brtx12 brtx12位 0/1 reload reload寄存器数值 0-255 /*输出参数: -1 s2smod位错误,没有写入0/1 -2 brtx12位错误,没有写入0/1 0 微波 /********************************************************************/ char Uart2Init(char s2_p4,char s2smod,charbrtx12,unsigned char reload) { S2CON= 0X50;//8位可变波特率,无奇偶位 BRT = reload;//设置独立波特率发生器波特率 if(s2_p4== 1) { AUXR1|= S2_P4; //S2_P4 = 1;//将串口2映射到P4口,1:RXD2(P4.2)TXD2(P4.3) } elseif(s2_p4 == 0) { AUXR1&= (~S2_P4); //S2_P4 = 0;//将串口2映射到P1口,0:RXD2(P1.2)TXD2(P1.3) } else { return-4; } if(s2smod== 1) { AUXR|= S2SMOD; //S2SMOD = 1;//波特率倍速位 } elseif(s2smod == 0) { AUXR&= (~S2SMOD); //S2SMOD = 0;//取消波特率倍速位 } else { return-1; } if(brtx12== 1) { AUXR|= BRTx12;//BRTx12 = 1;1T模式 } elseif(brtx12 == 0) { AUXR&= (~BRTx12);//BRTx12 = 0;12T模式 } else { return-2; } AUXR|= BRTR;//开启波特率发生器 //设置串口2中断优先级 IP2H|= PS2H; //设置串口2优先级为3(最高) IP2|= PS2; if(UART2_PRIO & 0x02) { IP2H|= PS2H; } else { IP2H&= ~PS2H; } if (UART2_PRIO & 0x01) { IP2|= PS2; } else { IP2&= ~PS2; } IE2|= ES2;// ES2 = 1; //允许串口2中断 EA= 1; //开总中断 return0; } /***************************串口2发送字符函数************************/ /*函数原型:voidUart2SendHex(uchar i) /*函数功能:串口2发送函数,发送单一数据 /*输入参数:数据 /*输出参数:无 /********************************************************************/ void Uart2SendHex(uchar i) { while(uart2Sending== 1); uart2Sending= 1; S2BUF= i;//装入数据 } /***************************串口2发送字符串函数**********************/ /*函数原型:void Uart2SendStr(char*data_at) /*函数功能:串口2发送函数,发送字符串 /*输入参数:字符串指针 /*输出参数:无 /********************************************************************/ void Uart2SendStr(char* data_at) { while(*data_at) { Uart2SendHex(*data_at++); } } /***************************串口1初始化函数**********************/ /*函数原型:charUart1Init(char smod,char brtx12,unsigned char reload) /*函数功能:串口1初始化 /*输入参数: smod smod位 0/1 brtx12 brtx12位 0/1 reload reload寄存器数值 0-255 /*输出参数: -1 smod位错误,没有写入0/1 -2 brtx12位错误,没有写入0/1 0 /*备注:串口设置位独立波特率提供波特率,和串口2使用同一个波特率,也可以使用定时器1来提供波特率 /********************************************************************/ char Uart1Init(char smod,charbrtx12,unsigned char reload) { SCON= 0X50;//8位可变波特率,无奇偶位(SM0=0,SM1=1),使能串口接收模块(REN=1) BRT = reload;//设置独立波特率发生器波特率 if(smod== 1) { PCON|= SMOD; //SMOD = 1;//波特率倍速位 } elseif(smod == 0) { PCON&= (~SMOD); //SMOD = 0;//取消波特率倍速位 } else { return-1; } if(brtx12== 1) { AUXR|= BRTx12;//BRTx12 = 1;1T模式 } elseif(brtx12 == 0) { AUXR&= (~BRTx12);//BRTx12 = 0;12T模式 } else { return-2; } AUXR |= S1BRS;//串口1设置为使用独立波特率发生器 AUXR|= BRTR;//开启波特率发生器 //设置串口1中断优先级 if(UART1_PRIO & 0x02) { IPH|= PSH; } else { IPH&= ~PSH; } if (UART1_PRIO & 0x01) { PS= 1; } else { PS= 0; } ES= 1; //开串口中断 EA= 1; //开总中断 return0; } /***************************串口1发送函数**********************/ /*函数原型:voidUart1SendHex(char i) /*函数功能:串口1发送函数 /*函数功能:串口1发送函数,发送单一数据 /*输入参数:数据 /*输出参数:无 /**************************************************************/ void Uart1SendHex(char i) { while(uart1Sending);//等待发送完毕 uart1Sending= 1; SBUF= i;//将数据放入寄存器发送 } /***************************串口1发送字符串函数**********************/ /*函数原型:voidUart1SendStr(char* data_at) /*函数功能:串口1发送函数,发送字符串 /*输入参数:字符串指针 /*输出参数:无 /********************************************************************/ void Uart1SendStr(char* at) { while(*at) //判断一串数据是否结束 { Uart1SendHex(*at++);//发送数据 } } /***************************串口1发送接收中断函数********************/ /*函数原型:voidUart1InterruptReceive(void) interrupt 4 /*函数功能:串口2发送接收中断函数 /*输入参数:无 /*输出参数:无 /*备注:接收函数内部不可以放入其他的中断或者发送函数,否则影响接收数据 /********************************************************************/ void Uart1InterruptReceive(void) interrupt4 { chartmp = 0; if(RI) { ES=0;//关串行口中断 RI=0;//接收中断信号清零,表示将继续接收 tmp= SBUF;//接收数据 #ifdef UART1_DEBUG //将接收到的数据放入DebugBuf_U1,在定时器内,DebugBuf_U1会被串口2发送给GSM模块。 // 这样通过串口1 发送到单片机的数据GSM 模块就可以收到了,主要为了调试的方便。 DebugBuf_U1[Debug1RcvCnt]= tmp; Debug1RcvCnt++; if(Debug1RcvCnt>=MAXBUF-1) { Debug1RcvCnt= 0; } #endif ES=1;//开串行口中断 } if(TI) { TI= 0; uart1Sending= 0; } } /***************************串口2发送接收中断函数**********************/ /*函数原型:voidUart2InterruptReceive(void) interrupt 8 /*函数功能:串口2发送接收中断函数 /*输入参数:无 /*输出参数:无 /*备注:接收函数内部不可以放入其他的中断或者发送函数,否则影响接收数据 用于接收GPRS模块传输来的数据,将数据保存到GsmRcv[],在函数中使用strstr判断数据。 /********************************************************************/ void Uart2InterruptReceive(void) interrupt8 { unsignedchar tmp = 0; uchari = 0; ucharm = 0; IE2&= (~ES2); //关闭串口2中断//ES2 = 0; if(S2CON& S2RI) //if(S2RI == 1) { S2CON&= (~S2RI);//S2RI = 0; tmp= S2BUF; #ifdef UART1_DEBUG //将接收到的数据放入DebugBuf_U2,在定时器内,DebugBuf_U2会被串口1发送给PC机。 //这样GSM发送给单片机的数据也可以在电脑上观察到了。 //H1005071 1597422124 2000-01-01 01:01:01 0a0d DebugBuf_U2[Debug2RcvCnt]= tmp; Debug2RcvCnt++; if(Debug2RcvCnt>=MAXBUF-1) { Debug2RcvCnt= 0; } #endif GsmRcv[GsmRcvCnt]= tmp; GsmRcvCnt++; if(GsmRcvCnt> MAXRCV) { GsmRcvCnt= 0; GsmAtFlag2= 1; // m= 0; } } if(S2CON& S2TI) { S2CON&= ~S2TI; uart2Sending= 0; } IE2|= ES2;//ES2 = 1; } /***************************初始化定时器0****************************/ /*函数原型:Timer0Init /*函数功能:初始化定时器0 /*输入参数:无 /*输出参数:无 /********************************************************************/ voidTimer0Init(void) { TMOD=0x01; //设置定时器0为工作方式1 //AUXR|=T0x12; TH0=T0H; //放入初值,11.0592M,1ms TL0=T0L; // 设置定时器0中断优先级(优先级1) IPH &= ~PT0H; PT0 = 1; EA=1; //开总中断 ET0=1; //开定时器0中断 TR0=1; //启动定时器0 } /***************************定时器0中断******************************/ /*函数原型:Timer0 /*函数功能:每1ms执行一次中断,中断内部重新赋值 /*输入参数:无 /*输出参数:无 /********************************************************************/ void timer0()interrupt 1 { uchar i = 0; TH0=T0H; TL0=T0L; #ifdefUART1_DEBUG//发送数据用于调试。 timer0_debug_cnt++; if(timer0_debug_cnt== 20) { timer0_debug_cnt= 0; for(i=0;i { DebugBuf_U2 =0; } Debug2RcvCnt = 0; Uart2SendStr(DebugBuf_U1); for(i=0;i { DebugBuf_U1 =0; } Debug1RcvCnt = 0; } #endif timer0_cnt++; if(timer0_cnt ==1000) { timer0_cnt = 0; sec_cnt++; } #ifdefSHOW_TIME_DEBUG if(timer0_cnt ==500) { //显示时间 ShowTime(0, 4); //显示日期 ShowDate(0, 5); } #endif//SHOW_TIME_DEBUG } /***************************程序段2结束**************************/
|