手摸手教你撕碎西门子S7通讯协议02--socket连接

1、S7协议通讯流程回顾

1)建立Socket连接:进行TCP三次握手 

这里是指要建立socket的tcp连接,是tcp连接而不是udp连接,tcp连接是可靠连接,tcp连接就是要有稳定的IP地址,它是通过字节方式进行通讯,在程序中就是要创建socket对象,利用socket的方式来实现字节的发送和接收,包括解析数据,这个socket是连接谁呢?肯定是连接plc设备,所以plc设备必须有IP地址,端口号,那么谁去连接了,当然是我们的PC电脑,电脑在这个场景下就是我们的上位机,软件工程师通过开发应用程序来与PLC通讯,模型如下:

2)COTP的握手请求(请求建立通信)

在“握手”之后,并不能马上进行数据交换,需要进行这一步的操作,即客户端发送COTP报文给服务端,在COTP报文中包含“连接请求”和“Destination TSAP”,以明确CPU的机架号和槽号;服务端应答COTP报文,包含“连接确认”;这样服务端就清楚了客户端需要和哪个CPU来进行数据通讯。在这个过程中,有非常标准和严重要求的报文格式,这个过程会有22个字节,每个报文的字段内容代表不同的含义,千万不能搞错,否则服务器,也就是PLC就会不搭理你。报文信息如下,搞不懂没有关系,后面的文章会详细介绍,手摸手教,服务到位,包你满意。

3)S7COMM的握手请求(请求建立操作通信)

在成功完成上面的COTP请求后,现在客户端发送S7 Communicaton报文给服务端,在S7Communicaton报文中包含“通讯请求”; 服务端反馈S7 Communicaton报文。同样的报文中每个字段都有含义,必须严格遵守,这个过程是交换通信信息,共25个字节,报文信息如下:搞不懂没有关系,后面的文章会详细介绍,手摸手教,服务到位,包你满意。

4) 进行读写操作(S7协议报文)

 在成功完成上面的1,2,3的三个过程后,现在才是读、写、PLC启停、时间、上传下载等,读取的报文比写入的报文要简单些,但报文结构确实复杂,需要大师给你开光,现在搞不懂没有关系,后面的文章会详细介绍,手摸手教,服务到位,包你满意。

2、开搞socket连接 

1)安装西门子博途v15环境

应用环境要求是win10企业版,搭建这个西门子PLC的环境还是蛮消耗时间,精力和能力,耐心的,要求也高,这个事情必须做好,不能偷懒,绝不能失败,否则整个系列的内容就实现不了,具体安装过程请看下面文章,这里不展示,因为过程实在是众多,需要细致。

windows10企业版安装西门子博途V15---01准备环境_博途v15.1安装需求-CSDN博客

windows10企业版安装西门子博途V15---02安装软件_博图v15软件安装步骤-CSDN博客

windows10企业版安装西门子博途V15---03安装仿真软件_西门子v15仿真软件-CSDN博客

windows10企业版安装西门子博途V15---04连接测试_博图v15第一次连接plc步骤-CSDN博客

1)西门子PLC存储区简介

I:数字量输入(DI)

Q:数字量输出

AI:模拟量输入

AQ:模拟量输出

V:变量存储区

M:位存储区

T:定时器存储区

C:计数器存储区

HC:高速计数器

AC:累加器

SM:特殊存储器

L:局部存储区

S:顺序控制继电器

DB:数据块

2)访问规则:bit、B、W、D B:byte W:word ->2byte D:double->4byte Bit: I0.0

DataType:

0x01 - BIT:一个无符号的bit
0x02 - BYTE:一个8位的数字
0x03 - CHAR:一个字符
0x04 - WORD:两个字节宽的无符号整数
0x05 - INT:两个字节宽的有符号整数。
0x06 - DWORD:四字节宽的无符号整数
0x07 - DINT:四字节宽的有符号整数
0x08 - REAL:四个字节宽的IEEE浮点数
0x1c - COUNTER:PLC程序计数器使用的计数器类型
示例:变量的示例地址是DB123X 2.1,它访问DB块123的第3个Byte的第2个Bit。 

3)在本应用中,创建了一个192.168.1.66的PLC设备和hnplc项目,如图

2)创建vs项目

 

 

3、连接代码   

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace west.siemenscomm
{
    internal class Program
    {
        /// <summary>
        /// plc的ip地址
        /// </summary>
        static string _ip="192.168.1.66";
        /// <summary>
        /// 端口号
        /// </summary>
        static int _port=102;
        /// <summary>
        /// 机柜号,插槽号
        /// </summary>
        static byte _rack=0, _slot=1;
        /// <summary>
        /// socket对象
        /// </summary>
        static Socket socket = null;
        /// <summary>
        /// 时间事件
        /// </summary>
        static ManualResetEvent TimeoutObject = new ManualResetEvent(false);
        /// <summary>
        /// 连接状态 
        /// </summary>
        static bool connectState = false;

        static void Main(string[] args)
        {
            Connect();
            Console.ReadKey();
        } 

        private static void Connect(int timeout = 50)
        {
            TimeoutObject.Reset();
            try
            {
                socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                socket.BeginConnect(_ip, _port, callback =>
                {
                    connectState = false;
                    var cbSocket = callback.AsyncState as Socket;
                    if (cbSocket != null)
                    {
                        connectState = cbSocket.Connected;
                        if (cbSocket.Connected)
                            cbSocket.EndConnect(callback);
                    }
                    TimeoutObject.Set();
                }, socket);
                TimeoutObject.WaitOne(2000, false);
            }
            catch (SocketException ex)
            {
                if (ex.ErrorCode == 10060)
                    Console.WriteLine(ex.Message);
            }
            if (socket == null || !socket.Connected || ((socket.Poll(200, SelectMode.SelectRead) && (socket.Available == 0))))
            {
               Console.WriteLine("网络连接失败");
            }
            Console.WriteLine(connectState==true?"连接成功":"连接失败");
        }
    }
}
 

 一定注意一个问题,看这里

4)运行测试 

3、小结

 这就是第一个流程,建立TCP的三次握手,它是通过socket对象通讯实现的,小伙伴们,明白了不?下节继续硬起来。

原创不易,打字截图不易,走过路过,不要错过,欢迎点赞,收藏,转载,复制,抄袭,留言,动动你的金手指,早日实现财务自由   

  • 19
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

hqwest

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值