工控网首页
>

应用设计

>

运用VC#编程通过MPI方式与西门子S7系列PLC通讯

运用VC#编程通过MPI方式与西门子S7系列PLC通讯

2005/7/26 16:33:00
西门子S7300/400系列的PLC没有公开通讯协议,但西门子公司提供的ProDave软件公开了一系列库函数,使用计算机高级语言调用这些函数,可实现以MPI的方式与PLC通讯。当今的高级语言VC#有着非常高效的开发手段,在把基础类库、标准模块都编好的情况下,开发监控界面的速度比WinCC慢不了多少,但灵活性却是WInCC无法比的。 大家只要找到西门子的ProDave中的动态连接库:W95_S7.DLL,并把它注册到你的计算机即可(当然,你若有一套完整的ProDave安装程序,安装即可自动注册),然后在C#这边编程调用,下面来讲解如何在C#中调用动态库。 由于W95_S7.DLL是用C语言编写的,很多函数接口不适用于C#,因此我们可以创建一个C#类库,把这些函数进行封装,每次开发监控界面调用此类库即可。 一、 C#中调用DLL库的方法 1、 在名称空间之前使用: using System.Runtime.InteropServices; //用于调用动态库的接口,一定要引用 2、 导入每一个库函数,均要在函数声明之前使用属性字段: [DllImport("w95_s7.dll")] 譬如与PLC建立连接的库函数load_tool(),应使用如下的方式进行声明: [DllImport("w95_s7.dll")] private extern static int load_tool(byte nr,string device,byte[,] adr_table); 二、 ProDave中的重要库函数介绍 1、 与PLC建立通讯连接的库函数:load_tool() 该函数必须在其他所有函数调用之前被调用,在C中的声明为:int load_tool(int nr,char* device,char* adr_table);由于C#在安全模式下不容许使用指针,因此我们把它转换成C#模式: private extern static int load_tool(byte nr,string device,byte[,] adr_table); 参数 nr: 指定连接号1-4,一般设为1 device: 设备名称,西门子的示例是设为"s7online",测试时,若改成其他名称好像连不上。 adr_table: 一个二维数组,指定一系列连接参数,依次为:MPI地址、保留为0、CPU槽号、CPU机架号。在一个MPI网络中若有多个CPU时,可指定一个以上的连接列。最后一列的参数的MPI地址应制定为0,以标志参数列结束。 e.g.一个MPI网中有两个CPU,他们的MPI地址分别为2和3,槽号均为2,机架号均为0,则可按如下方式调用: byte[,] bt={{2,0,2,0},{3,0,2,0},{0,0,0,0}}; int err=load_tool(1, "s7online",bt); 注:ProDave中的所有库函数均返回整数数据,为0表示调用该函数成功,为其他十进制数时,可以查找西门子文档,看是什么错误。 可以看出,上面的函数不利于我们使用,我们可对他进行封装: <1>、在类之前声明用于传递参数列表的结构: #region 定义与外部联系的结构变量 /// /// 定义MPI链接参数 /// public struct ConnectionInfo{ /// /// 定义CPU的MPI地址 /// public byte Addres; /// /// 定义CPU的机架号 /// public byte Rack; /// /// 定义CPU的槽号 /// public byte Slot; } #endregion <2>、编写实现上述功能的公有方法: #region 与动态库函数相对应的公开函数 /// /// 建立连接,同一个连接只容许调用一次 /// /// 连接号1-4 /// 指定链接参数 /// 返回10进制错误号,0表示没有错误 public static int Open(byte cnnNo,ConnectionInfo[] cnnInfo){ int err; //传递参数不正确 if(cnnInfo.Length<=0){ return -1; } byte[,] btr=new byte[cnnInfo.Length+1,4]; //转换链接表 for(int i=0;i三、 ProDave中的其他一些函数的C#声明方式如下: /// /// 读取Output值 /// /// 指定QB号 /// 指定有多少个QB字节需要读出 /// 返回读出的值 /// [DllImport("w95_s7.dll")] private extern static int a_field_read (int no,int anzahl,ref long buffer); /// /// 向Output写入值 /// /// 指定QB号 /// 指定有多少个QB字节需要写入 /// 指定写入值 /// [DllImport("w95_s7.dll")] private extern static int a_field_write (int no,int anzahl,ref long buffer); /// /// 获取PLC的运行状态 /// /// 返回0或者1,0表示Run;1表示Stop或者Restart /// [DllImport("w95_s7.dll")] private extern static int ag_zustand (ref byte buffer); /// /// 测试指定的DB块是否存在 /// /// 返回一系列块的存在状态,=0不存在,!=0存在 /// [DllImport("w95_s7.dll")] private extern static int db_buch (ushort[] buffer); /// /// 从DB中读取数据 /// /// 指定DB块号 /// 指定读取的起始字序号,=0表示DBW0,=1表示DBW2 /// 指定读取的对象有多少个字 /// 返回值 /// [DllImport("w95_s7.dll")] private extern static int db_read(int dbno, int dwno, ref int anzahl, ref long buffer); /// /// 向DB中写入数据 /// /// 指定DB块号 /// 指定写入的起始字序号,=0表示DBW0,=1表示DBW2 /// 指定写入的对象有多少个字 /// 写入值 /// [DllImport("w95_s7.dll")] private extern static int db_write(int dbno, int dwno, ref int anzahl, ref long buffer); /// /// 读取Input的值 /// /// 指定IB号 /// 指定有多少个IB字节需要读出 /// 读取返回的值 /// [DllImport("w95_s7.dll")] private extern static int e_field_read (int no,int anzahl,ref long buffer); /// /// 获取MB变量的位状态值 /// ///
投诉建议

提交

查看更多评论
其他资讯

查看更多

工业自动化设计高级参考

使用西门子的SCL语言编写ABB变频器的总线控制程序块

PLC的面向对象编程

简化监控软件的编程方法