Modbus RTU 协议介绍

异步串行传输方式,采用二进制格式,适用于串行通讯(如RS-485),效率高,是工业现场的主流选择。

主站是Master,从站是Slave。

Modbus RTU 协议格式

帧结构

  • 地址码(1字节):从设备的地址,取值1-247。
  • 功能码(1字节):指定操作类型,如读取或写入。
  • 数据区(长度可变):包含具体的操作数据。
  • CRC校验(2字节):循环冗余校验码,确保数据无误。

功能码

功能码功能用途
01读线圈状态获取开关量输出状态
03读保持寄存器获取16位可读写数据
04读输入寄存器获取16位只读数据
05写单个线圈控制单个开关量输出
06写单个寄存器修改单个16位数据
16(0x10 十六进制)写多个寄存器修改多个16位数据

CRC 校验

CRC(循环冗余校验)是Modbus RTU的关键,用于检测传输错误。发送方计算CRC并附加在帧尾,接收方重新计算并比对。

CRC16校验算法示例:

const unsigned short wCRCTalbeAbs[] =
{0x0000, 0xCC01, 0xD801, 0x1400, 0xF001, 0x3C00, 0x2800, 0xE401, 0xA001, 0x6C00, 0x7800, 0xB401, 0x5000, 0x9C01, 0x8801, 0x4400,
};unsigned short mt_api_crc16(unsigned char *ptr, unsigned int len) 
{unsigned short wCRC = 0xFFFF;unsigned short i;unsigned char chChar;unsigned char temp[2];for (i = 0; i < len; i++){chChar = *ptr++;wCRC = wCRCTalbeAbs[(chChar ^ wCRC) & 15] ^ (wCRC >> 4);wCRC = wCRCTalbeAbs[((chChar >> 4) ^ wCRC) & 15] ^ (wCRC >> 4);}temp[0] = wCRC&0xFF; temp[1] = (wCRC>>8)&0xFF;wCRC = (temp[0]<<8)|temp[1];return wCRC;
}

0x01 功能码(读线圈状态)

请求数据

01 01 00 00 00 08 9C 03
  • 01:从设备地址(1-247)
  • 01:功能码(读线圈状态)
  • 00 00:起始线圈地址(2 字节)
  • 00 08:线圈个数(读取 8 个线圈)
  • 9C 03:CRC校验

更详细的格式如下:

从设备地址 + 功能码 + 起始线圈地址(高位) + 起始线圈地址(低位) + 线圈数量(高位) + 线圈数量(低位) + CRC(高位) + CRC(低位),一共 8 个字节。

响应数据

01 01 01 55 78 3A
  • 01:从设备地址(1-247)
  • 01:功能码(读线圈状态)
  • 01:线圈状态数据的总字节数(<font style="color:rgb(0, 0, 0);">ceil(线圈数量/8)</font>,8 个线圈 = 1 字节)
  • 55:线圈状态数据(1 个字节)
  • 78 3A:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 数据长度 + [线圈状态数据(N 字节)] + CRC(高位) + CRC(低位)

0x03 功能码(读保持寄存器)

请求数据

01 03 00 00 00 01 C4 0B
  • 01:从设备地址(1-247)
  • 03:功能码(读保持寄存器)
  • 00 00:起始寄存器地址(2 字节)
  • 00 01:寄存器个数(读取 1 个寄存器)
  • C4 0B:CRC校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位) + 起始寄存器地址(低位) + 寄存器数量(高位) + 寄存器数量(低位) + CRC(高位) + CRC(低位),一共 8 个字节。

响应数据

01 03 02 19 98 B2 7E
  • 01:从设备地址(1-247)
  • 03:功能码(读保持寄存器)
  • 02:后面数据的字节数,一个寄存器有 2 个字节,所以后面的字节数等于 2*查询的寄存器数量
  • 19 98:寄存器的值是 19 98
  • B2 7E:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 数据长度 + 寄存器数据 + CRC 校验码

字节数:1+1+1+2*N+2

0x04 功能码(读输入寄存器)

请求数据

01 04 00 01 00 03 60 0A 
  • 01:从设备地址(1-247)
  • 04:功能码(写输入寄存器)
  • 00 01:起始寄存器地址(2 字节)
  • 00 03:输入寄存器数量
  • 60 0A:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位) + 起始寄存器地址(低位) +寄存器数量(高位) + 寄存器数量(低位) + CRC 校验(高位) + CRC 校验(高位),一共 8 个字节。

响应数据

01 04 06 00 0A 01 F4 03 E8 75 3B
  • 01:从设备地址(1-247)
  • 04:功能码(写输入寄存器)
  • 06:输入寄存器数据的总字节数(寄存器数量 ×2,3×2=6 字节)
  • 00 0A:第一个输入寄存器值
  • 01 F4:第二个输入寄存器值
  • 03 E8:第三个输入寄存器值
  • 75 3B:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 数据长度 + [N 组寄存器数据(每组 2 字节)] + CRC 校验(高位) + CRC 校验(高位)

0x05 功能码(写单个线圈)

请求数据

01 05 00 03 FF 00 8C 3A
  • 01:从设备地址(1-247)
  • 05:功能码(写单个线圈)
  • 00 03:目标线圈地址
  • FF 00:线圈状态值
  • 8C 3A:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 目标线圈地址(高位) + 目标线圈地址(低位) + 线圈状态值(高位) + 线圈状态值(低位) + CRC 校验(高位) + CRC 校验(高位),一共 8 个字节。

响应数据

01 05 00 03 FF 00 8C 3A
  • 01:从设备地址(1-247)
  • 05:功能码(写单个线圈)
  • 00 03:目标线圈地址
  • FF 00:线圈状态值
  • 8C 3A:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 目标线圈地址(高位) + 目标线圈地址(低位) + 线圈状态值(高位) + 线圈状态值(低位) + CRC 校验(高位) + CRC 校验(高位),一共 8 个字节。

0x06 功能码( 写单个保持寄存器)

请求数据

01 06 00 00 00 01 48 0A
  • 01:从设备地址(1-247)
  • 06:功能码(写保持寄存器)
  • 00 00:起始寄存器地址(2 字节)
  • 00 01:写入的值
  • 48 0A:CRC校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位) + 起始寄存器地址(低位) + 写入值(高位) + 写入值(低位) + CRC(高位) + CRC(低位),一共 8 个字节。

响应数据

01 06 00 00 00 01 48 0A
  • 01:从设备地址(1-247)
  • 06:功能码(写保持寄存器)
  • 00 00:起始寄存器地址(2 字节)
  • 00 01:写入的值
  • 48 0A:CRC校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位) + 起始寄存器地址(低位) + 写入值(高位) + 写入值(低位) + CRC(高位) + CRC(低位),一共 8 个字节。

0x010 功能码( 写多个保持寄存器)

请求数据

01 10 00 02 00 03 06 00 0A 01 02 03 04 75 F5
  • 01:从设备地址(1-247)
  • 10:功能码(写保持寄存器)
  • 00 02:起始寄存器地址(2 字节)
  • 00 03:寄存器数量
  • 06:后续数据的总字节数(寄存器数量 x 2)
  • 00 0A:写入数据 1(2 字节)
  • 01 02:写入数据 3(2 字节)
  • 03 04:写入数据 3(2 字节)
  • 75 F5:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位)+ 起始寄存器地址(低位) + 寄存器数量(高位) + 寄存器数量(低位) + 数据总字节数 + [N 组写入值(每组 2 字节)] + CRC 高位 + CRC 低位

响应数据

01 10 00 02 00 03 A7 3C
  • 01:从设备地址(1-247)
  • 10:功能码(写保持寄存器)
  • 00 02:起始寄存器地址(2 字节)
  • 00 03:寄存器数量
  • A7 3C:CRC 校验

更详细的格式如下:

从设备地址 + 功能码 + 起始寄存器地址(高位)+ 起始寄存器地址(低位) + 寄存器数量(高位) + 寄存器数量(低位) + CRC 高位 + CRC 低位。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/diannao/98032.shtml
繁体地址,请注明出处:http://hk.pswp.cn/diannao/98032.shtml
英文地址,请注明出处:http://en.pswp.cn/diannao/98032.shtml

如若内容造成侵权/违法违规/事实不符,请联系英文站点网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

TCP/IP函数——sendmsg

sendmsg() 是 POSIX 标准中一个高级套接字发送函数,属于系统调用(由操作系统内核实现),定义在 <sys/socket.h> 头文件中。它的核心特点是支持复杂消息结构,不仅能发送常规数据,还能附加控制信息(如辅助数据、IP 选项等),适用于 TCP、UDP 等多种协议,功能比 sen…

运动控制中的插值运动(插补运动):原理、实现与应用

在自动化设备中,从起点到终点的精准轨迹控制是核心需求。当目标轨迹是直线、圆弧或复杂曲线时,仅通过离散的目标点无法实现平滑运动,这就需要插值运动(Interpolation Motion)技术 —— 通过控制算法在已知路径点之间计算出连续的中间点,使运动部件沿预定轨迹平滑移动。本…

GMT——用于人形全身控制的通用运动跟踪:两阶段师生训练框架下,全身基于单一策略,且自适应采样、MoE架构

前言 如此文《KungfuBot——基于物理约束和自适应运动追踪的人形全身控制PBHC&#xff0c;用于学习打拳或跳舞(即RL下的动作模仿和运控)》的开头所说 如此&#xff0c;便关注到最新出来的三个工作 第一个是GMT: General Motion Tracking for Humanoid Whole-Body Control第二个…

matlab版本粒子群算法(PSO)在路径规划中的应用

基于粒子群优化&#xff08;PSO&#xff09;算法的路径规划 MATLAB代码实现 1. 初始化环境和参数 % 初始化环境参数 mapSize [10, 10]; % 地图大小 startPoint [1, 1]; % 起点 endPoint [9, 9]; % 终点 obstacles [3, 3; 5, 5; 7, 7]; % 障碍物位置% PSO参数 numParticles …

Go语言面试:传值与传引用的区别及选择指南

在Go语言中&#xff0c;函数参数的传递方式有两种&#xff1a;传值&#xff08;pass-by-value&#xff09;和传引用&#xff08;pass-by-reference&#xff09;。理解这两种方式的区别及其适用场景&#xff0c;是成为Go语言开发高手的必备技能。本文将深入探讨Go语言中传值与传…

数据无言,网关有声 耐达讯自动化RS485转Profinet让千年液位数据“开口说话”

在能源行业的数字化转型浪潮中&#xff0c;你是否曾面临这样的困境&#xff1a; 现场大量采用RS485接口的液位计&#xff0c;数据孤立如信息孤岛&#xff0c;无法接入Profinet高速网络&#xff1f; 模拟信号传输距离受限&#xff0c;抗干扰能力弱&#xff0c;导致液位测量误差…

出口退税新政大提速:企业如何抓住政策红利,提升最高13%纯利?

近年来&#xff0c;出口退税政策的优化与升级&#xff0c;正在成为外贸企业提升资金周转率和利润率的关键。国家税务总局发布的 2022年第9号公告&#xff08;简称“9号公告”&#xff09;落地执行已两年&#xff0c;外贸行业普遍感受到退税速度显著加快&#xff0c;平均退税周期…

使用pytorch创建/训练/推理OCR模型

一、任务描述 从手写数字图像中自动识别出对应的数字&#xff08;0-9&#xff09;” 的问题&#xff0c;属于单标签图像分类任务&#xff08;每张图像仅对应一个类别&#xff0c;即 0-9 中的一个数字&#xff09; 1、任务的核心定义&#xff1a;输入与输出 输入&#xff1a;28…

新启航开启深孔测量新纪元:激光频率梳技术攻克光学遮挡,达 130mm 深度 2μm 精度

摘要&#xff1a;本文聚焦于深孔测量领域&#xff0c;介绍了一种创新的激光频率梳技术。该技术成功攻克传统测量中的光学遮挡难题&#xff0c;在深孔测量深度达 130mm 时&#xff0c;可实现 2μm 的高精度测量&#xff0c;为深孔测量开启了新的发展篇章。关键词&#xff1a;激光…

GEO优化推荐:AI搜索新纪元下的品牌内容权威构建

引言&#xff1a;AI搜索引擎崛起与GEO策略的战略重心转移2025年&#xff0c;以ChatGPT、百度文心一言、DeepSeek为代表的AI搜索引擎已深入成为公众信息获取的核心渠道。这标志着品牌营销策略的重心&#xff0c;正从传统的搜索引擎优化&#xff08;SEO&#xff09;加速向生成式引…

uniapp的上拉加载H5和小程序

小程序配置{"path": "list/course-list","style": {"navigationBarTitleText": "课程列表","enablePullDownRefresh": true,"onReachBottomDistance": 150}}上拉拉触底钩子onReachBottom() {var that …

【和春笋一起学C++】(四十)抽象数据类型

抽象数据类型&#xff08;abstract data type, ADT&#xff09;以通用的方式描述数据类型。C中类的概念非常适合于ADT方法。例如&#xff0c;C程序通过堆栈来管理自动变量&#xff0c;堆栈可由对它执行的操作来描述。可创建空堆栈&#xff1b;可将数据项添加到堆顶&#xff08;…

大文件断点续传解决方案:基于Vue 2与Spring Boot的完整实现

大文件断点续传解决方案:基于Vue 2与Spring Boot的完整实现 在现代Web应用中,大文件上传是一个常见但具有挑战性的需求。传统的文件上传方式在面对网络不稳定、大文件传输时往往表现不佳。本文将详细介绍如何实现一个支持断点续传的大文件上传功能,结合Vue 2前端和Spring Bo…

LeNet-5:手写数字识别经典CNN

配套讲解视频&#xff0c;点击下方名片获取20 世纪 90 年代&#xff0c;计算机已经能识别文本&#xff0c;但图片识别很困难。比如银行支票的手写数字识别&#xff0c;传统方法需要人工设计规则&#xff0c;费时费力且精度不高。 于是&#xff0c;Yann LeCun 及其团队提出了 Le…

如何在 C# 中将文本转换为 Word 以及将 Word 转换为文本

在现代软件开发中&#xff0c;处理文档内容是一个非常常见的需求。无论是生成报告、存储日志&#xff0c;还是处理用户输入&#xff0c;开发者都可能需要在纯文本与 Word 文档之间进行转换。有时需要将文本转换为 Word&#xff0c;以便生成结构化的 .docx 文件&#xff0c;使内…

Open SWE:重构代码协作的智能范式——从规划到PR的全流程自动化革命

在软件开发的演进史上,工具链的每一次革新都深刻重塑着开发者的工作方式。LangChain AI推出的Open SWE,作为首个开源的异步编程代理,正在重新定义代码协作的边界——它不再仅仅是代码生成工具,而是构建了从代码库分析、方案规划、代码实现到拉取请求创建的端到端自动化工作…

【ARDUINO】通过ESP8266控制电机【待测试】

需求 通过Wi-Fi控制Arduino驱动的3V直流电机。这个方案使用外部6V或9V电源&#xff0c;ESP8266作为Wi-Fi模块&#xff0c;Arduino作为主控制器&#xff0c;L298N作为电机驱动器。 手机/电脑 (Wi-Fi客户端) | | (Wi-Fi) | ESP8266 (Wi-Fi模块, AT指令模式) | | (串口通信) | A…

cuda编程笔记(18)-- 使用im2col + GEMM 实现卷积

我们之前介绍了cudnn调用api直接实现卷积&#xff0c;本文我们探究手动实现。对于直接使用for循环在cpu上的实现方法&#xff0c;就不过多介绍&#xff0c;只要了解卷积的原理&#xff0c;就很容易实现。im2col 的核心思想im2col image to column把输入 feature map 的每个卷积…

Loopback for Mac:一键打造虚拟音频矩阵,实现跨应用音频自由流转

虚拟音频设备创建 模拟物理设备&#xff1a;Loopback允许用户在Mac上创建虚拟音频设备&#xff0c;这些设备可被系统及其他应用程序识别为真实硬件&#xff0c;实现音频的虚拟化传输。多源聚合&#xff1a;支持将麦克风、应用程序&#xff08;如Skype、Zoom、GarageBand、Logic…

深入解析Django重定向机制

概述 核心是一个基类 HttpResponseRedirectBase&#xff0c;以及两个具体的子类 HttpResponseRedirect&#xff08;302 临时重定向&#xff09;和 HttpResponsePermanentRedirect&#xff08;301 永久重定向&#xff09;。它们都是 HttpResponse 的子类&#xff0c;专门用于告诉…