📄 modbus.lst
字号:
C51 COMPILER V8.01 MODBUS 03/26/2007 20:26:46 PAGE 1
C51 COMPILER V8.01, COMPILATION OF MODULE MODBUS
OBJECT MODULE PLACED IN modbus.OBJ
COMPILER INVOKED BY: C:\Program Files\Keil\C51\BIN\C51.EXE modbus.c BROWSE DEBUG OBJECTEXTEND
line level source
1 #include "reg52.h"
2 #include<modbus.h>
3 //类型定义
4 typedef unsigned char uchar;
5 typedef unsigned int uint;
6 typedef unsigned long ulong;
7 sbit E485=P3^2; //max485发送允许
8 uchar *pushMsg; /*要进行CRC校验的消息*/
9 uchar idata Rxbuf_com[16]=0; //接收数据缓冲区
10 uchar idata Rxbuf[16]=0; //接收命令数据缓冲区
11 uchar idata MBFrame_Len=0; //待处理命令消息字节长度
12 extern uchar idata MBFrame_OK; //接收到一个命令结束,等待处理时为1;否则为0.
13 uchar idata Txbuf[16]=0; //发送数据缓冲区
14 uchar idata Send_Count=1; //发送数据长度
15 uchar idata Receive_Count=0; //接收数据长度
16 uint idata crc_temp; //crc校验结果
17 uchar idata MBtimerT15=0;
18 uchar MBSlaveAdrress = 0x02;
19
20 extern int Parameter_Table[10];
21 #define Parameter_Num 10
22
23 unsigned int usMBCRC16( unsigned char * pucFrame, unsigned char usLen );//modbus crc 函数
24
25
26
27 extern void MBSerialInit(void); //串口配置函数
28
29 extern void ModBusProtocolProcess(void); //接收到的消息命令处理函数
30 void MBSerialSendTxbuf(void); //数据上传函数
31 void ReadHoldingRegister(void);//03读取保持寄存器命令处理
32 void WriteSingleHoldingRegister(void);//写单个保持寄存器处理
33 void WriteMultiHoldingRegister(void);//写多个保持寄存器处理
34 void Cmd08loopbackTesting(void);
35
36
37 /*===========================*/
38 /*=====下位机发送数据函数====*/
39 /*===========================*/
40 void MBSerialSendTxbuf(void)
41 {
42 1 uchar i;
43 1 uint k;
44 1 E485=1;
45 1 pushMsg=&Txbuf[0];
46 1 crc_temp=usMBCRC16(pushMsg,Send_Count);
47 1 k=crc_temp;
48 1 Txbuf[Send_Count]=(uchar)k; //+CRC_Li
49 1 Send_Count++;
50 1 Txbuf[Send_Count]=(uchar)(crc_temp>>8); //+CRC_Hi
51 1 ES=0;REN=0;
52 1 for(i=0;i<=Send_Count;i++)
53 1 {
54 2 SBUF=Txbuf[i];while(!TI);TI=0;
55 2 }
C51 COMPILER V8.01 MODBUS 03/26/2007 20:26:46 PAGE 2
56 1 ES=1;REN=1;
57 1 Send_Count=Send_Count-2; //恢复
58 1 E485=0;//恢复
59 1 }
60
61 void ModBusProtocolProcess(void)
62 {
63 1
64 1 pushMsg=&Rxbuf[0];
65 1 crc_temp=usMBCRC16(pushMsg,MBFrame_Len);
66 1 if((Rxbuf[0]==MBSlaveAdrress)&&(crc_temp==0))//是否发给本机,并CRC正确?
67 1 {
68 2
69 2 switch (Rxbuf[1])
70 2 {
71 3 case 0x03: //读取保持寄存器
72 3 {
73 4 ReadHoldingRegister();
74 4 break;
75 4 }//03命令处理结束
76 3 case 0x06: //写单个保持寄存器
77 3 {
78 4 WriteSingleHoldingRegister();
79 4 break;
80 4 }//06命令处理结束
81 3 case 0x08: //回路测试
82 3 {
83 4 Cmd08loopbackTesting();
84 4 break;
85 4 }//08命令处理结束
86 3 case 0x10: //写多个保持寄存器
87 3 {
88 4 WriteMultiHoldingRegister();
89 4 break;
90 4 }//10命令处理结束
91 3 default:
92 3 {
93 4 Txbuf[0]=MBSlaveAdrress; //取地址
94 4 Txbuf[1]=0xff; //命令号
95 4 Send_Count=2; //发送数据长度
96 4 MBSerialSendTxbuf();
97 4 break;
98 4 }
99 3 }// Swith Rxbuf[1] 结束
100 2 }//if 判断结束
101 1 else
102 1 {
103 2 //CRC较验出错或者不是发到本地址不做任何响应
104 2 }
105 1 MBFrame_OK=0; //消息处理完
106 1 }
107
108
109 void ReadHoldingRegister(void) //03命令处理
110 {
111 1 uint StratingAddress;
112 1 uint Numbers;
113 1 int temp;
114 1 uchar i,j,BytesCount;
115 1 StratingAddress=Rxbuf[2];
116 1 StratingAddress=(StratingAddress<<8)|Rxbuf[3];//取开始地址
117 1 Numbers=Rxbuf[4];
C51 COMPILER V8.01 MODBUS 03/26/2007 20:26:46 PAGE 3
118 1 Numbers=(Numbers<<8)|(Rxbuf[5]); //读取的数量
119 1 BytesCount=(uchar)(Numbers*2);
120 1 if((Numbers + StratingAddress)<=Parameter_Num)
121 1 {
122 2 Txbuf[0]=MBSlaveAdrress; //取地址
123 2 Txbuf[1]=0x03; //命令号
124 2 Txbuf[2]=BytesCount;////返回字节数
125 2 j=0;
126 2 for(i=0;i<BytesCount;)
127 2 {
128 3 temp = Parameter_Table[(uchar)StratingAddress+j];
129 3 Txbuf[3+i]=(uchar)(temp>>8); //返回测试数据高字节
130 3 i++;
131 3 Txbuf[3+i]=(uchar)temp;//返回测试数据低字节
132 3 i++;
133 3 j++;
134 3 }
135 2 Send_Count=(BytesCount+3); //发送数据长度(01+ 03 + BytesCount + 返回数据)
136 2 MBSerialSendTxbuf();
137 2 }
138 1 else
139 1 {
140 2 //返回错误信息
141 2 Txbuf[0]=MBSlaveAdrress; //取地址
142 2 Txbuf[1]=0x83; //命令号&0x80
143 2 Txbuf[2]=Rxbuf[2];
144 2 Txbuf[3]=Rxbuf[3];
145 2 Txbuf[4]=Rxbuf[5];
146 2 Txbuf[5]=Rxbuf[5];
147 2 Send_Count=6; //发送数据长度
148 2 MBSerialSendTxbuf();
149 2 }
150 1 }
151
152 void WriteSingleHoldingRegister(void) //06命令处理
153 {
154 1 uint StratingAddress;
155 1 uint Numbers;
156 1 int temp;
157 1 StratingAddress=Rxbuf[2];
158 1 StratingAddress=(StratingAddress<<8)|Rxbuf[3];//取开始地址
159 1 Numbers=1;//写寄存器的数量
160 1 if((Numbers + StratingAddress)<=Parameter_Num)
161 1 {
162 2 Txbuf[0]=MBSlaveAdrress; //取地址
163 2 Txbuf[1]=0x06; //命令号
164 2 Txbuf[2]=Rxbuf[2];
165 2 Txbuf[3]=Rxbuf[3];
166 2 Txbuf[4]=Rxbuf[4];
167 2 Txbuf[5]=Rxbuf[5];
168 2 Send_Count=6; //发送数据长度
169 2 temp=Rxbuf[4];//测试数据高位
170 2 temp=(temp<<8)|Rxbuf[5];//测试数据高低位合并
171 2 Parameter_Table[(uchar)StratingAddress]=temp;
172 2 MBSerialSendTxbuf();
173 2 }
174 1 else
175 1 {
176 2 //返回错误信息
177 2 Txbuf[0]=MBSlaveAdrress; //取地址
178 2 Txbuf[1]=0x86; //命令号&0x80
179 2 Txbuf[2]=Rxbuf[2];
C51 COMPILER V8.01 MODBUS 03/26/2007 20:26:46 PAGE 4
180 2 Txbuf[3]=Rxbuf[3];
181 2 Txbuf[4]=Rxbuf[4];
182 2 Txbuf[5]=Rxbuf[5];
183 2 Send_Count=6; //发送数据长度
184 2 MBSerialSendTxbuf();
185 2 }
186 1 }
187 void Cmd08loopbackTesting(void)
188 {
189 1 Txbuf[0]=MBSlaveAdrress; //取地址
190 1 Txbuf[1]=0x08; //命令号
191 1 Txbuf[2]=Rxbuf[2];
192 1 Txbuf[3]=Rxbuf[3];
193 1 Txbuf[4]=Rxbuf[4];
194 1 Txbuf[5]=Rxbuf[5];
195 1 Send_Count=6; //发送数据长度
196 1 MBSerialSendTxbuf();
197 1
198 1
199 1 }
200 void WriteMultiHoldingRegister(void) //10命令处理
201 {
202 1 uint StratingAddress;
203 1 uint Numbers;
204 1 int temp;
205 1 uchar i,BytesCount;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -