#pragma once
#include "snap7.h"
#include <string.h>
using namespace std;
class CPlcS7Comm
{
public:
CPlcS7Comm();
~CPlcS7Comm();
//设置PLC参数信息
bool InitPlcComm(string strIp, int iRack, int iSlot);
//链接PLC
bool Connect();
//链接PLC
bool reConnect();
//断开链接PLC
bool DisConnect();
// status get
bool getConnectStatus() const ;
bool getCurrentStatus() const ;
//读取
bool ReadInt4Byte(int iStartAddr,int &outValue);
bool ReadUInt4Byte(int iStartAddr,unsigned int &outValue);
bool ReadShort2Byte(int iStartAddr,short &outValue);
bool ReadFloat4Byte(int iStartAddr, float &outValue);
bool ReadCharByte(int iStartAddr, uint8_t &outValue);
bool ReadBool1Byte(int iStartAddr, bool &outValue);
/* 读PLC某个区域的值 Area表示内存区。取值0x84:V区 0x83:M区 0x82:O区 0x81:I区 0x1C:C区 0x1D:T区 enum PLCAREA
*DBNumber表示区域号,一般为1
*Start表示起始地址。当函数功能为读bit时,int addr =Start/8; int bit = Start%8;此时表示第addr地址的第Bit位。如Start = 8;则表示第1号地址的第0位,即addr.Bit(1.0);
*Amount表示要读取的数据长度,当函数类型为读bit时,只能为1
*WordLen决定函数的功能,函数功能有读位,字节,字,双字。取值: 0x1:Bit 0x2:Byte 0x4:Word 0x6:DW 0x8 : Real 0x1c : C区(16Bit) 0x1D:T区(16Bit)
*注意:读Word和DWord功能有问题,高位字节在前,低位字节在后(跟我们的程序反过来)
**pUsrData表示数据缓冲区,读取的数据存入该缓冲区 */
bool ReadBit( int Area, int DBNumber, int Start, int Amount, int WordLen, void *pUsrData);//plc any area
//写入
bool WriteInt4Byte(int iStartAddr, int inValue);
bool WriteShort2Byte(int iStartAddr, short inValue);
bool WriteFloat4Byte(int iStartAddr, float inValue);
bool WriteCharByte(int iStartAddr, char inValue);
bool WriteBool1Byte(int iStartAddr, bool inValue);
bool Write2CharByte(int iStartAddr, char inValue,char inValue2);
bool Write2CharByte(int iStartAddr,unsigned char inValue,unsigned char inValue2);
/*
*Area表示内存区。取值0x84:V区 0x83:M区 0x82:O区 0x81:I区 0x1C:C区 0x1D:T区
*DBNumber表示区域号,一般为1
*Start表示起始地址。当函数功能为写bit时,int addr =Start/8; int bit = Start%8;此时表示第addr地址的第Bit位。如Start = 8;则表示第1号地址的第0位,即addr.Bit(1.0);
*Amount表示要写的数据长度,当函数类型为写bit时,只能为1
* WordLen决定函数的功能,函数功能有写位,字节,字,双字。取值: 0x1:Bit 0x2:Byte 0x4:Word 0x6:DW 0x8 : Real 0x1c : C区(16Bit) 0x1D:T区(16Bit)
注意:读Word和DWord功能有问题,高位字节在前,低位字节在后(跟我们的程序反过来)
*pUsrData表示数据缓冲区,写入PLC的数据存入该缓冲区
* */
bool WriteArea(int Area, int DBNumber, int Start, int Amount, int WordLen, void *pUsrData);
private:
void Reverse(char *pData, int iLength);
private:
TS7Client *m_pT7Client;
string m_strServerIp;
int m_iRack;
int m_iSlot;
int m_iDbNum;
bool m_isConnect ;
bool m_isInit;
};
#include "PlcS7Comm.h"
#include "CLogOper2.h"
enum PLCAREA
{
//读PLC某个区域的值 Area表示内存区。取值0x84:V区 0x83:M区 0x82:O区 0x81:I区 0x1C:C区 0x1D:T区
AREA_V = 0x84,
AREA_M = 0x83,
AREA_O = 0x82,
AREA_I = 0x81,
AREA_C = 0x1C,
AREA_T = 0x1D
};
CPlcS7Comm::CPlcS7Comm()
{
m_isConnect = false;
m_isInit = false;
m_pT7Client = new TS7Client();
m_iDbNum = 100;// value to mean
m_strServerIp = "192.168.1.10";
m_iRack = 0;
m_iSlot = 0;
}
CPlcS7Comm::~CPlcS7Comm()
{
if (NULL != m_pT7Client)
{
delete m_pT7Client;
m_pT7Client = NULL;
}
}
bool CPlcS7Comm::InitPlcComm(string strIp, int iRack, int iSlot)
{
int timeout1000 = 1000;
int timeout2000 = 2000;
m_strServerIp = strIp;
m_iRack = iRack;
m_iSlot = iSlot;
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
m_pT7Client->SetParam(p_i32_PingTimeout, &timeout1000);
m_pT7Client->SetParam(p_i32_SendTimeout, &timeout2000);
m_pT7Client->SetParam(p_i32_RecvTimeout, &timeout2000);
m_isInit = true;
Connect();
return true;
}
bool CPlcS7Comm::Connect()
{
m_isConnect = false;
if(!m_isInit)
{
return false;
}
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
if(0 == m_pT7Client->ConnectTo(m_strServerIp.c_str(), m_iRack, m_iSlot))
{
m_isConnect = true;
return true;
}else
{
g_MonitorLog->LogInfo("[%s][%s][%d] IP = %s m_iRack = %d m_iSlot = %d connect failed" , __FILE__, __FUNCTION__,__LINE__,m_strServerIp.c_str(),m_iRack,m_iSlot);
}
return false;
}
bool CPlcS7Comm::reConnect()
{
if(!m_isInit)
{
printf("PLC not init .....\n");
m_isConnect = false;
return false;
}
DisConnect();
for (size_t i = 0; i < 3; i++)
{
if(Connect())
{
return true;
}
}
return false;
}
bool CPlcS7Comm::DisConnect()
{
if(!m_isInit)
{
m_isConnect = false;
return false;
}
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
if (0 == m_pT7Client->Disconnect())
{
m_isConnect = false;
return true;
}
return false;
}
bool CPlcS7Comm::getConnectStatus() const
{
bool bRet = false;
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bRet = m_pT7Client->Connected();
return bRet;
}
bool CPlcS7Comm::getCurrentStatus() const
{
return m_isConnect;
}
bool CPlcS7Comm::ReadInt4Byte(int iStartAddr, int &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
byte szBuf[128] = "";
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 4, szBuf);
if (iRet == 0)
{
Reverse((char*)szBuf, 4);
int *pIOut = (int*)&szBuf;
outValue = *pIOut;
bRet = true;
}
return bRet;
}
bool CPlcS7Comm::ReadUInt4Byte(int iStartAddr,unsigned int &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
byte szBuf[10] = "";
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 4, szBuf);
if (iRet == 0)
{
Reverse((char*)szBuf, 4);
unsigned int *pIOut = (unsigned int*)&szBuf;
outValue = *pIOut;
bRet = true;
}
return bRet;
}
bool CPlcS7Comm::ReadShort2Byte(int iStartAddr, short &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
byte szBuf[128] = "";
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 2, szBuf);
if (iRet == 0)
{
Reverse((char*)szBuf, 2);
short *pIOut = (short*)&szBuf;
outValue = *pIOut;
bRet = true;
}
return bRet;
}
bool CPlcS7Comm::ReadFloat4Byte(int iStartAddr, float &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
byte szBuf[128] = "";
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 4, szBuf);
if (iRet == 0)
{
Reverse((char*)szBuf, 4);
float *pIOut = (float*)&szBuf;
outValue = *pIOut;
bRet = true;
}
return bRet;
}
bool CPlcS7Comm::ReadCharByte(int iStartAddr, uint8_t &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
uint8_t szBuf = 0;
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 1, &szBuf);
if (iRet == 0)
{
outValue = szBuf;
return true;
}else
{
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d read error msg = %s", __FILE__, __FUNCTION__,__LINE__,iStartAddr, CliErrorText(iRet).c_str());
return false;
}
}
bool CPlcS7Comm::ReadBool1Byte(int iStartAddr, bool &outValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
bool bRet = false;
byte szBuf[128] = "";
int iRet = m_pT7Client->DBRead(m_iDbNum, iStartAddr, 1, szBuf);
if (iRet == 0)
{
bool *pIOut = (bool*)&szBuf;
outValue = *pIOut;
bRet = true;
}
return bRet;
}
bool CPlcS7Comm::ReadBit( int Area, int DBNumber, int Start, int Amount, int WordLen, void *pUsrData)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
int iRet = m_pT7Client->ReadArea(Area, DBNumber, Start, Amount, WordLen, pUsrData);
if(iRet != 0)
{
return false;
}
return true;
}
bool CPlcS7Comm::WriteInt4Byte(int iStartAddr, int inValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
Reverse((char*)&inValue, 4);
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 4, &inValue);
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d ", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet);
if (iRet == 0)
{
return true;
}
return false;
}
bool CPlcS7Comm::WriteShort2Byte(int iStartAddr, short inValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
Reverse((char*)&inValue, 2);
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 2, &inValue);
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d ", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet);
if (iRet == 0)
{
return true;
}
return false;
}
bool CPlcS7Comm::WriteFloat4Byte(int iStartAddr, float inValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
Reverse((char*)&inValue, 4);
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 4, &inValue);
//g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d ", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet);
if (iRet == 0)
{
return true;
}
return false;
}
bool CPlcS7Comm::WriteCharByte(int iStartAddr, char inValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 1,&inValue);
if (iRet != 0)
{
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d PLC error msg = %s", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet, CliErrorText(iRet).c_str());
return false;
}
return true;
}
bool CPlcS7Comm::Write2CharByte(int iStartAddr, char inValue,char inValue2)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
char szBuf[2]={0};
szBuf[0]=inValue;
szBuf[1]=inValue2;
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 2,&szBuf);
if (iRet != 0)
{
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d PLC error msg = %s", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet, CliErrorText(iRet).c_str());
return false;
}
return true;
}
bool CPlcS7Comm::Write2CharByte(int iStartAddr,unsigned char inValue,unsigned char inValue2)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
unsigned char szBuf[2]={0};
szBuf[0]=inValue;
szBuf[1]=inValue2;
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 2,&szBuf);
if (iRet != 0)
{
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d PLC error msg = %s", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet, CliErrorText(iRet).c_str());
return false;
}
return true;
}
bool CPlcS7Comm::WriteBool1Byte(int iStartAddr, bool inValue)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
int iRet = m_pT7Client->DBWrite(m_iDbNum, iStartAddr, 1, &inValue);
if (iRet != 0)
{
g_MainCoreLog->LogInfo("[%s][%s][%d] iStartAddr :%d Write Value:%d iRet=%d error%s", __FILE__, __FUNCTION__,__LINE__,iStartAddr,inValue,iRet, CliErrorText(iRet).c_str());
return false;
}
return true;
}
bool CPlcS7Comm::WriteArea(int Area, int DBNumber, int Start, int Amount, int WordLen, void *pUsrData)
{
if(NULL == m_pT7Client)
{
g_MainCoreLog->LogError("[%s][%s][%d] NULL == m_pT7Client", __FILE__, __FUNCTION__,__LINE__);
return false;
}
int iRet = m_pT7Client->WriteArea( Area, DBNumber, Start, Amount, WordLen, pUsrData);
if(iRet != 0)
{
printf("plc error == %d",iRet);
return false;
}
return true;
}
void CPlcS7Comm::Reverse(char *pData, int iLength)
{
if (NULL == pData)
{
return;
}
for (int i = 0, j = iLength - 1; i < j; i++, j--) {
char c = pData[i];
pData[i] = pData[j];
pData[j] = c;
}
}