📄 tcp103.cpp
字号:
/******************************************************************
* Copyright (c) 2004-2005, 许继日立公司
* All rights reserved.
*
* 文件名称:tcp103.cpp
* 文件标识:
* 摘 要:tcp103类。主要处理103应用层信息,链路层套用104。
*
* 当前版本:1.0
* 作 者:李龙伟 <lilongwei1@hotmail.com>
* 完成日期:2004年11月24日
*
* 取代版本:1.0
* 原作者 :李龙伟
* 完成日期:2004年11月24日
******************************************************************/
#include "tcp103.h"
#include "ntdef.h"
#include "ext.h"
/*====================================================================================
*
* Subroutine : CTcp103()
*
* Parameters :
*
*
* Called from :
*
* Description : CTcp103类构造函数
*
* Return :
*
* Modification:
* 2004-11-24:
*
*====================================================================================*/
CTcp103::CTcp103(BYTE no, short rlen, short slen) : BaseRule(no,rlen,slen)
{
m_wSendCount = 0;
m_wRevCount = 0;
m_bRii = 0;
m_bDataSend = false; //是否连接标志
m_bFrameLen = 0;
memset(&m_bFrameBuf, 0x00, sizeof(unsigned char)*0x100);
memset(&m_bYXInfBuf, 0x00, sizeof(BYTE)*512);
memset(&m_bSector, 0x00, sizeof(BYTE)*512);
ReadYXInf103();
}
/*====================================================================================
*
* Subroutine : ~CTcp103()
*
* Parameters :
*
*
* Called from :
*
* Description : CTcp103类析构函数
*
* Return :
*
* Modification:
* 2004-11-24:
*
*====================================================================================*/
CTcp103::~CTcp103()
{
}
/*====================================================================================
*
* Subroutine : RuleLoop()
*
* Parameters :
*
*
* Called from : Rule_Data()
*
* Description : tcp103数据大循环函数
*
* Return :
*
* Modification:
* 2004-11-24:
*
*====================================================================================*/
void CTcp103::RuleLoop()
{
int nResult = 0; //返回值
int nResult1 = 0; //返回值
bool bConnect = false; //连接成功
unsigned long i_start; //收到报文判断开始
unsigned long i_end; //结束时间
int tstop = 30;//??????
i_start = GetTickCount(); //初始化
i_end = GetTickCount(); //初始化
//延时5秒钟,等待CDT规约连接正常
Sleep(5000);
while (1)
{
if (g_bSysStop)
{
break;
}
if (BaseConnect(CHANNEL_SOCK) == 0)
{
Sleep(10);
continue;
}
while (1)
{
Sleep(10);
nResult = BaseRead(1, 0, CHANNEL_SOCK);
if ( nResult > 0 )
{
///////////////////////////
printf("receive \n");
for (int i=0; i<m_wRevLen; i++)
{
printf("%02x ", m_bRevBuf[i]);
}
printf("\n");
///////////////////////////
do
{
nResult = CheckRevData();
if (nResult != 0)
{
nResult1 = TcpHeart();
if ((nResult1 == 0)
&& (m_bDataSend))
{
UnpackData();
}
else if (m_bDataSend)
{
GetYC();
}
SetNetState(GATE_CLOSE);
i_start = GetTickCount();
bConnect = true;
PackData();
///////////////////////////
printf("send \n");
for (int i=0; i<m_wSendLen; i++)
{
printf("%02x ", m_bSendBuf[i]);
}
printf("\n");
///////////////////////////
}
else
{
i_end = GetTickCount();
if (((i_end-i_start) / 1000) > tstop)
{
SetNetState(GATE_UNCLOSE);
m_bDataSend = false; //连接失败
bConnect = false;
break;
}
}
}while(m_wRevLen != 0);
if (!bConnect)
{
break;
}
}
else
{
i_end = GetTickCount();
if ((i_end-i_start) / 1000 > tstop)
{
m_bDataSend = false; //连接失败
bConnect = false;
SetNetState(GATE_UNCLOSE);
break;
}
}
// PackData();
}
}
}
/*====================================================================================
*
* Subroutine : CheckRevData()
*
* Parameters :
*
*
* Called from : RuleLoop()
*
* Description : 校验收到的数据是否正确
*
* Return : 0 不正确
* !=0 正确
* Modification:
* 2004-12-03:
*
*====================================================================================*/
int CTcp103::CheckRevData(void)
{
unsigned int nLength = 0; //长度
unsigned char nResult = 0; //起始符
nLength = m_bRevBuf[1];
if ((m_bRevBuf[0] == 0x68)
|| (m_wRevLen >= (nLength+2)))
{
m_bFrameLen = nLength + 2;
memcpy(&m_bFrameBuf[0], &m_bRevBuf[0], m_bFrameLen);
memcpy(&m_bRevBuf[0], &m_bRevBuf[m_bFrameLen], m_wRevLen-m_bFrameLen);
m_wRevLen -= m_bFrameLen;
nResult = 1;
}
else
{
m_wRevLen = 0;
}
return nResult;
}
/*====================================================================================
*
* Subroutine : TcpHeart()
*
* Parameters :
*
*
* Called from : UnpackData()
*
* Description : 控制域数据处理
*
* Return : 0 数据没有处理完,需要应用层数据
* !0 数据已经处理完并打包
* Modification:
* 2004-12-13:
*
*====================================================================================*/
int CTcp103::TcpHeart(void)
{
int nResult = 0; //返回值
int iLength = 0; //数据长度
unsigned char bType1 = 0;//报文类型
unsigned char bType2 = 0;//报文类型
bool bStart = false; //开始标志
bool bStop = false; //结束标志
bool bTest = false; //测试标志
DATA_STR DataInfo; //数据信息格式
memset(&DataInfo, 0x00, sizeof(DATA_STR));
iLength = m_bFrameBuf[1];
bType1 = m_bFrameBuf[2] & 0x01;
m_wRevCount+=2; //最低位未使用
// m_wSendCount+=2; //最低位未使用
//固定长的报文格式
if (bType1 != 0)
{
nResult = 1;
if (m_bFrameBuf[2] & 0x04)
{
bStart = true;
}
if (m_bFrameBuf[2] & 0x10)
{
bStop = true;
}
if (m_bFrameBuf[2] & 0x40)
{
bTest = true;
}
DataInfo.ApduHead.bStartCode = 0x68;
DataInfo.ApduHead.bApduLength = 0x04;
DataInfo.ApduHead.bControlCode2 = 0;
DataInfo.ApduHead.bControlCode3 = 0;
DataInfo.ApduHead.bControlCode4 = 0;
bType2 = m_bFrameBuf[2] & 0x02;
if ( (iLength == 4)
&& (bType2!=0x00)
&& (bStart)
&& (!bTest))
{
m_bDataSend = true;
DataInfo.ApduHead.bControlCode1 = 0x0b;
m_SendList.push_back(DataInfo);
ID_State(m_iAddress, 1);////////////////??
}
else if ((iLength == 4)
&& (bType2 != 0x00)
&& (bStop))
{
m_bDataSend = false;
DataInfo.ApduHead.bControlCode1 = 0x23;
m_SendList.push_back(DataInfo);
}
else if ( (iLength == 4)
&& (bType2 != 0x00)
&& (bTest))
{
DataInfo.ApduHead.bControlCode1 = 0x83;
m_SendList.push_back(DataInfo);
}
else
{
DataInfo.ApduHead.bControlCode1 = 1;
DataInfo.ApduHead.bControlCode3 = m_wRevCount % 0x100;
DataInfo.ApduHead.bControlCode4 = m_wRevCount / 0x100;
m_SendList.push_back(DataInfo);
}
}
return nResult;
}
/*====================================================================================
*
* Subroutine : UnpackData()
*
* Parameters :
*
*
* Called from : RuleLoop()
*
* Description : 对103数据进行解包处理
*
* Return :
*
* Modification:
* 2004-12-03:
*
*====================================================================================*/
void CTcp103::UnpackData(void)
{
unsigned char bFrameType = 0; //帧类型
unsigned char bInf = 0; //信息序号
bInf = m_bFrameBuf[13];
bFrameType = m_bFrameBuf[6];
switch (bFrameType)
{
case CMDCODE_GI_103: //总召唤
GeneralInquire();
break;
case CMDCODE_TIME_103: //时间同步
CalibrateTime();
m_wSendCount += 2; //最低位未使用
break;
case CMDCODE_NORMAL_103: //一般命令,复归使用
NormalCommand();
m_wSendCount += 2; //最低位未使用
break;
case CMDCODE_BREAK_103: //断路器控制
case CMDCODE_SWITCH_103: //调压开关升降
RtuControl();
m_wSendCount += 2; //最低位未使用
break;
case CMDCODE_VALUE_103: //定值命令
SettingOperate(bInf);
m_wSendCount += 2; //最低位未使用
break;
case CMDCODE_REPORT_103: //故障报告
break;
case CMDCODE_AMMETER_103: //电度信息
break;
case CMDCODE_FREEZE_103: //电度冻结
break;
case CMDCODE_CHECK_103: //自检与运行事件信息
break;
default:
break;
}
return;
}
/*====================================================================================
*
* Subroutine : PackData()
*
* Parameters :
*
*
* Called from : RuleLoop()
*
* Description : 对103数据进行打包处理
*
* Return :
*
* Modification:
* 2004-12-03:
*
*====================================================================================*/
void CTcp103::PackData(void)
{
int i = 0; //一般变量
int bLength = 0;//存储的值长度
int ret = 0; //返回值变量
unsigned char index = 0; //序号
DATA_STR DataInfo; //数据信息格式
memset(&DataInfo, 0x00, sizeof(DATA_STR));
ret = PutSendList();
while (!m_SendList.empty())
{
DataInfo = m_SendList.front();
m_SendList.pop_front();
m_bSendBuf[index++] = DataInfo.ApduHead.bStartCode;
m_bSendBuf[index++] = DataInfo.ApduHead.bApduLength;
m_bSendBuf[index++] = DataInfo.ApduHead.bControlCode1;
m_bSendBuf[index++] = DataInfo.ApduHead.bControlCode2;
m_bSendBuf[index++] = DataInfo.ApduHead.bControlCode3;
m_bSendBuf[index++] = DataInfo.ApduHead.bControlCode4;
if (DataInfo.ApduHead.bApduLength > 4)
{
m_bSendBuf[index++] = DataInfo.AsduHead.bAsduType;
m_bSendBuf[index++] = DataInfo.AsduHead.bAsduVsq;
m_bSendBuf[index++] = DataInfo.AsduHead.nAsduCot % 0x100;
m_bSendBuf[index++] = DataInfo.AsduHead.nAsduCot / 0x100;
m_bSendBuf[index++] = DataInfo.AsduHead.nAsduComAddr % 0x100;//单元公共地址//??
m_bSendBuf[index++] = DataInfo.AsduHead.nAsduComAddr / 0x100;//单元公共地址 //??
m_bSendBuf[index++] = DataInfo.AsduHead.bAsduFun;//fun
m_bSendBuf[index++] = DataInfo.AsduHead.bAsduInf;//inf
bLength = DataInfo.bDataVec.size();
for (i=0; i<bLength; ++i)
{
m_bSendBuf[index++] = DataInfo.bDataVec[i];
}
}
m_wSendLen = index;
BaseSend(CHANNEL_SOCK);
}
return;
}
/*====================================================================================
*
* Subroutine : GeneralInquire()
*
* Parameters :
*
*
* Called from : RuleLoop()
*
* Description : 总召唤响应
*
* Return :
*
*
* Modification:
* 2004-07-29:
*
*====================================================================================*/
void CTcp103::GeneralInquire(void)
{
int i = 0; //常用变量
int nResult; //常用变量,返回值
int nNumber; //遥信数量
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -