📄 485.c
字号:
/******************************串口 103规约**************************************/
/***上行报文: */
/* */
/* 事件报文 ASDU1 */
/* 遥信量 ASDU1 */
/* 遥测量 ASDU9 */
/* 定值项 ASDU10 */
/* 描述表 ASDU10 */
/* */
/***下行报文: */
/* */
/* 对时 ASDU6 */
/* 总查询 ASDU7 */
/* 修改(定值、压板状态)、遥控 ASDU10 */
/* 复归保护信号 ASDU20 */
/* 读取(定值、压板状态、遥信) ASDU21 */
/* */
/***信息序号(inf) */
/* */
/* 0~79: 事件信息序号(80) */
/* 80~159: 告警信息序号(低压保护的告警组是不连续的)(80) */
/* 160~175: 压板信息序号(16) */
/* 176~207: 遥信信息序号(32) */
/* 208~223: 遥测信息序号(16) */
/* */
/***装置类型(FUN) */
/* */
/* 110KV、220KV线路保护(PSL620、PSL600) 178 */
/* 35KV保护(PSL640、PSP、PSC640系列) 242 */
/* 变压器保护(PST1200系列) 192 */
/* 11C 179 */
/* */
/* HISTORY NAME REMARKS */
/* */
/* 郑小军 2001-10-15 创建初始化版本 */
/********************************************************************************/
#include "typedef.h"
#include "generic.h"
#include "inforec.h"
#include "dev_mng.h"
#include "485.h"
/* 各组的起始点号 */
#define EVT_BEGIN -1
#define ALA_BEGIN 79
#define SFC_BEGIN 160
#define DIC_BEGIN 176
#define MEA_BEGIN 208
/* 各组的起始点号 */
BYTE sbuf[250];
BYTE lastbuf[10];
WORD lastid;
WORD tot_leng;
static BYTE powerflg;
static BYTE maskflg;
static BYTE measureflg;
static BYTE dzflg;
static BYTE sfcflg;
static BYTE listflg;
static BYTE diflg;
BYTE dznumber;
BYTE list_num;
BYTE count;
T_SET rsetbuf;
T_SET wsetbuf;
T_LIST list;
T_MEASURE measure;
T_SFC sfc;
T_DI di;
extern HANDLE hand;
void Serial_Interpret(const BYTE* rbuf,BYTE uart_port)
{
BYTE byDevAddr;
BYTE i;
WORD Dev_Num;
Dev_Num = Get_Device_Number();
for (i = 1;i <= Dev_Num;i++)
{
byDevAddr = ID_to_Addr(i);
switch (rbuf[0])
{
case 0x10:
if (rbuf[2] == byDevAddr)
{
Lan_Ack_Staid(rbuf,byDevAddr,uart_port);
return;
}
else
break;
case 0x68:
if (rbuf[5] == byDevAddr || rbuf[5] == 0xff)
{
Lan_Ack_Changeable(rbuf,byDevAddr,uart_port);
return;
}
else
break;
default:
return;
}
}
}
//可变帧长报文的处理
void Lan_Ack_Changeable(const BYTE* rbuf,BYTE byDevAddr,BYTE uart_port)
{
switch(rbuf[6])
{
case 0x06:
Lan_edit06(rbuf,byDevAddr,uart_port);//对时
return ;
case 0x07:
Lan_edit07(rbuf,byDevAddr,uart_port);//总查询
return ;
case 0x0a:
Lan_edit10(rbuf,byDevAddr,uart_port);//通用分类数据
return ;
case 0x14:
ReSet(rbuf,byDevAddr,uart_port);
// Lan_edit20(rbuf,byDevAddr,uart_port);//一般命令(复归保护信号)
return;
case 0x15:
Lan_edit21(rbuf,byDevAddr,uart_port);//通用分类命令
return ;
default:
return ;
}
}
//固定帧长报文的处理
void Lan_Ack_Staid(const BYTE* rbuf,BYTE byDevAddr,BYTE uart_port)
{
BYTE *crc;
BYTE *apack;
BYTE dev_fun;
T_EVENT pEvent;
T_SOE pDIC;
BOOL bDI,bEvent,bMeasure,bAlarm;
WORD wLen;
WORD ngd;
WORD dev_id;
dev_id = Addr_to_ID(byDevAddr);
if (rbuf[1] == lastbuf[0] && dev_id == lastid)
{
//将上次报文重发
wLen = tot_leng;
UART_Write(uart_port,sbuf,wLen);
return;
}
lastbuf[0] = rbuf[1];
lastid = dev_id;
switch(rbuf[1]&0x0f)
{
case 0x00:
//装置上电
powerflg = 0x33;
sbuf[0] = 0x10;
sbuf[1] = 0x20;
sbuf[2] = byDevAddr;
wLen = 2;
sbuf[3] = Makecrc(&sbuf[1],wLen);
sbuf[4] = 0x16;
wLen = 5;
tot_leng = wLen;
UART_Write(uart_port,sbuf,wLen);
break;
case 0x0a:
if (powerflg == 0x33)
{
//第一次回答上电表示报文
Ack_changjia(rbuf,byDevAddr,uart_port);
powerflg = 0x55;
return;
}
if (powerflg == 0x55)
{
//第二次回答上电表示报文
Ack_changjia(rbuf,byDevAddr,uart_port);
powerflg = 0x00;
return;
}
//检查是否总查询发生
if (maskflg == 0x33)
{
//asdu1
Ack_asdu1(rbuf,byDevAddr,uart_port);
return;
}
//传送描述表
if (listflg == 0x33)
{
BYTE i;
BYTE ginl;
BYTE data_leng;
T_ANALOG_ENTRY *p_analog_list;
T_SET_ENTRY *p_set_list;
T_SFC_ENTRY *p_sfc_list;
apack = sbuf;
*apack++ = 0x68;
apack++;
apack++;
*apack++ = 0x68;
crc = apack;
*apack++ = 0x28;
*apack++ = byDevAddr;
*apack++ = 0x0a;
*apack++ = 0x81;
*apack++ = 0x2a;
*apack++ = byDevAddr;
*apack++ = 0xfe;
*apack++ = 0xf1;
*apack++ = 0x00;
data_leng = 13;
*apack++ = (BYTE)list.l_size;
switch(list.l_type)
{
case LIST_T_ANALOG:
p_analog_list = (T_ANALOG_ENTRY *) list.l_ptr;
ginl = 0x01;
break;
case LIST_T_SET:
p_set_list = (T_SET_ENTRY *) list.l_ptr;
ginl = 0x04;
break;
case LIST_T_SFC:
p_sfc_list = (T_SFC_ENTRY *) list.l_ptr;
ginl = 0x06;
break;
}
i = 0;
while(i < 10)
{
if(list_num < list.l_size)
{
*apack++ = ginl;
*apack++ = list_num + 1;
*apack++ = 10;
*apack++ = 1;
*apack++ = 16;
*apack++ = 1;
data_leng += 6;
if(list.l_type == LIST_T_ANALOG)
{
memcpy(apack, p_analog_list->name,16);
apack += 16;
data_leng += 16;
list_num ++;
}
if(list.l_type == LIST_T_SET)
{
memcpy(apack, p_set_list->name,16);
apack += 16;
data_leng += 16;
list_num ++;
}
if(list.l_type == LIST_T_SFC)
{
memcpy(apack, p_sfc_list->name,16);
apack += 16;
data_leng += 16;
list_num ++;
}
i++;
}
else
break;
}
//超过10项分帧发送
sbuf[1] = data_leng;
sbuf[2] = data_leng;
if (list_num != list.l_size)
{
sbuf[13] = (i | 0x80);
sbuf[4] = 0x28;
}
else
{
sbuf[13] = (i | 0x00);
sbuf[4] = 0x08;
listflg =0;
}
wLen = data_leng;
*apack++ = Makecrc(crc,wLen);
*apack++ = 0x16;
wLen = data_leng + 6;
tot_leng = wLen;
UART_Write(uart_port,sbuf,wLen);
return;
}
//是否传送遥信量
if(diflg == 0x33)
{
BYTE i;
diflg = 0x00;
apack = sbuf;
*apack++ = 0x68;
apack++;
apack++;
*apack++ = 0x68;
crc = apack;
*apack++ = 0x08;
*apack++ = byDevAddr;
*apack++ = 0x0a;
*apack++ = 0x81;
*apack++ = 0x2a;
*apack++ = byDevAddr;
*apack++ = 0xFE;
*apack++ = 0xf1;
*apack++ = 0x00;
*apack++ = (BYTE) di.di_num;
for(i = 0;i< (di.di_num + 31)/32;i++)
{
*apack++ = 0x07;//遥信组
*apack++ = i + 1;
*apack++ = 1;
*apack++ = 7;
*apack++ = 4;
*apack++ = 1;
*apack++ = *((BYTE *)&di.di_val[i] + 3);
*apack++ = *((BYTE *)&di.di_val[i] + 2);
*apack++ = *((BYTE *)&di.di_val[i] + 1);
*apack++ = *((BYTE *)&di.di_val[i] );
}
wLen = apack - crc;
sbuf[1] = wLen + 2;
sbuf[2] = wLen + 2;
*apack++ = Makecrc(crc,wLen);
*apack++ = 0x16;
wLen = apack - sbuf;
tot_leng = wLen;
UART_Write(uart_port,sbuf,wLen);
return;
}
//是否要传送遥测值
if(measureflg == 0x33)
{
BYTE i;
measureflg = 0x00;
apack = sbuf;
*apack++ = 0x68;
apack++;
apack++;
*apack++ = 0x68;
crc = apack;
*apack++ = 0x08;
*apack++ = byDevAddr;
*apack++ = 0x0a;
*apack++ = 0x81;
*apack++ = 0x2a;
*apack++ = byDevAddr;
*apack++ = 0xFE;
*apack++ = 0xf1;
*apack++ = 0x00;
*apack++ = (BYTE) measure.ms_num;
for(i = 0;i< measure.ms_num;i++)
{
*apack++ = 0x01;//遥测组
*apack++ = i + 1;
*apack++ = 1;
*apack++ = 7;
*apack++ = 2;
*apack++ = 1;
*apack++ = (BYTE)(measure.ms_val[i]);
*apack++ = (BYTE)(measure.ms_val[i] >> 8);
}
wLen = apack - crc;
sbuf[1] = wLen + 2;
sbuf[2] = wLen + 2;
*apack++ = Makecrc(crc,wLen);
*apack++ = 0x16;
wLen = apack - sbuf;
tot_leng = wLen;
UART_Write(uart_port,sbuf,wLen);
return;
}
//检查是否要传送软压板
if(sfcflg == 0x33)
{
BYTE i;
sfcflg = 0x00;
apack = sbuf;
*apack++ = 0x68;
apack++;
apack++;
*apack++ = 0x68;
crc = apack;
*apack++ = 0x08;
*apack++ = byDevAddr;
*apack++ = 0x0a;
*apack++ = 0x81;
*apack++ = 0x2a;
*apack++ = byDevAddr;
*apack++ = 0xFE;
*apack++ = 0xf1;
*apack++ = 0x00;
*apack++ = (BYTE) sfc.sfc_num;
for(i = 0;i< sfc.sfc_num;i++)
{
*apack++ = 0x06;//压板组
*apack++ = i + 1;
*apack++ = 1;
*apack++ = 10;
*apack++ = 1;
*apack++ = 1;
*apack++ =((BYTE) (sfc.sfc_val[0] >> i)&0x00000001) + 1;
if(i == 31)
{
sfc.sfc_val[0] = sfc.sfc_val[1];
}
}
wLen = apack - crc;
*apack++ = Makecrc(crc,wLen);
*apack++ = 0x16;
wLen = apack - sbuf;
tot_leng = wLen;
UART_Write(uart_port,sbuf,wLen);
return;
}
//检查是否要传送保护定值 asdu10
if (dzflg == 0x33)
{
BYTE data_leng,i;
apack = sbuf;
*apack++ = 0x68;
apack++;
apack++;
*apack++ = 0x68;
crc = apack;
*apack++ = 0x28;
*apack++ = byDevAddr;
*apack++ = 0x0a;
*apack++ = 0x81;
*apack++ = 0x2a;
*apack++ = byDevAddr;
*apack++ = 0xFE;
*apack++ = 0xf1;
*apack++ = 0x00;
data_leng = 9;
ngd = rsetbuf.set_num;
if(ngd > 20)
{
ngd = ngd | 0x80;
}
*apack++ = (BYTE) ngd;
data_leng++;
i = 0;
while (i < 20)
{
if (dznumber < rsetbuf.set_num)
{
*apack++ = 0x04;//定值组号
data_leng++;
*apack++ = dznumber + 1;//条目号
data_leng++;
*apack++ = 0x01;//描述类别
data_leng++;
switch (rsetbuf.set_val[dznumber].type)
{
case SET_T_UINT:
*apack++ = 0x24;//ASCII码 四方
*apack++ = 0x02;
*apack++ = 0x01;
*apack++ = (BYTE) rsetbuf.set_val[dznumber].un_val.u_val;
*apack++ = (BYTE) (rsetbuf.set_val[dznumber].un_val.u_val >> 8);
dznumber++;
data_leng += 5;
break;
case SET_T_FLOAT:
*apack++ = 0x07;//float
*apack++ = 0x04;
*apack++ = 0x01;
*apack++ = *((BYTE *)&rsetbuf.set_val[dznumber].un_val.f_val + 3);
*apack++ = *((BYTE *)&rsetbuf.set_val[dznumber].un_val.f_val + 2);
*apack++ = *((BYTE *)&rsetbuf.set_val[dznumber].un_val.f_val + 1);
*apack++ = *(BYTE *)&rsetbuf.set_val[dznumber].un_val.f_val;
dznumber++;
data_leng += 7;
break;
}
i++;
}
else
{
break;
}
}
//超过20项定值分帧发
sbuf[1] = data_leng;
sbuf[2] = data_leng;
if (dznumber != rsetbuf.set_num)
{
sbuf[13] = (i | 0x80);
sbuf[4] = 0x28;
}
else
{
sbuf[13] = (i | 0x00);
sbuf[4] = 0x08;
dzflg =0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -