📄 send_receive.h
字号:
///////////////////////////////////////////////////
#ifndef Send_Receive_h
#define Send_Receive_h
#include<reg51.h>
#include <absacc.h>
#include<DATA_define.h>
#include<buffer.h>
#include<display.h>
//////////////////////////////////////
///////////////////////////////////
unsigned char CheckADR(void)
{
if((Rbuffer[3]-'0')*16+Rbuffer[4]-'0'==HOST_ADR)
return 1;
else
return 0;
}
unsigned char CheckCHKSUM(void)//检查CHKSUM
{
unsigned char i=1,temp=0;
while(Rbuffer[i]!=EOI && i<MAXNUM_BUF)//有解决不了的问题,有空讨论,现在正确
{
if (Rbuffer[i]==EOI || i>=MAXNUM_BUF) break;
if(i%2!=0)
temp=temp+(Rbuffer[i]-'0')*16;
else
temp=temp+Rbuffer[i]-'0';
i++;
}//i=21;Rbuffer[21]=EOI ,Rbuffer_point=1 .Rbuffer[20]正确
//设置检测码时,应为3A到3F,而不应该是a到f
if(temp==0)
return 1;
else
return 0;
}
////////////////////////////////////
unsigned char CheckLENGTH(void)//检查数据长度
{
unsigned char i=0;
while(Rbuffer[i]!=EOI&&i<MAXNUM_BUF)
{
i++;
}
if(i-13==2*Get_LENGTH()) //Rbuffer_point=1;i=21
return 1;
else
return 0;
}
///////////////////////////////////////////
unsigned char CheckINFO(void)///各组自己去检查???????????????????????
{
return 1;
}
///////////////////////////////////////////
unsigned char CheckCOM1(void)
{ //set=0x00,red=0x01
if(Rbuffer[5]==Sbuffer[5]&&Rbuffer[6]==Sbuffer[6] )
return 1;
else
return 0;
}
/////////////////////////////
unsigned char CheckCOM2(void)//暂不作处理
{
return 1;
}
//////////////////////////////////////////
unsigned char CheckVER(void)
{
if((Rbuffer[1]-'0')*16+Rbuffer[2]-'0'==VER)
return 1;
else
return 0;
}
////////////////////////////////////
void Set_RTN(void)///检测命令是否合法,并设置RTN
{
if(!CheckVER())
{RTN=VER_ERR;}
else if(!CheckCHKSUM()/*CHKSUM出错*/)//?????????????
{RTN=CHKSUM_ERR;}
else if(!CheckCOM1()||!CheckCOM2()/*CMD1\CMD2合法*/)
{RTN=COMMAND_ERR;}
else if(!CheckLENGTH()/*LENGTH与INFO段实际长度是否相符*/)
{RTN=LENGTH_ERR;}
else if(!CheckINFO()/*INFO段中各参数的合法性和有效性*/)
{RTN=INFO_ERR;}
else if(!CheckADR())/*地址错*/
{RTN=ADR_ERR;}
else
{RTN=FRAME_OK;}
}
//////////////////////////////////////
void PR1 (void)//状态一
{
switch(state_flag)
{
case C11 :state=1;//收到字节不是SOI
case C12 :buffer_flag=0;state=2;//收到字节是SOI
}
}
///////////////////////////////////////////
void PR2 (void)//状态二
{
switch(state_flag)
{
case C22a:Rbuffer[Rbuffer_point]=SBUF;Rbuffer_point++;state=2;break;//收到有效字节 /*填写buf*/
case C22b:Rbuffer_point=1;state=2;break;//收到字节是SOI /*清空buf*/
case C21a:Rbuffer_point=1;state=1;break;//超时未收到后续字节;帧长度超限 /*清空buf*/
case C21b:Rbuffer[Rbuffer_point]=EOI;state=1;break;//收到字节是EOI,但帧长度为0 /*无*/
case C21c:Rbuffer[Rbuffer_point]=EOI;buffer_flag=1;state=1;break;//收到字节是EOI,帧长度不为0 /*设置buf有效标志*/
default:state=1;break;
}
}
//////////////////////////////////////////////
void SetFlag(void)//状态机标志位设置
{
unsigned char temp=SBUF;
if(state==1)
{
if(temp!=SOI) //收到字节不是SOI
{state_flag=C11;}
else{ state_flag=C12;}//收到字节是SOI
}
else if(state==2)
{
if(temp==EOI)
{
if(LENGTH==0)
state_flag=C21b;//收到字节是EOI,但帧长度为0
else state_flag=C21c;//收到字节是EOI,帧长度不为0
}
else if(temp==SOI)
{state_flag=C22b;}//收到字节是SOI
else if(Rbuffer_point>=MAXNUM_BUF-2)//帧长度超限
//关于桢长度超出限制的问题,如果一直向机器发出信号,虽然有桢长度超限的检查,但是
//因为一直有接收的中断,所以程序会出错。但是在正常的情况下是不会出现这样的问题的
//——总线上有干扰信号。
{state_flag=C21a;}////???????????????????超时未收到后续字节;帧长度超限
else {state_flag=C22a;}//收到有效字节
}
}
////////////////////////////////////
void FSM(void)//状态机
{
SetFlag();
switch(state)
{
case 1: PR1( );break;
case 2: PR2( );break;
default:state=1;
}
}
////////////////////////////////////////////
/*
void Send(unsigned char ADR_char)
{
unsigned char i;
for(i=0;i<10+2*LENGTH+3;i++)//??????????????????
{
TI=0;
SBUF=Sbuffer[i];
while(TI==0);
}
// if(Sbuffer[Sbuffer_point]!=EOI)
// {
// SBUF=Sbuffer[Sbuffer_point];
// Sbuffer_point++;
// }
}
*/
////////////////////////////////////
void BusControl(unsigned char i)//控制总线的选通,这个函数只有主机上用
{
buscontrol_output=2^i;
if(buffer_flag)
{
address++;
address=address%NUM_OF_SITE;
}
else if(Adrchange_flag)
{
address++;
address=address%NUM_OF_SITE;
}
//付给一端口????????待修改
}
/////////////////////////////////////////////////
void SendBack()
{
Set_RTN();
Set_RSPD();
Set_LENGTH();
Set_B_INFO();
Set_CHKSUM();
}
///////////////////////////////////
void Set_BUF(void)//
{
Set_RTN();
Set_SOI();
Set_VER();
Set_ADR();
Set_RSPD();
Set_LENGTH();
Set_B_INFO();
Set_CHKSUM();
Set_EOI();
}
//////////////////////////////////
void Set_address(unsigned char i) //选择接入总线的站点
{
int j;
// WR_8255=0;//可写
// RD_8255=1;//不可读
// RESET_8255=0;//复位无效
/* ADDR_8255_control=0x80;//写方式字
for(j=0;j<2000;j++);
switch(i)
{
////////////////////////////////////////////////////////////////////
//
//设置温度
case 0:ADDR_8255_data=0x53;CMD1=SET;ADR=CUP_ADR;break;//主机-〉温控
case 1:ADDR_8255_data=0x5c;break;//温控-〉主机
//设置转速
case 2:ADDR_8255_data=0x17;CMD1=SET;ADR=MOTOR_ADR;break;//主机-〉电机
case 3:ADDR_8255_data=0xd4;break;//电机-〉主机
//获得距离
case 4:ADDR_8255_data=0x47;CMD1=RED;ADR=DIST_ADR;break;//主机-〉超声
case 5:ADDR_8255_data=0x74;break;//超声-〉主机
//获得温度
case 6:ADDR_8255_data=0x53;CMD1=RED;ADR=CUP_ADR;break;//主机-〉温控
case 7:ADDR_8255_data=0x5c;break;//温控-〉主机
//获得转速
case 8:ADDR_8255_data=0x17;CMD1=RED;ADR=MOTOR_ADR;break;//主机-〉电机
case 9:ADDR_8255_data=0xd4;break;//电机-〉主机
default:ADDR_8255_data=0xaa;break;//全部不工作
for(j=0;j<2000;j++);
ADDR_8255_control=0x81;
}
// ADDR_8255_data=0x53;//主机-〉超声
// WR_8255=1;//不可写 */
}
////////////////////////////
#endif
//////////////////////////////////////////////////
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -