关于单片机串口中断接收帧包,此类东西网上一搜也是一大片,具体我就不在这里做过多的介绍了。
不过还是大概说下吧:所谓帧就是一串特定格式的数据,而数据当然是由字符构成的。
一般帧由 :帧头、地址信息、数据类型、数据长度、数据块、校验码、帧尾
逻辑协议解析的目的,首先判断数据包的完整性,正确性,然后提取数据类型,数据等数据,存放起来用于主程序处理。
本文假设此数据为: 0x0C 0xAA 0xFA 0x55 0xFA data[...]... sum xor 0xf9
帧头 Ox0C OxAA
源地址 0xFA
目的地址 0x55
数据长度 0xfa
校验码 sum xor
帧尾 0xf9
代码如下:
1 unsigned char data_BUFF[]={0}; 2 unsigned char datacheck_OK = 0; //数据接收校验标志位 3 unsigned char rc_datbuff; //数据 4 unsigned char lennum; //帧 数据长度 5 unsigned char length=0; // 帧数据包的主数据 标志 6 unsigned char sumchkm=0; //帧数据和校验 7 unsigned char xorchkm=0; //帧数据的与或校验 8 9 void RXBUFFINIT(){ 10 11 EA=1; 12 . 13 . 14 . 15 16 } 17 18 void main(){ 19 20 21 while(1){ 22 if(datacheck_OK == 0){ //校验第一次包头码 23 if(rc_datbuff == 0x0C) 24 datacheck_OK = 1; 25 else datacheck_OK = 0; 26 } 27 esle if(datacheck_OK == 1){ //校验第二次包头码 28 if(rc_datbuff == 0x0C) 29 datacheck_OK = 2; 30 else datacheck_OK = 0; 31 } 32 else if(datacheck_OK == 2){ 33 if(rc_datbuff == 0xFA){ //校验源地址码 34 sumchkm = rc_datbuff; //开始计算累加、异或校验和 35 xorchkm = rc_datbuff; 36 datacheck_OK = 3; 37 } 38 else datacheck_OK =0; 39 } 40 else if(datacheck_OK == 3){ // 校验目的地址码 41 if(rc_datbuff == 0x55){ 42 sumchkm += rc_datbuff; //开始计算累加、异或校验和 43 xorchkm ^= rc_datbuff; 44 datacheck_OK = 4; 45 } 46 else datacheck_OK =0; 47 } 48 else if(datacheck_OK == 4){ //数据长度 49 length = 0; //数据计数清零 50 lennum = rc_datbuff; //数据长度 51 sumchkm += rc_datbuff; 52 xorchkm ^= rc_datbuff; 53 datacheck_OK = 5; 54 } 55 else if(datacheck_OK == 5 || datacheck_OK == 6){ //数据接收&完成 56 data_BUFF[length++] = rc_datbuff; 57 sumchkm += rc_datbuff; 58 xorchkm ^= rc_datbuff; 59 if(length == lennum) datacheck_OK = 7; 60 else datacheck_OK = 6; 61 } 62 else if(datacheck_OK == 7){ 63 if(sumchkm == rc_datbuff ) datacheck_OK == 8; //校验累加值与与或值是否相等 64 else datacheck_OK == 0; 65 } 66 else if(datacheck_OK == 8){ 67 if(xorchkm == rc_datbuff ) datacheck_OK == 9; //校验累加值与与或值是否相等 68 else datacheck_OK == 0; 69 } 70 else if(datacheck_OK == 9){ //判断帧尾 71 if(rc_datbuff == 0xf9) datacheck_OK == 0xff; //置为标志位 72 else datacheck_OK == 0; 73 } 74 75 } 76 } 77 78 79 80 void RX_BUFF(void) interrupt 0 using 1 { 81 82 . 83 . 84 . 85 rc_datbuff=BUFF; 86 87 }
datacheck_OK:为数据标志位,用于确定当前包在数据中的那个位置,并且接收过程中自动对接收数据进行校验和处理,
在数据包接收完的同时也进行了校验的比较。因此当帧尾结束符接收到的时候,则表示一帧数据已经接收完毕,并且通过了校验,
关键数据也保存到了缓冲去中。