📄 usart.c
字号:
#include "24c08.h"
#include "Config.h"
#include "USART.h"
#include "display.h"
/*******************************************************************************
Rec_Judge()
接受数据的判断函数 判断是否符合645协议 并验证效验码
*******************************************************************************/
uchar Rec_Judge(uchar *s)
{
uchar i,j,k;
if((*s != 0x68) && (*(s+7) != 0x68))
return 0;
else
{
for(i=1;i<7;i++)
{
if(*(s+i) > 0x99)
return 0;
}
}
if(*(s+9) > (Num-12))
return 0;
for(k=0;k<(*(s+9)+10);k++)
{
CS += *(s+k);
}
for(j=0;j<*(s+9);j++)
{
*(s+10+j) -= 0x33;
}
if(CS != *(s+(*(s+9)+10)))
return 0;
if(*(s+(*(s+9)+11)) != 0x16)
return 0;
else
return 1;
}
/*******************************************************************************
Send_Set()
数据发送的准备函数 把所发送的数据存到s_buf[N]数组中,完成后关节后关闭接受中断,
打开发送中断
*******************************************************************************/
void Send_Set(uchar *s)
{
uint ii,jj,kk;
for(ii=0;ii<3;ii++) //前导字节
{
s_buf[ii] = 0xFE;
aa += 1;
}
for(jj=0;jj<10;jj++) //帧起始符到数据长度
{
s_buf[3+jj] = *(s+jj);
aa += 1;
SS1 += s_buf[3+jj];
}
for(kk=0;kk<s_buf[12];kk++) // 数据域的处理和准备
{
s_buf[13+kk] = (readdata[kk] + 0x33);
aa += 1;
SS1 += s_buf[13+kk];
}
aa ++;
s_buf[(13+s_buf[12])] = SS1; //效验码的计算结果
aa ++;
s_buf[(14+s_buf[12])] = 0x16; //帧结束符
TXBUF0 = 0xFE;
IE1 &= ~URXIE0; //关接受中断
IE1 |= UTXIE0; //开发送中断
CY = 1;
}
/*******************************************************************************
usart_tx()
发送中断函数
*******************************************************************************/
#pragma vector=UART0TX_VECTOR
__interrupt void usart0_tx(void)
{
IFG1 &= ~UTXIFG0; //清零
TXBUF0 = s_buf[s0++]; //发送数据到缓冲寄存器
if(s0 >= aa) //发送接受的标志
{
s0 = 0;
aa = 0;
SS1 = 0;
LCDMEM[11] &= ~0x05;
IE1 &= ~UTXIE0; //关闭发送中断
IE1 |= URXIE0; //打开接受中断
}
}
/*******************************************************************************
delay()
延时函数
*******************************************************************************/
void delay(uint nn)
{
while(nn -->0);
}
/*******************************************************************************
Serial_Addr()
通讯地址判断函数
*******************************************************************************/
uchar Serial_Addr(uchar *s1)
{
uchar i,a[6];
for(i=0;i<=5;i++)
{
if((*(s_buf+i)) != 0x99) //不是广播地址
break;
if(i==5)
return(0x01);
}
for(i=0;i<=5;i++)
{
if((*(s1+i)) != a[i])
return(0x00); //地址不相同
}
return(0x02);
}
/*******************************************************************************
Serial_Password()
通讯密码判断函数
*******************************************************************************/
char Serial_Password(uchar *s1)
{
uchar i,a[4];
for(i=0;i<=3;i++)
{
if((*(s1+i)) != a[i])
return 0;
}
return 1;
}
/*******************************************************************************
Serial_Command_Run()
通讯执行函数
*******************************************************************************/
char Serial_Command_Run(uchar *s)
{
switch(Serial_Addr(s)) //判断地址是否正确
{
case 0x02: //广播地址999999999999H
break;
case 0x01:
switch(*(s_buf+6)) //正常地址
{
case 0x0f: //进行密码修改
if(~Serial_Password(s+8))
return 0;
delay(5);
(*(s+6)) |= 0x80;
(*(s+7)) = 0x04;
Send_Set(s); //*存取新密码
break;
case 0x02:
break;
case 0x04:
break;
default:
break;
}
break;
case 0x00:
return 0;
}
return 1;
}
/*******************************************************************************
USART()
通讯主函数
*******************************************************************************/
void USART()
{
if(RXFLG) // 准备发送数据
{
RXFLG = 0;
TXFLG = Rec_Judge(r_buf);
if(TXFLG)
{
TXFLG = 0;
Write_Data(&r_buf[10],StartAddr,r_buf[9]);
_NOP();
_NOP();
_NOP();
CS = 0x00;
Display_Flag = Read_Data(readdata,StartAddr,r_buf[9]);
if(Display_Flag)
{
Display_Flag = 0;
display();
}
Command_Status1 |= 0x04;
if(CY == 1)
{
Send_Set(r_buf);
}
}
}
if(Command_Status1 & 0x04) //通讯事件发送
{
if(~Serial_Command_Run(s_buf)) //帧执行
{
Command_Status1 &= 0xfb; //帧错误,恢复信道功
return;
}
Command_Status1 &= 0xfb; //清除通讯处理事件
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -