map/das-dn/subiec101balanced/sub_iec101_balanced.cpp
2024-07-08 10:27:17 +08:00

242 lines
8.5 KiB
C++

#include "sub_iec101_balanced.h"
/***************************************************************************************/
BOOLEAN CIEC101SecondaryBalancedProcess::OnPreCreate(int id)
{
if (!CIEC101Process::OnPreCreate(id)) return FALSE;
int i;
int uid;
CIEC101SecondaryBalancedProcessItem* pItem;
for (i = 0; i < PROCESS_UNIT_NUM; i++)
{
pItem = (CIEC101SecondaryBalancedProcessItem *)GetItem(i);
if (NULL == pItem) continue;
uid = pItem->GetUnitID();
if (uid < 0 || uid >= UNIT_NUM) continue;
BYTE phy_addr[2];
GetUnitAddr(uid, phy_addr, 2);
pItem->Attach(uid, phy_addr[0], phy_addr[0], m_option.originatorAddress); //默认公共地址和物理地址一致
pItem->setAppLayerParameters(m_option.sizeOfCOT, m_option.sizeOfCA, m_option.sizeOfIOA, m_option.maxSizeOfASDU);
Slave_setLinkLayerAddressOtherStation(pItem, phy_addr[1]);
pItem->setAppLayerIOABase();
pItem->setAppLayerDataCount(GetUnitYXCount(uid), GetUnitYCCount(uid), GetUnitYMCount(uid));
}
last_sec != (time_t)system32.timers;
return TRUE;
}
BOOLEAN CIEC101SecondaryBalancedProcess::Run(void)
{
if (!CIEC101Process::Run()) return FALSE;
FeedDog();
CIEC101ProcessItem* pItem = (CIEC101ProcessItem *)GetCurItem();
LinkLayerPrimaryBalanced_runStateMachine(pItem);
return TRUE;
}
BOOLEAN CIEC101SecondaryBalancedProcess::OnTimer(void)
{
if (!CIEC101Process::OnTimer()) return FALSE;
BOOLEAN sec_changed = FALSE;
if (last_sec != (time_t)system32.timers)
{
last_sec = (time_t)system32.timers;
sec_changed = TRUE;
}
CIEC101ProcessItem* pItem = (CIEC101ProcessItem *)GetCurItem();
if (NULL == pItem) return TRUE;
int uid = pItem->GetUnitID();
if (uid < 0 || uid >= UNIT_NUM) return TRUE;
//刷新事件记录库
GetItemEvents(pItem);
//刷新遥测库
FetchUnitYC(0);
if (pItem->interrogation_finish)
{
//总召唤结束,开始上送遥信变位
GetItemYXBWs(pItem);
//总召唤结束,开始刷新遥测变位缓冲。
if (pItem->ycbws.count <= 0)
{ //当遥测变位发送结束后才更新
GetItemYCBWs(pItem);
}
//发送遥控返校
if (MakeYKFrame(pItem)) return TRUE;
if (MakeYTFrame(pItem)) return TRUE;
if (Send_Single_point_information(pItem)) return TRUE;
if (Send_Single_point_information_with_time_tag_cp56time2a(pItem)) return TRUE;
if (!pItem->interrogation_start)
{ //变位遥测优先级在总召唤之后。
if (sec_changed)
{
switch (m_option.yc_type)
{
case USE_YC_NB: //标度化值
return Send_Measured_value_scaled(pItem);
case USE_YC_NC: //短浮点数
return Send_Measured_value_short_floating_point(pItem);
case USE_YC_ND: //不带品质归一化值
return Send_Measured_value_normalised_without_quality(pItem);
default: //USE_YC_NA: 归一化值
return Send_Measured_value_normalised(pItem);
}
}
}
}
//响应总召唤命令
if (pItem->interrogation_start)
{
if (pItem->call_type != IEC_101_104_COT_INTERROGATION)
{ //组召唤
//激活终止
Send_FrameInterrogation(pItem);
pItem->call_type = 0;
pItem->interrogation_finish = TRUE;
pItem->interrogation_start = FALSE;
pItem->interrogation_yx_fin = TRUE;
pItem->interrogation_yc_fin = TRUE;
}
else if (!pItem->interrogation_yx_fin)
{
Send_Single_point_information(pItem, IEC_101_104_COT_INTERROGATION);
}
else if (!pItem->interrogation_yc_fin)
{
switch (m_option.yc_type)
{
case USE_YC_NB: //标度化值
return Send_Measured_value_scaled(pItem, IEC_101_104_COT_INTERROGATION);
case USE_YC_NC: //短浮点数
return Send_Measured_value_short_floating_point(pItem, IEC_101_104_COT_INTERROGATION);
case USE_YC_ND: //不带品质归一化值
return Send_Measured_value_normalised_without_quality(pItem, IEC_101_104_COT_INTERROGATION);
default: //USE_YC_NA: 归一化值
return Send_Measured_value_normalised(pItem, IEC_101_104_COT_INTERROGATION);
}
}
else
{
Send_FrameInterrogation(pItem);
pItem->call_type = 0;
pItem->interrogation_finish = TRUE;
pItem->interrogation_start = FALSE;
pItem->interrogation_yx_fin = TRUE;
pItem->interrogation_yc_fin = TRUE;
}
}
else if (pItem->pulse_start)
{
if (!pItem->pulse_fin)
{
Send_Integrated_totals(pItem, IEC_101_104_COT_REQCOGEN);
}
else
{
Send_FrameCounterInterrogation(pItem);
pItem->call_type = 0;
pItem->pulse_start = FALSE;
pItem->pulse_fin = TRUE;
}
}
return TRUE;
}
//平衡方式从协议接收到主站报文
void CIEC101SecondaryBalancedProcess::LinkLayerSecondaryBalanced_ReceivedMessage(BYTE fc, BOOLEAN isBroadcast, BOOLEAN fcb, BOOLEAN fcv, int address, BYTE* msg, int userDataStart, int userDataLength)
{
CIEC101ProcessItem* pItem;
if (address == -1) pItem = (CIEC101ProcessItem *)GetCurItem();
else
{
int uid = GetUnitByAddr((BYTE *)&address, m_linkLayer.linkLayerParameters.addressLength);
if (uid < 0 || uid >= UNIT_NUM) return;
pItem = (CIEC101ProcessItem *)GetItem(GetOrderByUnitID(uid));
UnitFeedDog(uid);
}
if (pItem == NULL)
{
vLog(LOG_DEBUG, "PLL RECV - response from unknown slave %i\n", address);
return;
}
pIEC101_LinkLayerSecondaryBalanced self = &(pItem->secondaryLinkBalanced);
if (fcv)
{
if (LinkLayerSecondaryBalanced_checkFCB(self, fcb) == FALSE) return;
}
switch (fc)
{
case LL_FC_00_RESET_REMOTE_LINK:
//vLog(LOG_DEBUG, "SLL - RECV FC 00 - RESET REMOTE LINK\n");
self->expectedFcb = TRUE;
//vLog(LOG_DEBUG, "SLL - SEND FC 00 - ACK\n");
if (m_linkLayer.linkLayerParameters.useSingleCharACK)
{
SendSingleCharCharacter();
}
else
{
SendFixedFrame(LL_FC_00_ACK, pItem->address, FALSE, m_linkLayer.dir, FALSE, FALSE);
}
break;
case LL_FC_02_TEST_FUNCTION_FOR_LINK:
//vLog(LOG_DEBUG, "SLL - RECV FC 02 - TEST FUNCTION FOR LINK\n");
//vLog(LOG_DEBUG, "SLL - SEND FC 00 - ACK\n");
if (m_linkLayer.linkLayerParameters.useSingleCharACK)
{
SendSingleCharCharacter();
}
else
{
SendFixedFrame(LL_FC_00_ACK, pItem->address, FALSE, m_linkLayer.dir, FALSE, FALSE);
}
break;
case LL_FC_03_USER_DATA_CONFIRMED:
//vLog(LOG_DEBUG, "SLL - RECV FC 03 - USER DATA CONFIRMED\n");
if (userDataLength > 0)
{
if (ApplicationLayer_ReceivedData(pItem, msg, isBroadcast, userDataStart, userDataLength))
{
//vLog(LOG_DEBUG, "SLL - SEND FC 00 - ACK\n");
if (m_linkLayer.linkLayerParameters.useSingleCharACK)
{
SendSingleCharCharacter();
}
else
{
SendFixedFrame(LL_FC_00_ACK, pItem->address, FALSE, m_linkLayer.dir, FALSE, FALSE);
}
}
}
break;
case LL_FC_04_USER_DATA_NO_REPLY:
//vLog(LOG_DEBUG, "SLL -FC 04 - USER DATA NO REPLY\n");
if (userDataLength > 0)
{
ApplicationLayer_ReceivedData(pItem, msg, isBroadcast, userDataStart, userDataLength);
}
break;
case LL_FC_09_REQUEST_LINK_STATUS:
//vLog(LOG_DEBUG, "SLL - RECV FC 09 - REQUEST LINK STATUS");
//vLog(LOG_DEBUG, "SLL - SEND FC 11 - STATUS OF LINK\n");
SendFixedFrame(LL_FC_11_STATUS_OF_LINK_OR_ACCESS_DEMAND, pItem->address, FALSE, m_linkLayer.dir, FALSE, FALSE);
break;
default:
//vLog(LOG_DEBUG, "SLL - UNEXPECTED LINK LAYER MESSAGE");
//vLog(LOG_DEBUG, "SLL - SEND FC 15 - SERVICE NOT IMPLEMENTED\n");
SendFixedFrame(LL_FC_15_SERVICE_NOT_IMPLEMENTED, pItem->address, FALSE, m_linkLayer.dir, FALSE, FALSE);
break;
}
}