ST ENUM UNION
TYPE ENUM_tcp_client :
(
nInitial:=0,
nConnect,
nWhetherConnect,
nDetermineAction,
nSend,
nWhetherSend,
nReceive,
nWhetherReceive,
nClose,
nWhetherClose
);
END_TYPE
TYPE ENUM_tcp_server :
(
nInitial:=0,
nListen,
nWhetherListen,
nAccept,
nWhetherAccept,
nDetermineAction,
nSend,
nWhetherSend,
nReceive,
nWhetherReceive,
nCloseAll,
nWhetherCloseAll
);
END_TYPE
TYPE UNION_tcp_hex_char :
UNION
nByte:ARRAY[0..255] OF BYTE;
sString:STRING(256);
END_UNION
END_TYPE
TYPE ST_tcp_client :
STRUCT
control:ST_tcp_client_control;
parameter:ST_tcp_parameter;
status:ST_tcp_client_status;
FB:FB_tcp_client;
END_STRUCT
END_TYPE
TYPE ST_tcp_client_control :
STRUCT
bConnect:BOOL;
bReceive:BOOL;
bSend:BOOL;
bClose:BOOL;
END_STRUCT
END_TYPE
TYPE ST_tcp_client_status :
STRUCT
bConnectDone:BOOL;
bReceiveDone:BOOL;
bSendDone:BOOL;
bCloseDone:BOOL;
END_STRUCT
END_TYPE
TYPE ST_tcp_parameter :
STRUCT
sIp:T_IPv4Addr;
nPort:UDINT;
SendData:UNION_tcp_hex_char;
nSendDataLength:UINT:=256;
ReceiveData:UNION_tcp_hex_char;
nReceiveDataLength:UINT:=256;
END_STRUCT
END_TYPE
TYPE ST_tcp_server :
STRUCT
control:ST_tcp_server_control;
parameter:ST_tcp_parameter;
status:ST_tcp_server_status;
FB:FB_tcp_server;
END_STRUCT
END_TYPE
TYPE ST_tcp_server_control :
STRUCT
bListen:BOOL;
bReceive:BOOL;
bSend:BOOL;
bCloseAll:BOOL;
END_STRUCT
END_TYPE
TYPE ST_tcp_server_status :
STRUCT
bListenDone:BOOL;
bAcceptAccepted:BOOL;
bReceiveDone:BOOL;
bSendDone:BOOL;
bCloseAllDone:BOOL;
END_STRUCT
END_TYPE
FB_tcp_client
FUNCTION_BLOCK FB_tcp_client
VAR_INPUT
TcpClientControl:ST_tcp_client_control;
END_VAR
VAR_IN_OUT
TcpClientParameter:ST_tcp_parameter;
END_VAR
VAR_OUTPUT
TcpClientStatus:ST_tcp_client_status;
END_VAR
VAR
nClientStep:INT;
hSocket:T_HSOCKET;
nReceiveBytes:UDINT;
i:UDINT;
SocketConnect:FB_SocketConnect;
SocketReceive:FB_SocketReceive;
SocketSend:FB_SocketSend;
SocketClose:FB_SocketClose;
END_VAR
CASE nClientStep OF
ENUM_tcp_client.nInitial://复位信号
SocketConnect.bExecute:=FALSE;
SocketReceive.bExecute:=FALSE;
SocketSend.bExecute:=FALSE;
SocketClose.bExecute:=FALSE;
TcpClientStatus.bConnectDone:=FALSE;
TcpClientStatus.bReceiveDone:=FALSE;
TcpClientStatus.bSendDone:=FALSE;
TcpClientStatus.bCloseDone:=FALSE;
IF TcpClientControl.bConnect THEN
nClientStep:=ENUM_tcp_client.nConnect;
END_IF
ENUM_tcp_client.nConnect://连接服务器
SocketConnect.bExecute:=TRUE;
IF SocketConnect.bBusy THEN
SocketConnect.bExecute:=FALSE;
nClientStep:=ENUM_tcp_client.nWhetherConnect;
END_IF
ENUM_tcp_client.nWhetherConnect://判断是否连接成功
IF SocketConnect.bError THEN
nClientStep:=ENUM_tcp_client.nInitial;
END_IF
IF NOT SocketConnect.bBusy AND NOT SocketConnect.bError THEN
TcpClientStatus.bConnectDone:=TRUE;
nClientStep:=ENUM_tcp_client.nDetermineAction;
END_IF
ENUM_tcp_client.nDetermineAction://判断动作
TcpClientStatus.bSendDone:=FALSE;
TcpClientStatus.bReceiveDone:=FALSE;
IF TcpClientControl.bClose THEN
nClientStep:=ENUM_tcp_client.nClose;
ELSIF TcpClientControl.bSend THEN
nClientStep:=ENUM_tcp_client.nSend;
ELSE
nClientStep:=ENUM_tcp_client.nReceive;
END_IF
ENUM_tcp_client.nReceive://接收数据
SocketReceive.bExecute:=TRUE;
IF SocketReceive.bBusy THEN
SocketReceive.bExecute:=FALSE;
nClientStep:=ENUM_tcp_client.nWhetherReceive;
END_IF
ENUM_tcp_client.nWhetherReceive://判断是否接收成功
IF SocketReceive.bError THEN
nClientStep:=ENUM_tcp_client.nClose;
END_IF
IF NOT SocketReceive.bBusy AND NOT SocketReceive.bError THEN
IF nReceiveBytes>0 THEN
TcpClientStatus.bReceiveDone:=TRUE;
nClientStep:=ENUM_tcp_client.nDetermineAction;
ELSE
nClientStep:=ENUM_tcp_client.nDetermineAction;
END_IF
END_IF
ENUM_tcp_client.nSend://发送数据
SocketSend.bExecute:=TRUE;
IF SocketSend.bBusy THEN
SocketSend.bExecute:=FALSE;
nClientStep:=ENUM_tcp_client.nWhetherSend;
END_IF
ENUM_tcp_client.nWhetherSend://判断是否发送成功
IF SocketSend.bError THEN
nClientStep:=ENUM_tcp_client.nClose;
END_IF
IF NOT SocketSend.bBusy AND NOT SocketSend.bError THEN
TcpClientStatus.bSendDone:=TRUE;
nClientStep:=ENUM_tcp_client.nDetermineAction;
END_IF
ENUM_tcp_client.nClose://断开连接
SocketClose.bExecute:=TRUE;
IF SocketClose.bBusy THEN
SocketClose.bExecute:=FALSE;
nClientStep:=ENUM_tcp_client.nWhetherClose;
END_IF
ENUM_tcp_client.nWhetherClose://判断是否断开连接
IF SocketClose.bError THEN
nClientStep:=ENUM_tcp_client.nInitial;
END_IF
IF NOT SocketClose.bBusy AND NOT SocketClose.bError THEN
TcpClientStatus.bConnectDone:=FALSE;
TcpClientStatus.bReceiveDone:=FALSE;
TcpClientStatus.bSendDone:=FALSE;
TcpClientStatus.bCloseDone:=TRUE;
nClientStep:=ENUM_tcp_client.nInitial;
END_IF
END_CASE
//功能块
SocketConnect(
sSrvNetId:='' ,
sRemoteHost:=TcpClientParameter.sIp ,
nRemotePort:=TcpClientParameter.nPort ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> ,
hSocket=>hSocket );
SocketReceive(
sSrvNetId:='' ,
hSocket:=hSocket ,
cbLen:=TcpClientParameter.nReceiveDataLength ,
pDest:=ADR(TcpClientParameter.ReceiveData) ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> ,
nRecBytes=>nReceiveBytes );
IF nReceiveBytes>0 THEN
TcpClientParameter.ReceiveData.sString:=LEFT(TcpClientParameter.ReceiveData.sString,UDINT_TO_INT(nReceiveBytes));
FOR i:=nReceiveBytes TO 255 BY 1 DO
TcpClientParameter.ReceiveData.nByte[i]:=0;
END_FOR
END_IF
IF SocketSend.bExecute THEN
FOR i:=TcpClientParameter.nSendDataLength TO 255 BY 1 DO
TcpClientParameter.SendData.nByte[i]:=0;
END_FOR
END_IF
SocketSend(
sSrvNetId:='' ,
hSocket:=hSocket ,
cbLen:=TcpClientParameter.nSendDataLength ,
pSrc:=ADR(TcpClientParameter.SendData) ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> );
SocketClose(
sSrvNetId:='' ,
hSocket:=hSocket ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> );
FB_tcp_server
FUNCTION_BLOCK FB_tcp_server
VAR_INPUT
TcpServerControl:ST_tcp_server_control;
END_VAR
VAR_IN_OUT
TcpServerParameter:ST_tcp_parameter;
END_VAR
VAR_OUTPUT
TcpServerStatus:ST_tcp_server_status;
END_VAR
VAR
nServerStep:INT;
hListener:T_HSOCKET;
hSocket:T_HSOCKET;
nReceiveBytes:UDINT;
i:UDINT;
SocketListen:FB_SocketListen;
SocketAccept:FB_SocketAccept;
SocketReceive:FB_SocketReceive;
SocketSend:FB_SocketSend;
SocketCloseAll:FB_SocketCloseAll;
END_VAR
CASE nServerStep OF
ENUM_tcp_server.nInitial://复位
SocketListen.bExecute:=FALSE;
SocketAccept.bExecute:=FALSE;
SocketSend.bExecute:=FALSE;
SocketReceive.bExecute:=FALSE;
SocketCloseAll.bExecute:=FALSE;
TcpServerStatus.bListenDone:=FALSE;
TcpServerStatus.bAcceptAccepted:=FALSE;
TcpServerStatus.bReceiveDone:=FALSE;
TcpServerStatus.bSendDone:=FALSE;
TcpServerStatus.bCloseAllDone:=FALSE;
IF TcpServerControl.bListen THEN
nServerStep:=ENUM_tcp_server.nListen;
END_IF
ENUM_tcp_server.nListen://打开监听
SocketListen.bExecute:=TRUE;
IF SocketListen.bBusy THEN
SocketListen.bExecute:=FALSE;
nServerStep:=ENUM_tcp_server.nWhetherListen;
END_IF
ENUM_tcp_server.nWhetherListen://判断是否监听成功
IF SocketListen.bError THEN
nServerStep:=ENUM_tcp_server.nInitial;
END_IF
IF NOT SocketListen.bBusy AND NOT SocketListen.bError THEN
TcpServerStatus.bListenDone:=TRUE;
nServerStep:=ENUM_tcp_server.nAccept;
END_IF
ENUM_tcp_server.nAccept://接收客户端
IF TcpServerControl.bCloseAll THEN
nServerStep:=ENUM_tcp_server.nCloseAll;
ELSE
SocketAccept.bExecute:=TRUE;
END_IF
IF SocketAccept.bBusy THEN
SocketAccept.bExecute:=FALSE;
nServerStep:=ENUM_tcp_server.nWhetherAccept;
END_IF
ENUM_tcp_server.nWhetherAccept://判断是否接收到客户端
IF SocketAccept.bError THEN
nServerStep:=ENUM_tcp_server.nCloseAll;
END_IF
IF NOT SocketAccept.bBusy AND NOT SocketAccept.bError THEN
IF NOT TcpServerStatus.bAcceptAccepted THEN
nServerStep:=ENUM_tcp_server.nAccept;
ELSE
nServerStep:=ENUM_tcp_server.nDetermineAction;
END_IF
END_IF
ENUM_tcp_server.nDetermineAction://判断动作
TcpServerStatus.bSendDone:=FALSE;
TcpServerStatus.bReceiveDone:=FALSE;
IF TcpServerControl.bCloseAll THEN
nServerStep:=ENUM_tcp_server.nCloseAll;
ELSIF TcpServerControl.bSend THEN
nServerStep:=ENUM_tcp_server.nSend;
ELSE
nServerStep:=ENUM_tcp_server.nReceive;
END_IF
ENUM_tcp_server.nReceive://接收数据
SocketReceive.bExecute:=TRUE;
IF SocketReceive.bBusy THEN
SocketReceive.bExecute:=FALSE;
nServerStep:=ENUM_tcp_server.nWhetherReceive;
END_IF
ENUM_tcp_server.nWhetherReceive://判断是否接收成功
IF SocketReceive.bError THEN
nServerStep:=ENUM_tcp_server.nCloseAll;
END_IF
IF NOT SocketReceive.bBusy AND NOT SocketReceive.bError THEN
IF nReceiveBytes>0 THEN
TcpServerStatus.bReceiveDone:=TRUE;
nServerStep:=ENUM_tcp_server.nDetermineAction;
ELSE
nServerStep:=ENUM_tcp_server.nDetermineAction;
END_IF
END_IF
ENUM_tcp_server.nSend://发送接收数据
SocketSend.bExecute:=TRUE;
IF SocketSend.bBusy THEN
SocketSend.bExecute:=FALSE;
nServerStep:=ENUM_tcp_server.nWhetherSend;
END_IF
ENUM_tcp_server.nWhetherSend://判断是否发送成功
IF SocketSend.bError THEN
nServerStep:=ENUM_tcp_server.nCloseAll;
END_IF
IF NOT SocketSend.bBusy AND NOT SocketSend.bError THEN
TcpServerStatus.bSendDone:=TRUE;
nServerStep:=ENUM_tcp_server.nDetermineAction;
END_IF
ENUM_tcp_server.nCloseAll://关闭服务器
SocketCloseAll.bExecute:=TRUE;
IF SocketCloseAll.bBusy THEN
SocketCloseAll.bExecute:=FALSE;
nServerStep:=ENUM_tcp_server.nWhetherCloseAll;
END_IF
ENUM_tcp_server.nWhetherCloseAll://判断是否关闭服务器
IF SocketCloseAll.bError THEN
nServerStep:=ENUM_tcp_server.nInitial;
END_IF
IF NOT SocketCloseAll.bBusy AND NOT SocketCloseAll.bError THEN
TcpServerStatus.bListenDone:=FALSE;
TcpServerStatus.bAcceptAccepted:=FALSE;
TcpServerStatus.bReceiveDone:=FALSE;
TcpServerStatus.bSendDone:=FALSE;
TcpServerStatus.bCloseAllDone:=TRUE;
nServerStep:=ENUM_tcp_server.nInitial;
END_IF
END_CASE
//功能块
SocketListen(
sSrvNetId:='' ,
sLocalHost:=TcpServerParameter.sIp ,
nLocalPort:=TcpServerParameter.nPort ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> ,
hListener=>hListener );
SocketAccept(
sSrvNetId:='' ,
hListener:=hListener ,
bExecute:= ,
tTimeout:=T#10S ,
bAccepted=>TcpServerStatus.bAcceptAccepted ,
bBusy=> ,
bError=> ,
nErrId=> ,
hSocket=>hSocket );
SocketReceive(
sSrvNetId:='' ,
hSocket:=hSocket ,
cbLen:=TcpServerParameter.nReceiveDataLength ,
pDest:=ADR(TcpServerParameter.ReceiveData) ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> ,
nRecBytes=>nReceiveBytes );
IF nReceiveBytes>0 THEN
TcpServerParameter.ReceiveData.sString:=LEFT(TcpServerParameter.ReceiveData.sString,UDINT_TO_INT(nReceiveBytes));
FOR i:=nReceiveBytes TO 255 BY 1 DO
TcpServerParameter.ReceiveData.nByte[i]:=0;
END_FOR
END_IF
IF SocketSend.bExecute THEN
FOR i:=TcpServerParameter.nSendDataLength TO 255 BY 1 DO
TcpServerParameter.SendData.nByte[i]:=0;
END_FOR
END_IF
SocketSend(
sSrvNetId:='' ,
hSocket:=hSocket ,
cbLen:=TcpServerParameter.nSendDataLength ,
pSrc:=ADR(TcpServerParameter.SendData) ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> );
SocketCloseAll(
sSrvNetId:='' ,
bExecute:= ,
tTimeout:=T#10S ,
bBusy=> ,
bError=> ,
nErrId=> );
GVL_tcp
VAR_GLOBAL
tcpClient:ST_tcp_client;
tcpServer:ST_tcp_server;
END_VAR
P_tcp_client
//远程IP和端口号
IF tcpClient.parameter.sIp='' THEN
tcpClient.parameter.sIp:='192.168.0.240';
tcpClient.parameter.nPort:=55;
END_IF
//功能块
tcpClient.FB(
TcpClientControl:=tcpClient.control ,
TcpClientParameter:=tcpClient.parameter ,
TcpClientStatus=>tcpClient.status );
//复位
IF tcpClient.status.bSendDone THEN
tcpClient.control.bSend:=FALSE;
END_IF
P_tcp_server
//本地IP和端口号
IF tcpServer.parameter.sIp='' THEN
tcpServer.parameter.sIp:='192.168.0.240';
tcpServer.parameter.nPort:=66;
END_IF
//功能块
tcpServer.FB(
TcpServerControl:=tcpServer.control ,
TcpServerParameter:=tcpServer.parameter ,
TcpServerStatus=>tcpServer.status );
//复位
IF tcpServer.status.bSendDone THEN
tcpServer.control.bSend:=FALSE;
END_IF