对欧姆龙PLC使用Python程序连接使用方法的研究

  作者:牛凯,李冰融,李鑫(国网上海市电力公司,上海 200235) 时间:2023-08-20来源:电子产品世界

编者按:在工业上PLC的使用十分广泛,其是许多大规模工作系统的基础控件。欧姆龙PLC提供Fins协议作为与其通信的方法,为了搭建计算机主机与PLC通信的桥梁,需要专门的Python程序用于与欧姆龙通信。本文介绍了使用Python程序与欧姆龙PLC进行通信的基本步骤以及在项目中Python通信程序的具体构建方法,在如今基于Python程序进行Fins协议进行通信的资料较少的情况下,对同类型的项目有着借鉴作用。


0 引言

PLC( 可编程逻辑控制器) 是一种专门为在工业环境下应用而设计的数字运算操作电子系统。在工业上PLC的使用十分广泛,其是许多大规模工作系统包括钢铁、石油、化工、电力、建材、机械制造、汽车、轻纺、交通、环保、文化娱乐等各行业中得到广泛的应用的基础控件。虽然PLC 对基础的工业控制能起到很好的效果,但对于更加复杂的应用场景,单纯使用PLC 进行控制难度较大。因此为了实现较为复杂的功能,在PLC 的上层,往往需要使用应用更加广泛的编程语言如C++、Python编写的复杂程序等进行控制,由于PLC 的运行与承载程序的上位计算机的底层逻辑并不相同,PLC 与上位计算机的通信成为工程上的重要课题。在实际应用中不同厂家所提供的PLC 通信方法并不相同,因此需要根据实际需求设计针对性的通信程序[1]

欧姆龙PLC提供Fins协议作为与其通信的方法,为了搭建计算机主机与PLC 通信的桥梁,当计算机使用Python语言编写控制逻辑时,需要专门的Python 通信程序用于与PLC 通信。由于大部分的PLC 设备都不直接与Python程序直连,而是通过C/C++ 的方式作为中间层的程序,这使得网上公开的使用Python 程序基于Fins 协议通信欧姆龙PLC 的程序难以寻找且仅有的程序注释解释不足,在实际运行过程中容易出现各种问题,自己根据实际要求开发对应的Python 通信程序是必要的[2]

本文介绍了使用Python 程序与欧姆龙PLC 进行通信的基本步骤以及在项目中Python 通信程序的具体构建方法,在如今基于Python 程序进行Fins 协议进行通信的资料较少的情况下,对同类型的项目有着借鉴作用。

1 Python程序与欧姆龙PLC通信

在进行程序上的通信前首先要建立物理上的连接。此次使用的欧姆龙PLC 型号为CP1H,其状态如图1 所示。此次选择的通讯方式是通过网线连接,一端连接计算机,一端连接PLC,用以传输数据,该PLC 还能够使用USB 连接,此时可以使用对应的调试程序对其进行修改,主要用于程序调试和测试。

硬件连接后,下一步则是进行软件的连接通讯,Fins协议属于数据层的协议,依赖于TCP/IP 协议,该型号的PLC 使用TCP 协议进行通讯,这里Fins 协议将作为TCP协议的数据进行传输。TCP协议的可靠性较好,但传输数据需要经过多次确认,因此在速度上略有损失。同时Fins 协议也规定了自己的返回信息。Fins 协议的数据传递逻辑如下。

1692475083141464.png

图1 CP1H型PLC与连接

1.1 TCP连接

在主机与PLC 沟通之前,首先要建立TCP 的连接。这一部分可以调用Socket 包来实现,对于不同语言来说,需要设置的结构会存在一些差别。TCP 协议共需要经过3 次握手,第1 次握手为客户端向服务端发送网络包,以此发起连接,同时向服务端告知自己的传输能力。第2 次为服务端向客服端回发,以测试客户端的接受能力以及服务端的发送能力。第3 次客户端再次向服务端发信,进行进一步确认,从而进行联系。在TCP 层面,之后每次传递数据都会收到回复。

1.2 Fins连接

完成TCP 连接后,接下来依靠TCP 协议进行Fins协议的连接。对于Fins 协议连接也需要进行一次请求,这里的请求与TCP 不同,只需要进行两次,一次由主机向PLC 发送请求信息,另一次由PLC 发送确认信息,这一过程规定了Fins 协议通信中的一些基础信息,包括节点地址、节点网络号等。

1.3 PLC通信

当主机和PLC 完成确认后就可以进行信息的传输工作。对于Fins 协议通信,最重要的特点就是所有的数据请求都由主机发出,PLC 只进行被动应答操作。如对于读入操作,由主机发送信息,确认要进行读取以及读取的位置,PLC 接受到信号后按照信号进行操作,之后将数据进行返回[3],在这种情况下,主机被称为发送方,而PLC 被称为接收方。在这种框架下,命令只能由发送方发出,PLC 会将数据存储在实现规定的地方,让主机发布命令获取。

2 Fins数据帧

Fins 数据帧包括Fins header、Fins command 和Fins data3 部分,其中Fins header 用于对地址目标进行识别,Fins command 用于传递命令,而Fins data 用于传输所需数据。在Fins 协议中,发送方使用的命令帧和接收方使用的响应帧的结构是有所区别的,其中命令帧的主要结构如下。

2.1 Fins header

该部分共有10个字节,按顺序依次为ICF(Information Control Field),用于显示框架信息,由4 个子字段组成,有效信息包括是否使用网关、该数据的具体类型(响应或命令)以及是否必须进行回应,该字节还有5个保留位,在一些情况下可以指定一些特殊信息;RSV(Reserved),系统保留字;GCT(Gateway count),网关的允许数量;DNA(Destination  network address)发送目标的网络地址,用于指定目标的节点网络号;DA1(Destination node number)目标节点地址,此处需要注意的是可以设置为FF,此时为广播编号;DA2(Source unit number)目的单位地址,指定目标节点的单元编号;SNA(Source network address)发送方的网络地址,用于指定发送方所在的节点网络号,SA1(Source node number)发送方的节点地址;SA2(Source Unit address)发送方的目的单位地址;SID(Service ID)服务序列号,用于标识生成传输过程,响应中返回相同数字来匹配命令和响应。以上各单元均占1 个字节。

2.2 Fins command

该部分共占两个字节,包括MRC 和SRC,分别储存了1 个字节的请求代码,其中MRC 为主代码,决定命令类别,SRC 为次要代码,决定类别下的具体命令。例如当MRC 为01 时,类型为I/O 读写,此时当SRC为01 时,该命令为读取I/O。读取Fins 协议能够指定的命令相当多,常见的操作包括读写I/O 信息、读写参数区信息、操作模式切换、状态读取、时间读取、读写故障信息、读写文件和强制设置某些位等。

2.3 Fins data

存放需要传输的数据,最大2 000 字节,实际结构受到Fins command部分的约束,即不同命令需要传输的数据格式是不同的。例如读取I/O 区时,data 区的结构为一个字节的I/O 储存区的对应编号、3 个字节的数据起始位置和两个字节的读取数据大小。

对于响应帧,其与命令帧的区别在于Fins data 部分增加了两个字节,分别为MRES、SRES,存储了命令帧的主相应和子响应代码,其和实际的传输数据合一起组成了FINS 数据域,这使得响应帧能够传输的实际数据最大值变为1 998 个字节。

确定了欧姆龙PLC 传输数据的基本格式后,接下来就是设计所需的Python 程序了。本设计使用了Python包的socket 进行编写,通过调用该包的方式,可以避免对TCP 协议的头部进行设计和模拟,简化操作。

3 PLC连接过程的程序设计

3.1 对PLC进行初步连通

在对PLC 进行Fins 协议通信前,首先要确认连通了PLC 本身。此时应输入PLC 的IP 地址,还需要PLC的端口号,欧姆龙PLC 的端口号默认为9 600,基本不会改变。计算机的IP 地址由函数进行获取,由于不同系统获取IP 地址的方式不同,需要对应编写函数,再进行汇总,再使用socket 包自带的TCP 通讯函数在TCP 层面将主机与PLC 进行连通,测试成功连接后就可以进行下一步骤。

3.2 对PLC进行握手

根据之前的PLC 沟通过程,对PLC 进行握手是进行数据传输的必要步骤。拼接PLC 帧的方式是首先根据通信帧的具体结构对得出各个部分的具体数据,根据要求转换为十六进制,再转化为字符串,拼接在一起。拼接完数据后,再将数据发送出去,等待PLC 的响应和对应的连接数据传回。数据传回后,对其进行核对,不为空则成功连接,否则输出连接失败。如果数据超过一定时间没有传回,同样输出连接失败。

3.3 使用PLC

本项目中,主要通过程序对PLC的数据区进行操作。一共涉及读数据和写数据两种操作。在读数据的过程中,需要分别设计Fins 帧中的3 部分,其中Fins header由于主要用于输出连接信息,Fins command 则需要输出命令的具体内容,包括读命令,读取的具体区域,本项目中指DM 区,读数据的具体起始地址以及读取的长度,Fins data 则为空。然后将3 段拼接起来进行输出。之后线程开始等待PLC 返回的具体数值,数据返回后,对命令进行解析判断,当格式符合要求时,读取对应的数据,并对其进行格式转换。等待需要设计1 个时限,当超过一定时间数据仍为进行返回或者没有返回正确数据时,认为发生了未知错误,程序报错并退出,并及时通知主程序。写数据与读数据存在一些区别,包括Finsdata 将输出写入命令,写入的具体区域,写数据的具体起始区域以及写入长度,之后还要传输经过格式转换后的写入数据。当命令传输后,只需要解析返回帧是否符合要求即可。

3.4 注意事项

除了对于读写数据需要设计专门的函数外,由于不同的数据类型数据结果区别很大,且PLC 的数据类型与Python 不能简单兼容,需要将数据分为Bool、UShort、Int、Float 和String 几类,根据具体情况分别设计读写函数,且不同情况下的字符转换方式也需要分别设计。对于Bool 类型的数据,由于Python 中将Bool和数字分为两类,读取后需要将其转换为对应的数字,对于数字类型,则需要根据实际存放的要求转换为对应的十六进制数。对于Float 类型数据需要注意小数点的位置。对于String 类型则需要逐一读取字符,先转换回十进制字符,再根据对应的ASCII 码值替换成对应的字符。对于写操作则按以上进行相反的操作。对于位操作,由于其不需要进行类型转换,为了提高读取写入速度,需要设计专门的写入读取函数,以简化操作步骤,提高运行效率。最后对于所有操作都需要设计1 个时钟计数,当1 个操作经过一定时间没有被响应,则判断连接出现问题,需要及时向上层程序进行反馈。

在实际一般的需求通信的程序运行过程中,一般需要单独开辟1 个线程负责与PLC 的连接通信操作,并将其全程挂起,以达到实时接收发送数据的目的,但这样可能会占用大量的内存资源。鉴于Fins 协议可以只从主机一端开始通信的特点,可以设计专门的线程函数,在未使用时将其挂起,当需要使用是再进行唤醒和调用,从而提高使用效率,将更多内存放松给主机使用。这种操作的缺点在于,当系统需要与PLC 进行通信时,才可能得知现在的连接状态是否出现问题。如果需要对连接状态进行实时控制,还是应当使用连续的进程。

为了保证数据进行平稳传输,还需要为线程设计1个锁对象,用于锁定通讯流程,使流程过程中其操作的数据不会被随意改变且线程不会被随意中断,保证整个读取过程的稳定性。此外当通信的中间环节发生错误时,需要及时将信号发送给上层程序,之后退出通信。值得注意的是,Fins 协议中不存在实际上的退出过程,这意味着实际上通讯是能够随时中断的,并不会影响端口的使用和占用[4]

由于PLC 存在多个接口,所以可以在连通的情况下使用另一根导线连接另一个接口,这样可以使用另一台主机对PLC 的实时状态进行监测,以在没有让PLC实际运行线下设备的状态下进行调试。

在设计完成后,需要对程序设计测试。本次测试使用CX-Programmer 软件在另一台监控主机上进行,在运行Python 程序前先查看PLC 的DM 区的具体数据,再使用程序进行PLC 进行读写操作,然后再使用软件查看具体数据变化,对于读操作则查看是否读取了对应数据,对于写操作则查看是否写入正确数据,结果完美完成了读出写入数据的任务,反应时长达到使用要求,且当人为设计了连接错误后,能较好地将连接错误反应到上层程序。

4 结束语

本文设计了欧姆龙PLC 使用Python 程序基于Fins协议的进行通信的具体步骤,并设计了一种基于Python的软件通信方法,该方法完成了主机与PLC的连接通信,并完成了读取数据区数据和写入数据的操作,在Python软件程序与欧姆龙PLC 通过Fins 协议进行通讯的网络资料较少的现状下,具有一定的借鉴作用。由于现存的实际项目对于通讯的功能要求不高,不要求通过软件对PLC 进行实际控制,本文只研究了读取和写入数据区的两类功能,在今后的研究中,还需要继续研究对PLC 进行控制以及读写大文件的软件程序编写方法,从而提高程序的泛用性和功能性。

参考文献:

[1] 黄燕民,陈宏轩,罗友高,等.基于Python与S7-1500的清洗机器人运动控制系统[J].机电一体化,2022,28(Z2):79-84.

[2] 王奚,王新月,李航,等.面向PLC产品的自动化测试系统平台设计与实现[J].自动化仪表,2022,43(5):8-11+19.

[3] 韩志三.基于Python的丰炜系列PLC与PC串行通信的实现[J].硅谷,2013,6(22):59-60+15.

[4] 周任杰,刘宇,张子立,等.基于Python的龙骨成型机通信方案设计[J].计算机应用与软件,2019,36(06):93-96+135.

(本文来源于必威娱乐平台 杂志2023年8月期)

关键词: 202308 PLC Python 通信

加入微信
获取电子行业最新资讯
搜索微信公众号:EEPW

或用微信扫描左侧二维码

相关文章

查看电脑版