协议文件定义,头文件

#pragma  once
//
//  constants define
//
#define SOCKETCREATEFAIL         -1
#define SOCKETBINDFAIL           -2
#define SOCKETIOCTLFAIL          -3
#define SOCKETSETLECTFAIL        -4
#define SOCKETCONETCFAIL         -5
//
// struct define
//
typedef struct {
 unsigned char SystemID;
 unsigned char NULL1;
 unsigned char headerlength;
 unsigned char IDopCode;
 unsigned char OpCodelength;
 unsigned char OpCode;
    unsigned char ORGField;
 unsigned char ORGfieldlength;
 unsigned char ORGID;
 unsigned char DBNR;
 unsigned char HighofStartAddress;
 unsigned char LowofStartAddress;
 unsigned char HighofLength;
 unsigned char LowofLength;
 unsigned char EmptyField;
 unsigned char LengthofEmptyField;
 unsigned char Data;
}StructReqFrame;
typedef struct  {
 int Area;
 int DBNR;
 int StartAddress;
 int Length;
}StructPLCAddr;
//
//  function header 
//
void Log(char *LogFileDirectory ,char pData[4096], int len, int nDatatype);
int CreateTCPSocket(struct sockaddr_in *socketAddr);

                    

 协议文件CPP

#include <StdAfx.h>
#include "DrvProtocol .h"
#include <windows.h>
#include <time.h>
#include <locale.h>
#include <stdio.h>
#include <WINSOCK2.H>
extern char  szDllPath[80];
void Log(char *LogFileDirectory ,char pData[4096], int len, int nDatatype)
{ 
 SYSTEMTIME st;
 setlocale(LC_ALL, "");
 GetLocalTime(&st); 
 char *sPath   = new char[256];
 char *sFile   = new char[256];
 char *sWrite  = new char[5000];
 memset(sWrite, 0, 5000);
 memset(sPath, 0, 256);
 strcpy(sPath, LogFileDirectory) ;
    memset(sFile, 0, 256);
 sprintf(sFile, "%d%02d%02d%02d.log", st.wYear, st.wMonth, st.wDay, st.wHour);
    sprintf(sPath, "%s\\%s", LogFileDirectory, sFile);
    
 sprintf(sWrite, "%02d:%02d:%02d ", st.wHour, st.wMinute, st.wSecond);
 switch(nDatatype)
 {
 case 1:
  strcat(sWrite,"发送:");
  break;
 case 2:
  strcat(sWrite,"接收:");
  break;
 default:
  strcat(sWrite,"消息:");
  break;
 }
 
 if(nDatatype == 1 || nDatatype == 2)
 {
  for (int i=0; i<len; i++)
  {
   char temp[20];
   memset(temp, 0, 20);
   sprintf(temp, "%02X ", pData[i]);
   if( pData[i] & 0x80) 
   {
    strcat(sWrite, temp + 6);
   }
   else strcat(sWrite, temp);
  }
 }
    else
    strcat(sWrite,pData);
 strcat(sWrite, "\r");
 strcat(sWrite, "\n"); 
 FILE *pFile;
    pFile = fopen(sPath, "at+"); 
 if (pFile != NULL)
 {
  fputs(sWrite, pFile);
  fclose(pFile);
 }
 delete sFile;
 delete sWrite;
 delete sPath;
}
int CreateTCPSocket(struct sockaddr_in *socketAddr)
{
 int ret;
    int nsocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
 if (nsocket == INVALID_SOCKET)
 {
  printf("socket() failed!\n");
  return SOCKETCREATEFAIL;
 }
 
 ret = connect(nsocket, (struct sockaddr *)socketAddr, sizeof(*socketAddr));
 if (ret == SOCKET_ERROR)
 {
  printf("connect() failed!\n");
  closesocket(nsocket); 
  return SOCKETCONETCFAIL;
 }
// unsigned  long   ul = 1; 
// ret = ioctlsocket(nsocket,FIONBIO,(unsigned long*)&ul); 
// if(ret==SOCKET_ERROR)
// {
//  closesocket(nsocket);
//  Log(szDllPath,"ioctlsocket socket fail",22,3);
//  WSACleanup();  
//  return SOCKETIOCTLFAIL;
// }
 return nsocket;  
}

调用CPP

// CPReadWrite.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <stdlib.h>
#include "DrvProtocol .h"
#include <winsock.h>
#pragma comment(lib,"Ws2_32")
char          szDllPath[80];
WORD          wCommand = 1;
char *pCharData;
int PlcAddrConfig(char * strConfigFile, StructPLCAddr * &plcAddr,char * &pCh)
{
 int  nret = -1;
 int  ntmp =  0;
 int  ntotal;
 char strBuffer[64];
 int  nAddrtotallLength = 0;
 ntotal = GetPrivateProfileInt("PLCDATA","TOTALDATA",-1,strConfigFile);
 if(- 1 == ntotal) return -1;
 plcAddr = new StructPLCAddr[ntotal + 1];
 memset(plcAddr,0,sizeof(StructPLCAddr) * (ntotal + 1));
 while(nret)
 {
  char* pChr,*pNchr;
  memset(strBuffer,0,64);
  nret = GetPrivateProfileString("PLCDATA",NULL,"",strBuffer,sizeof(strBuffer),strConfigFile); 
  printf("KeyName:%s",strBuffer);
  nret = GetPrivateProfileString("PLCDATA",strBuffer,"",strBuffer,sizeof(strBuffer),strConfigFile); 
  printf("Value:%s\n",strBuffer);
  pChr = strBuffer;
  pNchr = strchr(pChr,'|');
  plcAddr[ntmp].Area = atoi(strstr(pChr,pNchr));
  pChr = pNchr;
  pNchr = strchr(pChr,'|');
  plcAddr[ntmp].DBNR = atoi(strstr(pChr,pNchr));
  pChr = pNchr;
  pNchr = strchr(pChr,'|');
  plcAddr[ntmp].StartAddress = atoi(strstr(pChr,pNchr));
  pChr = pNchr;
   
  pNchr = strchr(pChr,'|');
  plcAddr[ntmp].Length = atoi(strstr(pChr,pNchr));
  pChr = pNchr;
  nAddrtotallLength += plcAddr[ntmp].Length;
  if(++ntmp = ntotal)
  {
   break;
  }
 }
 if(!nret)
 {
  Log(szDllPath,"the configure TOTALDATA > PLCDATA number",45,3);
 }
 pCh = new char[ntmp];
 memset(pCh,0,ntmp);
 return 0;
}
void main(int argc, char* argv[])
{
 char *strIniFile = ".\\SiemensCP.ini";
 StructPLCAddr *pPlcAddre;
 StructPLCAddr *t_pPlcAddre;
 StructReqFrame ReqFrame;
    char *t_pCharData;
    PlcAddrConfig(strIniFile,pPlcAddre,pCharData);
    t_pPlcAddre = pPlcAddre;
 t_pCharData  = pCharData;
 SOCKET socket_Fetch = 0;
 SOCKET socket_Write = 0;
    sockaddr_in socketAddr;
 char *chipAddress = new char[40];
 char *socketBuff = new char[2049];
    WORD ret = 0;
    strcpy(szDllPath,"D:\\"); 
 memset(chipAddress,0,40);
 memset(socketBuff,0,2049);
 ReqFrame.SystemID      =  0x53; 
 ReqFrame.NULL1         =  0x35;
 ReqFrame.headerlength  =  0x10;
 ReqFrame.IDopCode      =  0x01;
 ReqFrame.OpCodelength  =  0x03;
    ReqFrame.ORGField      =  0x03;
 ReqFrame.ORGfieldlength=  0x08; 
    int nPort;
 WSADATA wsaData;
 ret = WSAStartup(MAKEWORD(2, 2), &wsaData); 
    if(ret!=0)  
 {  
  WSACleanup();  
  return ;  
 }
 if(LOBYTE(wsaData.wVersion)!=2 || HIBYTE(wsaData.wVersion)!=2)
 {
  WSACleanup(); 
  printf("Invalid WinSock version!\n");
  return ;
 }
 
 socketAddr.sin_family = AF_INET;
 GetPrivateProfileString("SIEMENSCP","FETCHIP",NULL,chipAddress,40,strIniFile);
 nPort      = GetPrivateProfileInt("SIEMENSCP","FETCHPORT",NULL,strIniFile);
    socketAddr.sin_port = htons(nPort); 
 socketAddr.sin_addr.S_un.S_addr = inet_addr(chipAddress);
 Log(szDllPath,"Fetch ip:",9,3);
    Log(szDllPath,chipAddress,20,3);
 socket_Fetch = CreateTCPSocket(&socketAddr);
 GetPrivateProfileString("SIEMENSCP","WRITEIP ",NULL,chipAddress,40,strIniFile);
    nPort          = GetPrivateProfileInt("SIEMENSCP","WRITEPORT",NULL,strIniFile);
 socketAddr.sin_port = htons(nPort); 
    socketAddr.sin_addr.S_un.S_addr = inet_addr(chipAddress);
 Log(szDllPath,"Write ip:",9,3);
    Log(szDllPath,chipAddress,20,3);     
 socket_Write   = CreateTCPSocket(&socketAddr);
  
    while(socket_Fetch  > 0 && socket_Write > 0)
 {   
  ReqFrame.EmptyField         =  (char)0XFF;
     ReqFrame.LengthofEmptyField =  0x02;
        if(0 == wCommand) break;
  switch(wCommand)
  {
  case 1:
   ReqFrame.OpCode             =  0x05;  
   Log(szDllPath,(char*)&ReqFrame,16,1);
   memcpy(socketBuff,&ReqFrame,16);
   while(pPlcAddre->Area)
   {
    send(socket_Fetch,socketBuff,16,0);
    memset(socketBuff,0,2049);
    recv(socket_Fetch,socketBuff,2048,0);
       strcpy(t_pCharData,(socketBuff + pPlcAddre->Length + 1));
    t_pCharData += pPlcAddre->Length;
    pPlcAddre++;
   }  
         Log(szDllPath,socketBuff,17 + (int)ReqFrame.LowofLength + (int)ReqFrame.HighofLength,2);
   break;
  case 2:
   ReqFrame.OpCode             =  0x03;
   memcpy(socketBuff,&ReqFrame,17);
   Log(szDllPath,(char*)&ReqFrame,16 + (int)ReqFrame.LowofLength +  (int)ReqFrame.HighofLength,1);
   send(socket_Write,socketBuff,16 + (int)ReqFrame.LowofLength +  (int)ReqFrame.HighofLength,0);
    memset(socketBuff,0,2049);
    do
    {
     recv(socket_Write,socketBuff,2048,0);
    }while(NULL == *socketBuff);
         Log(szDllPath,socketBuff,16,2);
   break;
  default:
   break;
  }
 }
 delete chipAddress;
 delete socketBuff;
 delete pPlcAddre;
 delete pCharData;
 closesocket(socket_Fetch);
 closesocket(socket_Write);
 Log(szDllPath,"PLC thread exit",16,3);
 WSACleanup(); 
 return ;
}

配置文件

[SIEMENSCP]
DEBUG         = 1
FETCHIP       = 172.30.0.204
FETCHPORT     = 2000
WRITEIP       = 172.30.0.204
WRITEPORT     = 2001
TOTALLENGTH   = 250
[PLCDATA]
1 = 区|开始地址|长度
2 = 区|开始地址|长度
3 = 区|开始地址|长度
4 = 区|开始地址|长度
                       ;01   = 0X0000 -- 0XEFFF       ;栈 0 - 15 板 0 - 15
                       ;02   = 0XF000 -- 0XF1FF       ;栈 16     板 1       通道 0   - 127 
                       ;03   = 0XF200 -- 0XF28F       ;栈 16     板 2       通道 0   - 127 
                       ;04   = 0XF290 -- 0XF2FF       ;栈 16     板 2       通道 128 - 255
                       ;05   = 0XF300 -- 0XF3FF       ;栈 16     板 3       通道 0   - 255
                       ;06   = 0XF400 -- 0XF4FF       ;栈 16     板 4       通道 0   - 255
                       ;07   = 0XF500 -- 0XF5FF       ;栈 16     板 5       通道 0   - 255