#include "stdafx.h" #include "DataMate3000.h" CDataMate3000::CDataMate3000(char *szPath,char *szIniName,int nCommPort,int nAddr,int nRate,int nDataBit,int nStopBit,int nParity,int nInterval) { #if IS_USE_READMSG_CS InitializeCriticalSection( &m_csReadMsg ); //初始化一个临界资源对象 #endif MTVERIFY( m_hSemComm = CreateEvent( NULL, TRUE, TRUE, 0 ) ); //CreateEvent()创建或打开一个命名的或无名的事件对象 for( int i = 0; i < MAX_ADDR; i++ ) { memset(m_szDataMate3000_42Msg[i], 0, sizeof(m_szDataMate3000_42Msg[i])); memset(m_szDataMate3000_43Msg[i], 0, sizeof(m_szDataMate3000_43Msg[i])); memset(m_szDataMate3000_47Msg[i], 0, sizeof(m_szDataMate3000_47Msg[i])); memset(m_szDataMate3000_4DMsg[i], 0, sizeof(m_szDataMate3000_4DMsg[i])); memset(m_szDataMate3000_82Msg[i], 0, sizeof(m_szDataMate3000_82Msg[i])); memset(m_szDataMate3000_45Msg[i], 0, sizeof(m_szDataMate3000_45Msg[i])); m_devOnline[i] = TRUE; m_dwOnlineTick[i] = 0; } } CDataMate3000::~CDataMate3000() { #if IS_USE_READMSG_CS DeleteCriticalSection( &m_csReadMsg ); #endif MTVERIFY( CloseHandle( m_hSemComm ) ); CloseComm(); } BOOL CDataMate3000::DataMate3000OpenComm(int nCommPort, int nAddr, int nRate, int nDataBit, int nStopBit, int nParity, int nInterval) { BOOL bResult = FALSE; bResult = OpenComm( nCommPort, nAddr, nRate, nDataBit, nStopBit, nParity, nInterval ); //LOG4C((LOG_NOTICE,"DME3000 DataMate3000OpenComm::%d",bResult)); return bResult; } int CDataMate3000::GetIniInfo(char *szPath,char *szIniName,char *szCmd,char *IniSendCMD,int &IniSendlen,char *szDataType,int &nIndex,int &nLen, int &iSBit, int &iEBit) { CHAR szFile[MAX_PATH + 1] = ""; wsprintf(szFile, "%s\\config\\%s", szPath, szIniName); IniSendlen = GetPrivateProfileString(szCmd, "SendCmd", "", IniSendCMD, 10, szFile); // 返回的字符串是以\0结束的; GetPrivateProfileString(szCmd, "type", "", szDataType, 10, szFile); szDataType[strlen(szDataType)] = '\0'; nIndex = GetPrivateProfileInt(szCmd, "Index", 0, szFile); nLen = GetPrivateProfileInt(szCmd, "Len", 0, szFile); iSBit = GetPrivateProfileInt(szCmd, "StaBit", 0, szFile);//从配置文件中取值 iEBit = GetPrivateProfileInt(szCmd, "EndBit", 0, szFile); return 0; } void lowcase2uppcase(BYTE &btSrc) { if( btSrc >= 'a' && btSrc <= 'z' ) btSrc = btSrc - 'a' + 'A'; } void CDataMate3000::GetDME3000Check(char *szData, char *szCheck ,int nlen /* = 12 */) { DWORD dwSum(0); for (int i(0); i < nlen; i++) dwSum += szData[i] ; WORD iCompliment = dwSum; iCompliment = ~iCompliment;//取反 iCompliment++; itoa(iCompliment, szCheck, 16); for (int i(0); i < 5 ; i++) lowcase2uppcase((BYTE &)szCheck[i]); } int CDataMate3000::SendReadRequest( char *szPath, char *szIniName, int nCommPort, int nAddr, char *szCmd, char *szMsg, int nReversed1, int nReversed2, int nReversed3, int nReversed4, int nReversed5, float fReversed1, float fReversed2, float fReversed3, char *szReversed1, char *szReversed2, char *szReversed3, char *szReversed4, char *szReversed5 ) { CCommProcess *pComm = FindComm(nCommPort); if( pComm == NULL ) return -1; int nRet = -1; int nIndex(0), nLen(0), IniSendlen(0),iSBit(0), iEBit(0); char IniSendCMD[MAX_CMD] = {0}, szDataType[CMD_TYPE] = {0}; GetIniInfo(szPath,szIniName,szCmd,IniSendCMD,IniSendlen,szDataType,nIndex,nLen,iSBit,iEBit); int iCmd = atoi(szCmd+4); if( nAddr < 1 ) return -1; if( (strlen(m_szDataMate3000_42Msg[nAddr -1]) == 0 && (iCmd >= 1 && iCmd <= 3)) || iCmd == 1 || (strlen(m_szDataMate3000_43Msg[nAddr -1]) == 0 && (iCmd ==4)) || iCmd == 4 || (strlen(m_szDataMate3000_47Msg[nAddr -1]) == 0 && (iCmd >= 5 && iCmd <= 10)) || iCmd == 5 || (strlen(m_szDataMate3000_4DMsg[nAddr -1]) == 0 && (iCmd >= 11 && iCmd <= 16)) || iCmd == 11 || (strlen(m_szDataMate3000_82Msg[nAddr -1]) == 0 && (iCmd >= 17 && iCmd <= 43)) || iCmd == 17 ) { nRet = GetDeviceParam( nAddr,pComm,szCmd,IniSendCMD,IniSendlen ); if( nRet != 0 ) { LOG4C((LOG_NOTICE,"DME3000 GetDeviceParam::Error")); return nRet; } } if( GetTickCount() - m_dwOnlineTick[nAddr - 1] > 60 *1000 && m_dwOnlineTick[nAddr - 1] > 0 ) { m_devOnline[nAddr - 1] = FALSE; } else if( GetTickCount() - m_dwOnlineTick[nAddr - 1] < 60 *1000 && m_dwOnlineTick[nAddr - 1] > 0 ) { m_devOnline[nAddr - 1] = TRUE; } if( m_devOnline[nAddr - 1] == FALSE ) { return -1; } nRet = GetDataMate3000_42VarMsg(nAddr, szCmd, szMsg, nIndex, nLen, szDataType,iSBit, iEBit); nRet = GetDataMate3000_43VarMsg(nAddr, szCmd, szMsg, nIndex, nLen, szDataType,iSBit, iEBit); nRet = GetDataMate3000_47VarMsg(nAddr, szCmd, szMsg, nIndex, nLen, szDataType,iSBit, iEBit); nRet = GetDataMate3000_4DVarMsg(nAddr, szCmd, szMsg, nIndex, nLen, szDataType,iSBit, iEBit); nRet = GetDataMate3000_82VarMsg(nAddr, szCmd, szMsg, nIndex, nLen, szDataType,iSBit, iEBit); //LOG4C((LOG_NOTICE, "DME3000 szCmd= %s, szMsg = %s", szCmd, szMsg)); return nRet; } int CDataMate3000::GetDataMate3000_42VarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { int iCmd = atoi(szCmd + 4); if( iCmd >= 1 && iCmd <=3 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif DataConversion(szType, m_szDataMate3000_42Msg[nAddr - 1] + nIndex, szMsg, nLen, 0, 0); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDataMate3000_43VarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { if(strcmp(szCmd, "cmd-4") == 0 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif DataConversion(szType, m_szDataMate3000_43Msg[nAddr - 1] + nIndex, szMsg, nLen, 0, 0); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDataMate3000_47VarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { int iCmd = atoi(szCmd + 4); if( iCmd >= 5 && iCmd <= 10 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif DataConversion(szType, m_szDataMate3000_47Msg[nAddr - 1] + nIndex, szMsg, nLen, 0, 0); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDataMate3000_4DVarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { int iCmd = atoi(szCmd + 4); if( iCmd >= 11 && iCmd <= 16 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif DataConversion(szType, m_szDataMate3000_4DMsg[nAddr - 1] + nIndex, szMsg, nLen, 0, 0); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDataMate3000_82VarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { int iCmd = atoi(szCmd + 4); if( iCmd >= 17 && iCmd <= 43 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif DataConversion(szType, m_szDataMate3000_82Msg[nAddr - 1] + nIndex, szMsg, nLen, iSBit, iEBit); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDataMate3000_45VarMsg(int nAddr,char *szCmd,char *szMsg,int &nIndex,int &nLen,char *szType,int iSBit,int iEBit) { if( strcmp(szCmd, "cmd-44") == 0) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(szMsg, m_szDataMate3000_45Msg[nAddr - 1] + nIndex, nLen); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } return 0; } int CDataMate3000::GetDeviceParam( int nAddr,CCommProcess *pComm,char *szCmd,char *IniSendCMD, const int &IniSendlen) { int nRet = -1; nRet = Send_ReadDeviceData(nAddr,pComm,szCmd,IniSendCMD,IniSendlen); if( nRet != 0 ) { LOG4C((LOG_NOTICE,"DME3000 RequestStatus::Error")); return nRet; // 串口忙 } nRet = Recv_ReadDeviceData(nAddr,pComm,szCmd); return nRet; } int CDataMate3000::SetDeviceParam( int nAddr,CCommProcess *pComm,char *szCmd,char *szSetMsg,char *szRecvMsg,char *IniSendCMD, const int &IniSendlen) { int nRet = -1; nRet = Send_WriteDeviceData(nAddr,pComm,szCmd,szSetMsg,IniSendCMD,IniSendlen); if( nRet != 0 ) { LOG4C((LOG_NOTICE,"DME3000 SetDeviceParam::Error")); return nRet; // 串口忙 } nRet = Recv_WriteDeviceData(nAddr,pComm,szCmd,szRecvMsg); return nRet; } void CDataMate3000::SetDataMate3000_42VarMsg( int nAddr, char *szCmd, char *pBuffer) { int iCmd = atoi(szCmd + 4); if( iCmd >= 1 && iCmd <= 3 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(m_szDataMate3000_42Msg[nAddr - 1], pBuffer, sizeof(m_szDataMate3000_42Msg[nAddr - 1])); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } } void CDataMate3000::SetDataMate3000_43VarMsg( int nAddr, char *szCmd, char *pBuffer) { if( strcmp(szCmd, "cmd-4") == 0) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(m_szDataMate3000_43Msg[nAddr - 1], pBuffer, sizeof(m_szDataMate3000_43Msg[nAddr - 1])); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } } void CDataMate3000::SetDataMate3000_47VarMsg( int nAddr, char *szCmd, char *pBuffer) { int iCmd = atoi(szCmd + 4); if( iCmd >= 5 && iCmd <= 10 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(m_szDataMate3000_47Msg[nAddr - 1], pBuffer, sizeof(m_szDataMate3000_47Msg[nAddr - 1])); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } } void CDataMate3000::SetDataMate3000_4DVarMsg( int nAddr, char *szCmd, char *pBuffer) { int iCmd = atoi(szCmd + 4); if( iCmd >= 11 && iCmd <= 16 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(m_szDataMate3000_4DMsg[nAddr - 1], pBuffer, sizeof(m_szDataMate3000_4DMsg[nAddr - 1])); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } } void CDataMate3000::SetDataMate3000_82VarMsg( int nAddr, char *szCmd, char *pBuffer) { int iCmd = atoi(szCmd + 4); if( iCmd >= 17 && iCmd <= 43 ) { #if IS_USE_READMSG_CS EnterCriticalSection( &m_csReadMsg ); #endif memcpy(m_szDataMate3000_82Msg[nAddr - 1], pBuffer, sizeof(m_szDataMate3000_82Msg[nAddr - 1])); #if IS_USE_READMSG_CS LeaveCriticalSection(&m_csReadMsg); #endif } } WORD CDataMate3000::GetDataLength(const WORD wLENID, char chLength[4]) { char szLenID[3] = {0}; //int nLen = 10; DigitToBinary(wLENID, szLenID, sizeof(szLenID)); char chCheckSum = GetLCheckSum(szLenID, sizeof(szLenID)); chLength[0] = chCheckSum; chLength[1] = szLenID[0]; chLength[2] = szLenID[1]; chLength[3] = szLenID[2]; return 0; } char CDataMate3000::GetLCheckSum(char *pBuf, int len) { //WORD iSum = 0; char chCompliment = 0; //unsigned char chCompliment[2] = {0}; for(int i=0; i>4) & 0x0f); byArySend[4] = ByteToAscii(nAddr & 0x0f); //Cid1 byArySend[5] = 0x36; byArySend[6] = 0x30; memcpy(byArySend + 7, IniSendCMD, 2); byArySend[9] = 0x30; byArySend[10] = 0x30; byArySend[11] = 0x30; byArySend[12] = 0x30; char cAryCheck[5] = {0}; GetDME3000Check((char*)byArySend + 1, cAryCheck, 12); memcpy(byArySend + 13,cAryCheck,4); byArySend[17] = 0x0D; CString strSendCommand = ""; strSendCommand.Format("%s",byArySend); //LOG4C((LOG_NOTICE,"SendCommand = %s",strSendCommand)); /************************************************************************/ if( WaitForSingleObject( m_hSemComm, 0 ) == WAIT_OBJECT_0 ) // 有信号才写串口 { ResetEvent( m_hSemComm ); int nResult = pComm->Write(byArySend, 18); if( nResult == 18 ) { nRet = 0; } else { SetEvent( m_hSemComm ); LOG4C((LOG_NOTICE,"DME3000 RequestStatus:写长度与返回值不等")); return ERR_CODE_DATAMATE3000_COM_INVALIDRES; } } else { LOG4C((LOG_NOTICE,"DME3000 RequestStatus:未获取事件信号权")); return ERR_CODE_DATAMATE3000_COM_BUSY; } #endif Sleep(150); return nRet; } int CDataMate3000::Recv_ReadDeviceData(int nAddr,CCommProcess *pComm,char *szCmd) { #if DEBUG_DataMate3000 int nReceiveLen = 60; BYTE *pBuffer = new BYTE[nReceiveLen]; ZeroMemory(pBuffer,60); int nReadLen = pComm->Read( pBuffer, nReceiveLen); //LOG4C((LOG_NOTICE,"DME3000 pBuffer = %s, nReadLen = %d",pBuffer,nReadLen)); if( nReadLen <= 0) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } LOG4C((LOG_NOTICE,"DME3000 ResponseStatus:读取长度 <= 0")); return ERR_CODE_DATAMATE3000_COM_READ_NO_DATA; } char cAryCheck[5] = {0}; GetDME3000Check((char*)pBuffer + 1, cAryCheck, nReadLen -6); //LOG4C((LOG_NOTICE,"cAryCheck = %s",cAryCheck)); char cTemp[5] = {0}; memcpy(cTemp, pBuffer + nReadLen - 5, 4); //LOG4C((LOG_NOTICE,"DME3000 cTemp = %s",cTemp)); if( strcmp( cAryCheck,cTemp) != 0 ) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } LOG4C((LOG_NOTICE,"DME3000 ResponseStatus:总校检错误")); return ERR_CODE_DATAMATE3000_COM_CHKSUM_LOST; } if (!CheckLength((char*)pBuffer)) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } LOG4C((LOG_NOTICE,"DME3000 ResponseStatus:长度校检错误")); return ERR_CODE_DATAMATE3000_COM_VARLEN; } int nRet = RtnCheck((char*)pBuffer); if(0 != nRet) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } LOG4C((LOG_NOTICE,"DME3000 ResponseStatus:返回码错误")); return nRet; } SetDataMate3000_42VarMsg(nAddr, szCmd, (char*)pBuffer); SetDataMate3000_43VarMsg(nAddr, szCmd, (char*)pBuffer); SetDataMate3000_47VarMsg(nAddr, szCmd, (char*)pBuffer); SetDataMate3000_4DVarMsg(nAddr, szCmd, (char*)pBuffer); SetDataMate3000_82VarMsg(nAddr, szCmd, (char*)pBuffer); m_dwOnlineTick[nAddr - 1] = GetTickCount(); // 设置串口等待事件为有信号; SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } #else SimulationCommData(); #endif Sleep(150); return 0; } int CDataMate3000::Send_WriteDeviceData(int naddr, CCommProcess *pComm, char *szCmd, char *szSetMsg, char *IniSendCMD, const int &IniSendlen ) { #if DEBUG_DataMate3000 char szSendMsg[DATAMATE3000_SEND_MSG]; int iSendlen = sizeof(REQUEST_STRUCT); REQUEST_STRUCT szSend; ZeroMemory(&szSend,sizeof(REQUEST_STRUCT)); if ( strcmp(szCmd,"cmd-44") == 0 ) { //sol szSend.Sol = 0x7E; //ver szSend.Ver[0] = '2'; szSend.Ver[1] = '1'; //adr szSend.Adr[0] = ByteToAscii((naddr>>4) & 0x0f); szSend.Adr[1] = ByteToAscii(naddr & 0x0f); //cid1 szSend.Cid1[0] = '6'; szSend.Cid1[1] = '0'; //cid2 memcpy(szSend.Cid2, IniSendCMD, 2); memset(szSend.Length, 0, 4); //length szSend.Length[1] = '0'; szSend.Length[2] = '0'; szSend.Length[3] = '2'; szSend.Length[0] = 'E'; //szInfo memcpy(szSend.szInfo,szSetMsg, sizeof(szSend.szInfo)); memset(szSend.Chksum, 0,sizeof(szSend.Chksum)); szSend.Eol = 0x0D; memcpy(szSendMsg, &szSend, sizeof(REQUEST_STRUCT)); GetChkSum(szSendMsg, (char *)szSend.Chksum, sizeof(REQUEST_STRUCT)); szSend.Eol = 0x0D; memcpy(szSendMsg, &szSend, sizeof(REQUEST_STRUCT)); } ResetEvent( m_hSemComm ); int nResult = pComm->Write((unsigned char *)szSendMsg, iSendlen); if( nResult == iSendlen ) { } else { SetEvent( m_hSemComm ); return EER_CODE_DATAMATE3000_COM_WRITE_DATA; } #endif return 0; } int CDataMate3000::Recv_WriteDeviceData(int nAddr, CCommProcess *pComm, char *szCmd, char *szRecvMsg ) { #if DEBUG_DataMate3000 int nReceiveLen = 0; int nProcessLen = 0; int nReadLen = 0; nReceiveLen = DATEMATE3000_RECEIVE_MSG; char *pBuffer = new char[ nReceiveLen ]; memset(pBuffer, 0, nReceiveLen); nReadLen = pComm->Read((BYTE *)pBuffer, nReceiveLen); if( nReadLen <= 0) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } return ERR_CODE_DATAMATE3000_COM_READ_NO_DATA; } #if 0 if (!ChkSumCheck(pBuffer, strlen(pBuffer))) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } return ERR_CODE_DATAMATE3000_COM_CHKSUM_LOST; } if (!CheckLength(pBuffer)) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } return ERR_CODE_DATAMATE3000_COM_VARLEN; } int nRet = RtnCheck(pBuffer); if(0 != nRet) { SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } return nRet; } #endif // 设置串口等待事件为有信号 SetEvent( m_hSemComm ); if( pBuffer != NULL) { delete[] pBuffer; pBuffer = NULL; } #else SimulationCommData(); #endif return 0; } void CDataMate3000::SimulationCommData(void) { } WORD CDataMate3000::RtnCheck(char Msg[VAR_MSG]) { int len ,index; len = 2; index = 7; char ch[2]; ch[0] = Msg[index]; ch[1] = Msg[index+1]; if (atoi(ch)==ERR_CID_RTN_VAR) { return ERR_CID_RTN_VAR; } else if (atoi(ch)==ERR_CID_RTN_CHKSUM) { return ERR_CID_RTN_CHKSUM; } else if (atoi(ch)==ERR_CID_RTN_LCHKSUM) { return ERR_CID_RTN_LCHKSUM; } else if (atoi(ch)==ERR_CID_RTN_CID2) { return ERR_CID_RTN_CID2; } else if (atoi(ch)==ERR_CID_RTN_FORMAT) { return ERR_CID_RTN_FORMAT; } else if (atoi(ch)==ERR_CID_RTN_INVALI_DATA) { return ERR_CID_RTN_INVALI_DATA; } else /*if (atoi(ch)==ERR_CID_RTN_NORMAL)*/ { return ERR_CID_RTN_NORMAL; } }