C# ModBus Tcp 直接读写PLC寄存器 您所在的位置:网站首页 plc怎么实现读取g代码 C# ModBus Tcp 直接读写PLC寄存器

C# ModBus Tcp 直接读写PLC寄存器

2023-09-02 19:05| 来源: 网络整理| 查看: 265

C# ModBus Tcp 直接读写PLC寄存器

MODBUS通用数据帧: 在这里插入图片描述在这里插入图片描述测试用modbus服务器下载地址: https://download.csdn.net/download/weixin_42288222/12457317 测试修改寄存器的值为1 代码下载地址:

具体modbus协议见pdf文档这里就不说了(下载包里有) 在这里插入图片描述 https://download.csdn.net/download/weixin_42288222/12457342

1.这边使用裸Tcp/ip协议 通过socket发送modbus的通讯报文地址数据等,操作plc寄存器(没有使用别人写好的类库)。

界面如下: 界面 2.TCP部分程序如下: 内联代码片。

using System; using System.Collections.Generic; using System.Linq; using System.Net; using System.Net.Sockets; using System.Text; using System.Threading; using System.Threading.Tasks; using System.Windows.Forms; namespace ModbusTcp { class TCP { public delegate void ChangeFormList(bool change); public event ChangeFormList ChangeList; public delegate void TcpStutas(bool change); public event TcpStutas ReturnFromPLC; readonly object obj = new object(); public string STR;//接收到的消息 public string SendMsg; /// /// 连接状态:true 连接中 false 连接中断 /// public bool isConnected; Socket socketSend; public bool Connect(string ip, int port) { try { socketSend = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); IPAddress IP = IPAddress.Parse(ip); IPEndPoint point = new IPEndPoint(IP, port); ; socketSend.Connect(point); isConnected = true; return true; } catch (Exception) { MessageBox.Show("请填写正确的IP地址和端口号!"); return false; } } /// /// 接收服务端返回的消息 /// void Received() { try { //1M的缓存区 byte[] data = new byte[1024]; //实际接收到的有效字节数 int len = socketSend.Receive(data);// 将接受到的数据存入到输入buffer中 if (len == 0) { isConnected = false; } int length = data[5];//读取数据长度 Byte[] datashow = new byte[length + 6];//定义所要显示的接收的数据的长度 for (int i = 0; i STR = stringdata; }; if (data[7] == 0x03) { STR = stringdata; };//功能码为3 if (data[7] == 0x05) { STR = stringdata; }; if (data[7] == 0x06) { STR = stringdata; };//功能码为6 if (data[7] == 0x0F) { STR = stringdata; }; if (data[7] == 0x10) { STR = stringdata; }; ChangeList(true); } catch (Exception ex) { MessageBox.Show("接收数据出现异常!" + ex.Message, "错误", MessageBoxButtons.OK, MessageBoxIcon.Error); } } /// /// 向服务器发送消息 /// /// /// public void Send(byte[] msg) { lock (obj) { try { socketSend.Send(msg); for (int i = 0; i MessageBox.Show(" 发送数据出现异常!" + ex.Message, "错误", MessageBoxButtons.OK, MessageBoxIcon.Error); } } } /// /// 16转10进制 /// /// /// public int GetDex(string msg) { int res = Convert.ToInt32(msg, 16); return res; } } }

3.主界面部分: 内联代码片。

using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; namespace ModbusTcp { public partial class Form1 : Form { public Form1() { InitializeComponent(); } /*具体详见modbus协议中文版.pdf 功能码说明(括号内为对应的16进制): 01(01):byte访问 读线圈 02(02):byte访问 读输入离散量 05(05):byte访问 写单个线圈 15(0F):byte访问 写多个线圈 03(03):16位byte访问 读多个寄存器 04(04):16位byte访问 读输入寄存器 06(06):16位byte访问 写单个寄存器 16(10):16位byte访问 写多个寄存器 23(17):16位byte访问 读/写多个寄存器 22(16):16位byte访问 屏蔽写寄存器 20(14):文件记录访问 读文件记录 21(15):文件记录访问 写文件记录 43(2B):封装接口 读设备识别码 */ private void button1_Click(object sender, EventArgs e) { //连接Tcp服务器 tcp.Connect(textBox1.Text, 502); } TCP tcp = new TCP(); private void Form1_Load(object sender, EventArgs e) { tcp.ChangeList += new TCP.ChangeFormList(f_ChangeList);//tcp通讯显示发送 tcp.ReturnFromPLC += new TCP.TcpStutas(f_TcpAtutas);//tcp通讯显示返回 } private void f_TcpAtutas(bool change) { Invoke(new Action(() =>{ richTextBox1.Text += tcp.STR + "***" + DateTime.Now.ToString("yyyy/mm/dd HH:mm:ss") + "\r\n"; } )); } private void f_ChangeList(bool change) { Invoke(new Action(() => { richTextBox2.Text += tcp.STR + "***" + DateTime.Now.ToString("yyyy/mm/dd HH:mm:ss") + "\r\n"; })); } /// /// 数据格式:0-6位:报文头;7位:功能码;8-9位:起始地址;10-11位:寄存器位数(读)/写入数据(写) /// byte[] data = new byte[] { 0x00, 0x01, 0x00, 0x00, 0x00, 0x06, 0x01, 0x06, 0x00, 0x00, 0x00, 0x01 }; private void button2_Click(object sender, EventArgs e) { try { data[7] = GetHex(textBox2.Text); data[11] = GetHex(textBox3.Text); data[9] = GetHex(textBox4.Text); tcp.Send(data); } catch (Exception ex) { MessageBox.Show(ex.ToString()); } } /// /// 10转16 /// /// /// private byte GetHex(string msg) { byte hex = Convert.ToByte(msg); return hex; } private void timer1_Tick(object sender, EventArgs e) { if (tcp.isConnected) { button1.Enabled = false; textBox1.Enabled = false; } else { button1.Enabled = true; textBox1.Enabled = true; } } } }


【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有