标题: STM32f103单片机与威纶通触摸屏modbus485通讯兼容上位机PLC程序 [打印本页]
作者: guobaox1981 时间: 2024-9-8 20:24
标题: STM32f103单片机与威纶通触摸屏modbus485通讯兼容上位机PLC程序
最近在改一个数控电源。主板保留有485通讯端口,无显示屏 主控stm32f103rc,没有原通讯协议,就依照电路重写了程序,加装oled显示器和时钟芯片,编码器,实现数字控制和库仑计,通讯,电源各种保护。调试中初期没写菜单系统相当头大。于是就利用modbus485通讯接触摸屏或串口助手调试。原机485部分为隔离式,使用485方便调试也保证了安全。电源完整代码暂时不公布。先公布modbus部分与触摸屏部分。程序可直接使用。程序兼容工控上位机,触摸屏,PLC。
触摸屏例子程序太难找,对初学者很不友好。触摸屏我是一边学一边做,本程序包含一般项目完整功能。主屏显示,IO状态,系统设置,趋势图记录,
报警记录,密码项目,快捷分组,宏指令。可做简易模板使用,只有UI设计不尽如意。抛砖引玉。触摸屏细节我会在工控区另开一贴详细说明
接线较简单可以使用串口转485模块,1-2元的模块很多。485模块A B 接威纶通触摸屏 com2的1,2孔
我非专业人士用到的知识都是大多来源与论坛,回馈论坛。
完整单片机代码在最后
部分代码:
#ifndef _modbus_
#define _modbus_
//发送使能DE 接受使能RE 可短接使用一条线,也可使用2线,
//双工模块可不接使能只使用VDD GND RXD TXD
//4810通讯电源主控通讯芯片接线
// 收发芯片为 ADM2483
// USART1_TXD PA9 Pin6 TXD
// USART1_RXD PA10 Pin3 RXD
// USART1_DE PA0 Pin5 DE
// USART1_RE PA2 Pin4 RE
#include "stm32f10x_conf.h"
#define RS485_DE_1 GPIO_SetBits (GPIOA, GPIO_Pin_0) //DE:驱动使能,高电平使能发送功能。
#define RS485_DE_0 GPIO_ResetBits(GPIOA, GPIO_Pin_0) //
#define RS485_RE_1 GPIO_SetBits (GPIOA, GPIO_Pin_2) //RE*:接收使能,低电平使能接收功能。
#define RS485_RE_0 GPIO_ResetBits(GPIOA, GPIO_Pin_2) //
#define RS485_RT_0 RS485_RE_0; RS485_DE_0;
#define RS485_RT_1 RS485_RE_1; RS485_DE_1;
typedef struct
{
u8 myadd;//本设备的地址
u8 rcbuf[256]; //MODBUS接收缓冲区
u16 timout;//MODbus的数据断续时间
-
通讯测试.png
(94.51 KB, 下载次数: 10)
-
历史.png
(49.82 KB, 下载次数: 7)
-
主屏.png
(54.73 KB, 下载次数: 9)
-
校正分项.png
(141.44 KB, 下载次数: 8)
-
状态.png
(53.14 KB, 下载次数: 8)
-
-
modbus485通讯触摸屏.7z
11.33 MB, 下载次数: 30, 下载积分: 黑币 -5
作者: donglw 时间: 2024-9-10 16:07
没有看到通讯协议的内容:例如帧头、帧尾、校验方式等信息。
作者: guobaox1981 时间: 2024-9-11 15:37
void Modbud_fun6() //6号功能码处理
{
u16 Regadd;
u16 val;
u16 i,crc,j;
i=0;
Regadd=modbus.rcbuf[2]*256+modbus.rcbuf[3]; //获取要修改的寄存器地址
val=modbus.rcbuf[4]*256+modbus.rcbuf[5]; //获取修改后的值
Reg[Regadd]=val; //修改本设备相应的寄存器
//以下为回应主机
modbus.Sendbuf[i++]=modbus.myadd;//添加本设备地址到发送缓冲区
modbus.Sendbuf[i++]=0x06; //添加功能码到发送缓冲区
modbus.Sendbuf[i++]=Regadd/256; //添加寄存器地址的高字节到发送缓冲区
modbus.Sendbuf[i++]=Regadd%256; //添加寄存器地址的低字节到发送缓冲区
modbus.Sendbuf[i++]=val/256; //添加修改后的值的高字节到发送缓冲区
modbus.Sendbuf[i++]=val%256; //添加修改后的值的低字节到发送缓冲区
crc=crc16(modbus.Sendbuf,i); //计算CRC校验码
modbus.Sendbuf[i++]=crc/256; //添加CRC校验码的高字节到发送缓冲区
modbus.Sendbuf[i++]=crc%256; //添加CRC校验码的低字节到发送缓冲区
RS485_RT_1; //设置RS485为发送模式
for(j=0;j<i;j++) //发送缓冲区中的所有数据
{
RS485_byte(modbus.Sendbuf[j]);
}
RS485_RT_0; //设置RS485为接收模式
}
Modbus协议中,CRC16校验用于检测通信数据的完整性。它通过对传输的数据进行循环冗余校验(CRC),生成一个16位的校验码,附加到数据的末尾,接收方根据相同算法计算CRC码,判断数据是否有误。
CRC校验方式说明:
1. CRC16多项式:采用的是0xA001,即Modbus协议中常用的CRC16-IBM算法,初始值为0xFFFF。
2. 查表法优化:代码使用了查表法来提高效率,通过auchCRCHi[]和auchCRCLo[]两个数组存储CRC的高位和低位预计算值。这样避免了逐位移位运算,减少了处理时间。
3. 计算过程:
初始化高位和低位CRC字节为0xFF。
遍历数据缓冲区的每一个字节,计算出当前CRC字节与当前数据字节异或的索引uIndex。
根据uIndex在auchCRCHi[]和auchCRCLo[]查找对应的高位和低位CRC值,更新uchCRCHi和uchCRCLo。
4. 结果组合:最终返回时,将高位字节uchCRCHi左移8位,与低位字节uchCRCLo合并,形成最终的16位CRC值。
这个方法有效地验证Modbus通信中的数据完整性,一旦接收方计算出的CRC值与附加的CRC码不一致,就说明数据传输过程中出现了错误。
在 Modbus 通信协议中,主机与设备之间通常使用 CRC16 校验 来确保通信数据的完整性。因此,主机与上面代码通信时,默认使用的校验方式也是 CRC16。
具体来说,Modbus 协议有两种主要的传输模式,每种模式的校验方式不同:
1. Modbus RTU 模式:
使用 CRC 校验:Modbus RTU(Remote Terminal Unit)是二进制通信格式,使用 CRC16 校验。如上代码所示,发送数据时,会计算数据的 CRC16 校验值,并将其附加在数据帧的末尾。接收方再通过相同的算法计算出 CRC 值,验证数据是否正确。
2. Modbus ASCII 模式:
使用 LRC 校验:在 Modbus ASCII 模式下,校验方式为 LRC(纵向冗余校验,Longitudinal Redundancy Check)。这是通过对数据帧中的每个字节进行异或运算,生成一个校验字节。
因此,如果通信采用 Modbus RTU 模式,则使用的是 CRC16 校验,这也是上述代码所实现的校验方式。如果是 Modbus ASCII 模式,则会使用 LRC 校验。
总结:
主机与上述代码进行通信时,通常使用的是 Modbus RTU 模式的 CRC16 校验。
触摸屏通讯设置的485通讯参数波特率,奇/偶/N效验,这些都是基本物理传输协议。 与程序中串口设置对应
/*USART初始化*/
USART_InitTypeDef USART_InitStructure; //定义结构体变量
USART_InitStructure.USART_BaudRate = 115200; //波特率
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; //硬件流控制,不需要
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx; //模式,发送模式和接收模式均选择
USART_InitStructure.USART_Parity = USART_Parity_No; //奇偶校验,不需要
USART_InitStructure.USART_StopBits = USART_StopBits_1; //停止位,选择1位
USART_InitStructure.USART_WordLength = USART_WordLength_8b; //字长,选择8位
USART_Init(USART1, &USART_InitStructure); //将结构体变量交给USART_Init,配置USART1
完成物理协议才是软件协议触摸屏选择的是 Modbus RTU 模式也就决定了数据格式,效验方式为CRC,具体数据协议为标准协议
按标准写就行了,具体通讯报文分析我提供的文档内都有
威纶通自由协议报文
地址 通讯
4x 15 01 03 00 0F 00 01 B4 09
数字元件 站号1、功能码03 读多个寄存器、 地址15 、 数量1、 效验码
5x 10 01 03 00 0A 00 01 A4 08
数字元件 站号1、功能码03 读多个寄存器、 地址10 、 数量1、 效验码
作者: lushui 时间: 2024-10-26 10:50
请问,威纶通的触摸屏,采用Modbus ,每个功能码代表着啥意思,你是怎么知道的,以及相应的寄存器地址是怎么分配的
欢迎光临 (http://www.51hei.com/bbs/) |
Powered by Discuz! X3.1 |