| | |
| | | #include "Model.h" |
| | | #include "Common.h" |
| | | #include <time.h> |
| | | #include <iostream> |
| | | #include <time.h> |
| | | #include <stdlib.h> |
| | | #include <string.h> |
| | | |
| | | |
| | | char g_szAckOkData[] = { 0, 0, 0, 0 }; |
| | | char g_szAckNgData[] = { 1, 0, 0, 0 }; |
| | | |
| | | unsigned __stdcall CimWorkThreadFunction(LPVOID lpParam) |
| | | { |
| | |
| | | m_bCimWorking = FALSE; |
| | | m_hCimWorkEvent = ::CreateEvent(NULL, TRUE, FALSE, NULL); |
| | | m_nSessionId = 1; |
| | | m_listener.onEQOffLine = nullptr; |
| | | m_listener.onEQOnLine = nullptr; |
| | | m_listener.onCommand = nullptr; |
| | | m_listener.onEQConstantRequest = nullptr; |
| | | m_listener.onEQConstantSend = nullptr; |
| | | InitializeCriticalSection(&m_criticalSection); |
| | | } |
| | | |
| | |
| | | DeleteCriticalSection(&m_criticalSection); |
| | | } |
| | | |
| | | void CHsmsPassive::setListener(SECSListener listener) |
| | | { |
| | | m_listener.onEQOffLine = listener.onEQOffLine; |
| | | m_listener.onEQOnLine = listener.onEQOnLine; |
| | | m_listener.onCommand = listener.onCommand; |
| | | m_listener.onEQConstantRequest = listener.onEQConstantRequest; |
| | | m_listener.onEQConstantSend = listener.onEQConstantSend; |
| | | } |
| | | |
| | | void CHsmsPassive::setActionTimeout(int nSecond) |
| | | { |
| | | m_nActionTimeout = max(3, nSecond); |
| | | } |
| | | |
| | | void CHsmsPassive::setEquipmentModelType(const char* pszMode) |
| | | { |
| | | m_strEquipmentModelType = pszMode; |
| | | if (m_strEquipmentModelType.length() > 20) { |
| | | m_strEquipmentModelType = m_strEquipmentModelType.substr(0, 20); |
| | | } |
| | | } |
| | | |
| | | void CHsmsPassive::setSoftRev(const char* pszRev) |
| | | { |
| | | m_strSoftRev = pszRev; |
| | | if (m_strSoftRev.length() > 20) { |
| | | m_strSoftRev = m_strSoftRev.substr(0, 20); |
| | | } |
| | | |
| | | } |
| | | |
| | | void CHsmsPassive::OnTimer(UINT nTimerid) |
| | |
| | | |
| | | int CHsmsPassive::onRecvMsg(IMessage* pMessage) |
| | | { |
| | | LOGI("onRecvMsg:%s", pMessage->toString()); |
| | | Lock(); |
| | | CHsmsAction* pAction = nullptr; |
| | | for (auto iter = m_listActionSent.begin(); iter != m_listActionSent.end(); iter++) { |
| | |
| | | LOGI("<HSMS>收到消息 S%dF%d", nStream, pHeader->function); |
| | | if (nStream == 1 && pHeader->function == 1) { |
| | | // S1F1 |
| | | replyAreYouThere(pHeader->systemBytes); |
| | | replyAreYouThere(pMessage); |
| | | } |
| | | else if (nStream == 1 && pHeader->function == 13) { |
| | | replyEstablishCommunications(pHeader->systemBytes); |
| | | replyEstablishCommunications(pMessage); |
| | | } |
| | | else if (nStream == 1 && pHeader->function == 15) { |
| | | replyOffLine(pMessage); |
| | | } |
| | | else if (nStream == 1 && pHeader->function == 17) { |
| | | replyOnLine(pMessage); |
| | | } |
| | | else if (nStream == 2 && pHeader->function == 13) { |
| | | replyEquipmentConstantRequest(pMessage); |
| | | } |
| | | else if (nStream == 2 && pHeader->function == 15) { |
| | | replyEquipmentConstantSend(pMessage); |
| | | } |
| | | else if (nStream == 2 && pHeader->function == 31) { |
| | | replyDatetime(pMessage); |
| | | } |
| | | else if (nStream == 2 && pHeader->function == 37) { |
| | | replyEanbleDisableEventReport(pMessage); |
| | | } |
| | | else if (nStream == 2 && pHeader->function == 41) { |
| | | replyCommand(pMessage); |
| | | } |
| | | else if (nStream == 5 && pHeader->function == 3) { |
| | | replyEanbleDisableAlarmReport(pMessage); |
| | | } |
| | | else if (nStream == 7 && pHeader->function == 19) { |
| | | replyQueryPPIDList(pMessage); |
| | | } |
| | | else if (nStream == 10 && pHeader->function == 3) { |
| | | replyTerminalDisplay(pMessage); |
| | | } |
| | | }; |
| | | |
| | |
| | | return 0; |
| | | } |
| | | |
| | | // 通用的reply ack函数 |
| | | void CHsmsPassive::replyAck(int s, int f, unsigned int systemBytes, BYTE ack, const char* pszAckName) |
| | | { |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, s, f, systemBytes); |
| | | ASSERT(pMessage); |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | | pItem->setBinary((const char*)&ack, 1, pszAckName); |
| | | m_pPassive->sendMessage(pMessage); |
| | | LOGI("<HSMS>[SECS Msg SEND]S%dF%d (SysByte=%u)", s, f, systemBytes); |
| | | HSMS_Destroy1Message(pMessage); |
| | | } |
| | | |
| | | // S1F1 |
| | | int CHsmsPassive::requestAreYouThere() |
| | | { |
| | |
| | | } |
| | | |
| | | // S1F2 |
| | | int CHsmsPassive::replyAreYouThere(unsigned int systemBytes) |
| | | int CHsmsPassive::replyAreYouThere(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 1, 2, systemBytes); |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 1, 2, pRecv->getHeader()->systemBytes); |
| | | ASSERT(pMessage); |
| | | |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | |
| | | return 0; |
| | | } |
| | | |
| | | // S1F14 |
| | | int CHsmsPassive::replyEstablishCommunications(unsigned int systemBytes) |
| | | // S1F15 |
| | | int CHsmsPassive::replyOffLine(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | |
| | | // 交由上层应用来获取机器常量值 |
| | | if (m_listener.onEQOffLine != nullptr) { |
| | | m_listener.onEQOffLine(this); |
| | | } |
| | | |
| | | |
| | | // 回复 |
| | | replyAck(1, 16, pRecv->getHeader()->systemBytes, BYTE(0), "OFLACK"); |
| | | return 0; |
| | | } |
| | | |
| | | // S1F17 |
| | | int CHsmsPassive::replyOnLine(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | |
| | | // 交由上层应用来获取机器常量值 |
| | | if (m_listener.onEQOnLine != nullptr) { |
| | | m_listener.onEQOnLine(this); |
| | | } |
| | | |
| | | |
| | | // 回复 |
| | | replyAck(1, 18, pRecv->getHeader()->systemBytes, BYTE(0), "ONLACK"); |
| | | return 0; |
| | | } |
| | | |
| | | int CHsmsPassive::replyEstablishCommunications(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 1, 14, systemBytes); |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 1, 14, pRecv->getHeader()->systemBytes); |
| | | ASSERT(pMessage); |
| | | |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | | pItem->addBinaryItem(g_szAckOkData, 1, "COMMACK"); |
| | | pItem->addBinaryItem(BYTE(0), "COMMACK"); |
| | | ISECS2Item* pList = pItem->addItem(); |
| | | pList->addItem(m_strEquipmentModelType.c_str(), "MDLN"); |
| | | pList->addItem(m_strSoftRev.c_str(), "SOFTREV"); |
| | |
| | | return 0; |
| | | } |
| | | |
| | | // S2F13 |
| | | int CHsmsPassive::replyEquipmentConstantRequest(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | |
| | | // 要获取的常量表表 |
| | | BOOL bCheckData = FALSE; |
| | | std::vector<EQConstant> eqcs; |
| | | { |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | int ecidSize = pItem->getSubItemSize(); |
| | | for (int i = 0; i < ecidSize; i++) { |
| | | EQConstant eqc; |
| | | unsigned short id; |
| | | if (pItem->getSubItemU2(i, id)) { |
| | | eqc.id = id; |
| | | eqcs.push_back(eqc); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // 交由上层应用来获取机器常量值 |
| | | if (m_listener.onEQConstantRequest != nullptr) { |
| | | m_listener.onEQConstantRequest(this, eqcs); |
| | | } |
| | | |
| | | |
| | | // 回复 |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 1, 14, pRecv->getHeader()->systemBytes); |
| | | ASSERT(pMessage); |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | | for (auto& item : eqcs) { |
| | | pItem->addItem(item.szValue, "ECV"); |
| | | } |
| | | |
| | | m_pPassive->sendMessage(pMessage); |
| | | LOGI("<HSMS>[SECS Msg SEND]S2F14 (SysByte=%u)", pMessage->getHeader()->systemBytes); |
| | | HSMS_Destroy1Message(pMessage); |
| | | |
| | | return 0; |
| | | } |
| | | |
| | | // S2F15 |
| | | int CHsmsPassive::replyEquipmentConstantSend(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | |
| | | // 要设置的常量表表 |
| | | BOOL bCheckData = FALSE; |
| | | std::vector<EQConstant> eqcs; |
| | | { |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | int ecidSize = pItem->getSubItemSize(); |
| | | for (int i = 0; i < ecidSize; i++) { |
| | | ISECS2Item* pItemEqc = pItem->getSubItem(i); |
| | | if (pItemEqc != nullptr) { |
| | | EQConstant eqc; |
| | | unsigned short eqcid; |
| | | const char* pszValue; |
| | | if (pItemEqc->getSubItemU2(0, eqcid) |
| | | && pItemEqc->getSubItemString(1, pszValue)) { |
| | | eqc.id = eqcid; |
| | | strcpy_s(eqc.szValue, 256, pszValue); |
| | | eqcs.push_back(eqc); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // 交由上层应用来保存和设置机器常量值 |
| | | std::vector<unsigned int> ecvs; |
| | | if (m_listener.onEQConstantSend != nullptr) { |
| | | m_listener.onEQConstantSend(this, eqcs); |
| | | } |
| | | |
| | | |
| | | // 回复 |
| | | replyAck(2, 16, pRecv->getHeader()->systemBytes, BYTE(0), "EACK"); |
| | | return 0; |
| | | } |
| | | |
| | | // S2F31 |
| | | #include <iostream> |
| | | #include <time.h> |
| | | #include <stdlib.h> |
| | | #include <string.h> |
| | | int CHsmsPassive::replyDatetime(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | |
| | | } |
| | | ISECS2Item* pBody = pRecv->getBody(); |
| | | if (pBody == nullptr || pBody->getType() != SITYPE::A) ER_PARAM_ERROR; |
| | | char* pszMessage; |
| | | const char* pszMessage; |
| | | if (pBody->getString(pszMessage)) { |
| | | // 更新时间 |
| | | SYSTEMTIME time; |
| | |
| | | SetLocalTime(&time); |
| | | } |
| | | |
| | | replyAck(2, 32, pRecv->getHeader()->systemBytes, BYTE(0), "TIACK"); |
| | | return 0; |
| | | } |
| | | |
| | | // S2F37 |
| | | int CHsmsPassive::replyEanbleDisableEventReport(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | ISECS2Item* pBody = pRecv->getBody(); |
| | | if (pBody == nullptr || pBody->getType() != SITYPE::A) ER_PARAM_ERROR; |
| | | |
| | | |
| | | |
| | | BOOL bCheckData = FALSE; |
| | | bool bEnable; |
| | | std::vector<unsigned int> ids; |
| | | { |
| | | ISECS2Item* pItemIds; |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | if (pItem->getSubItemSize() < 2) goto MYREPLY; |
| | | if (!pItem->getSubItemBool(0, bEnable)) goto MYREPLY; |
| | | pItemIds = pItem->getSubItem(1); |
| | | if (pItemIds == nullptr || pItemIds->getType() != SITYPE::L) goto MYREPLY; |
| | | for (int i = 0; i < pItemIds->getSubItemSize(); i++) { |
| | | unsigned int id; |
| | | if (pItemIds->getSubItemU4(i, id)) { |
| | | ids.push_back(id); |
| | | } |
| | | } |
| | | bCheckData = TRUE; |
| | | LOGI("EanbleDisableAlarm bEnable:%s", bEnable ? _T("YES") : _T("NO")); |
| | | for (auto item : ids) { |
| | | LOGI("ID:%u", item); |
| | | } |
| | | } |
| | | |
| | | |
| | | MYREPLY: |
| | | replyAck(2, 38, pRecv->getHeader()->systemBytes, BYTE(0), "ERACK"); |
| | | return 0; |
| | | } |
| | | |
| | | // S2F41 |
| | | int CHsmsPassive::replyCommand(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | ISECS2Item* pBody = pRecv->getBody(); |
| | | if (pBody == nullptr || pBody->getType() != SITYPE::A) ER_PARAM_ERROR; |
| | | |
| | | |
| | | |
| | | BOOL bCheckData = FALSE; |
| | | const char* pszCmdName; |
| | | std::vector<CommandParameter> params; |
| | | { |
| | | ISECS2Item* pItemParams, *pItemParam; |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | if (pItem->getSubItemSize() < 2) goto MYREPLY; |
| | | if (!pItem->getSubItemString(0, pszCmdName)) goto MYREPLY; |
| | | pItemParams = pItem->getSubItem(1); |
| | | if (pItemParams == nullptr || pItemParams->getType() != SITYPE::L) goto MYREPLY; |
| | | for (int i = 0; i < pItemParams->getSubItemSize(); i++) { |
| | | const char* pszParamName, * pszParamValue; |
| | | pItemParam = pItemParams->getSubItem(i); |
| | | if (pItemParam != nullptr |
| | | && pItemParam->getSubItemString(0, pszParamName) |
| | | && pItemParam->getSubItemString(1, pszParamValue)) { |
| | | CommandParameter cp; |
| | | strcpy_s(cp.szName, 256, pszParamName); |
| | | strcpy_s(cp.szValue, 256, pszParamValue); |
| | | params.push_back(cp); |
| | | } |
| | | } |
| | | bCheckData = TRUE; |
| | | } |
| | | |
| | | |
| | | // 回调到应用层 |
| | | if (bCheckData) { |
| | | if (m_listener.onCommand != nullptr) { |
| | | m_listener.onCommand(this, pszCmdName, params); |
| | | } |
| | | } |
| | | |
| | | MYREPLY: |
| | | replyAck(2, 42, pRecv->getHeader()->systemBytes, BYTE(0), "ERACK"); |
| | | return 0; |
| | | } |
| | | |
| | | // S5F3 |
| | | int CHsmsPassive::replyEanbleDisableAlarmReport(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | ISECS2Item* pBody = pRecv->getBody(); |
| | | if (pBody == nullptr || pBody->getType() != SITYPE::A) ER_PARAM_ERROR; |
| | | |
| | | |
| | | |
| | | BOOL bCheckData = FALSE; |
| | | const char* ALED; |
| | | unsigned int ALID; |
| | | unsigned int ALEDLEN; |
| | | { |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | if (pItem->getSubItemSize() < 2) goto MYREPLY; |
| | | if (!pItem->getSubItemBinary(0, ALED, ALEDLEN)) goto MYREPLY; |
| | | if (!pItem->getSubItemU4(1, ALID)) goto MYREPLY; |
| | | bCheckData = TRUE; |
| | | LOGI("EanbleDisableAlarmReport ALED:0x%02x, ALID:%d", ALED[0], ALID); |
| | | |
| | | double d; |
| | | float f; |
| | | pItem->getSubItemF4(2, f); |
| | | pItem->getSubItemF8(3, d); |
| | | LOGI("EanbleDisableAlarmReport d:%lf, f:%f", |
| | | d, f); |
| | | /* |
| | | unsigned long long n1; |
| | | unsigned int n2; |
| | | unsigned short n3; |
| | | unsigned char n4; |
| | | long long sn1; |
| | | int sn2; |
| | | short sn3; |
| | | char sn4; |
| | | pItem->getSubItemU8(2, n1); |
| | | pItem->getSubItemU4(3, n2); |
| | | pItem->getSubItemU2(4, n3); |
| | | pItem->getSubItemU1(5, n4); |
| | | pItem->getSubItemI8(6, sn1); |
| | | pItem->getSubItemI4(7, sn2); |
| | | pItem->getSubItemI2(8, sn3); |
| | | pItem->getSubItemI1(9, sn4); |
| | | |
| | | LOGI("EanbleDisableAlarmReport n1:%llu, n2:%u, n3:%hu, n4:%hhu", |
| | | n1, n2, n3, n4); |
| | | LOGI("EanbleDisableAlarmReport sn1:%lld, sn2:%d, sn3:%hd, sn4:%hhd", |
| | | sn1, sn2, sn3, sn4); |
| | | */ |
| | | } |
| | | |
| | | |
| | | MYREPLY: |
| | | replyAck(5, 4, pRecv->getHeader()->systemBytes, BYTE(0), "ACKC5"); |
| | | return 0; |
| | | } |
| | | |
| | | // S7F19 |
| | | int CHsmsPassive::replyQueryPPIDList(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 2, 32, pRecv->getHeader()->systemBytes); |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 7, 20, pRecv->getHeader()->systemBytes); |
| | | ASSERT(pMessage); |
| | | |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | | pItem->setBinary(g_szAckOkData, 1, "TIACK"); |
| | | pItem->addItem("banana1", "PPID1"); |
| | | pItem->addItem("banana2", "PPID2"); |
| | | pItem->addF8Item(-123.45, "PPID2"); |
| | | pItem->addF4Item(-568.99f, "PPID2"); |
| | | pItem->addF8Item(456.456, "PPID2"); |
| | | pItem->addF4Item(123.123f, "PPID2"); |
| | | m_pPassive->sendMessage(pMessage); |
| | | LOGI("<HSMS>[SECS Msg SEND]S2F32 (SysByte=%u)", pRecv->getHeader()->systemBytes); |
| | | LOGI("<HSMS>[SECS Msg SEND]S7F20 (SysByte=%u)", pMessage->getHeader()->systemBytes); |
| | | HSMS_Destroy1Message(pMessage); |
| | | |
| | | return 0; |
| | | } |
| | | |
| | | // S10F3 |
| | | int CHsmsPassive::replyTerminalDisplay(IMessage* pRecv) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | ISECS2Item* pBody = pRecv->getBody(); |
| | | if (pBody == nullptr || pBody->getType() != SITYPE::A) ER_PARAM_ERROR; |
| | | |
| | | |
| | | |
| | | BOOL bCheckData = FALSE; |
| | | const char* tid; |
| | | unsigned int tidlen; |
| | | const char* pszText = nullptr;; |
| | | { |
| | | ISECS2Item* pItem = pRecv->getBody(); |
| | | if (pItem->getSubItemSize() < 2) goto MYREPLY; |
| | | if (!pItem->getSubItemBinary(0, tid, tidlen)) goto MYREPLY; |
| | | if (!pItem->getSubItemString(1, pszText)) goto MYREPLY; |
| | | bCheckData = TRUE; |
| | | LOGI("TerminalDisplay tid:0x%02x, pszText:%s", tid[0], pszText); |
| | | m_pModel->notifyText(RX_HSMS_TERMINAL_TEXT, pszText); |
| | | } |
| | | |
| | | |
| | | MYREPLY: |
| | | replyAck(10, 4, pRecv->getHeader()->systemBytes, BYTE(0), "ACKC10"); |
| | | return 0; |
| | | } |
| | | |
| | | // S5F1 |
| | | int CHsmsPassive::requestAlarmReport(int ALCD, int ALID, const char* ALTX) |
| | | { |
| | | if (m_pPassive == NULL || STATE::SELECTED != m_pPassive->getState()) { |
| | | return ER_NOTSELECT; |
| | | } |
| | | |
| | | Lock(); |
| | | CHsmsAction* pAction = new CHsmsAction(ACTION_ALARM_REPORT, TRUE, m_nActionTimeout); |
| | | m_listAction.push_back(pAction); |
| | | IMessage* pMessage = NULL; |
| | | HSMS_Create1Message(pMessage, m_nSessionId, 5 | REPLY, 1, ++m_nSystemByte); |
| | | ASSERT(pMessage); |
| | | ISECS2Item* pItem = pMessage->getBody(); |
| | | pItem->addBinaryItem(BYTE(ALCD & 0xff), "ALCD"); |
| | | pItem->addU4Item(ALID, "ALID"); |
| | | pItem->addItem(ALTX, "ALTX"); |
| | | pAction->setSendMessage(pMessage); |
| | | |
| | | SetEvent(m_hCimWorkEvent); |
| | | Unlock(); |
| | | |
| | | return ER_NOERROR; |
| | | } |
| | | |
| | | |