西门子S7comm协议解析 —— 利用Wireshark对报文逐字节进行解析详细解析S7comm所含功能码以及UserData功能(path1)
Db2k 人气:6又一次成为懒蛋了,标题就这么改了改又是一篇新文章。
网上也有很多S7comm协议的解析,但还是如同我上一篇一样我只是做报文的解析对于S7comm的原理并进行阐述。
有些地方有错误的地方尽请大家指出,共同进步。
好了,言归正题。我们开始吧。
我还是按照功能码的顺序进行介绍吧。
s7抓包分析
TPKT层和COTP层我也不多做介绍了,有兴趣的可以自己去了解。今天我们主要是解析S7comm这一层。
功能码附录:
0x00 CPU services CPU服务
0xf0 Setup communication 建立通信
0x04 Read Var 读取值
0x05 Write Var 写入值
0x1a Request download 请求下载
0x1b Download block 下载块
0x1c Download ended 下载结束
0x1d Start upload 开始上传
0x1e Upload 上传
0x1f End upload 上传结束
0x28 PI-Service 程序调用服务
0x29 PLC Stop 关闭PLC
1、0xF0建立通信
发包
我们来先看Header头部分。
Byte[0] 32 为协议ID 一般指定为0x32
Byte[1] 01 为 PDU类型 一般有0x01 Job 主设备发起请求 0x02 Ack 确认响应 0x03 Ack_data 确认数据响应一般作为确认0x01的请求 0x07 USERDATA 协议的扩展,参数字段包含请求/响应ID
Byte[2]Byte[3] 00 00冗余数据,通常为0×0000
Byte[4]Byte[5] 3e 02协议数据单元的参考、通过请求事件增加
Byte[6]Byte[7] 00 08参数的总长度也就是parameter的长度
Byte[8]Byte[9] 00 00数据的长度、也就是data部分数据的长度如果无即为0
继续看Parmeter部分。
根据上面的length得知,我们的Parameter部分应该是8个位,数一数看看是不是8位
Byte[0] f0 为PDU的类型也就是功能码
Byte[1] 00 冗余数据,通常为0×0000
Byte[2] Byte[3] 发送连接请求
Byte[4] Byte[5] 发送通信请求
Byte[6] Byte[7] 协商的PDU长度
回包
红框内跟发包是一样的,就不再描述了。
从Error Class开始。
Byte[10] 00 为错误类型 、错误类型也有很多种、以下是错误类型附录。
0x00 No error 没有错误
0x81 Application relationship 应用关系
0x82 Object definition 对象定义
0x83 No resources available 没有可用资源
0x84 Error on service processing 服务处理中错误
0x85 Error on supplies 请求错误
0x87 Access error 访问错误
Byte[11] 00 为错误码 文章最后会附录一下全部错误码(很长不贴在这里了,搜索 附录一)
这里可以理解为 错误类型规定错误的大体方向而错误码规定错误的具体事件。
接下来我们看Parameter这一部分
可以看出跟发包是完全一样的,还是那句话百变不离其宗,协议嘛逃脱不了一发一收对吧。
Byte[0] f0 为PDU的类型也就是功能码
Byte[1] 00 冗余数据,通常为0×0000
Byte[2] Byte[3] 确认连接请求
Byte[4] Byte[5] 确认通信请求
Byte[6] Byte[7] 协商的PDU长度
2、0x04 读取数据
发包
Header头部与之前都一样的不再描述了
我们直接看Parameter部分吧。
Byte[0] 04 功能码
Byte[1] 01 代表了Item的个数 为1 即为 一个
再继续往下扒。
Item部分
Byte[0] 12 结构标识通常都为0x12,代表变量规范
Byte[1] 0a 长度规范、自此往后的长度
Byte[2] 10 IDS的地址规范的格式类型常见值如下表
0x10 S7ANY Address data S7-Any pointer-like DB1.DBX10.2
0x13 PBC-R_ID R_ID for PBC
0x15 ALARM_LOCKFREE Alarm lock/free dataset
0x16 ALARM_IND Alarm indication dataset
0x19 ALARM_ACK Alarm acknowledge message dataset
0x1a ALARM_QUERYREQ Alarm query request dataset
0x1c NOTIFY_IND Notify indication dataset
0xa2 DRIVEESANY seen on Drive ES Starter with routing over S7
0xb2 1200SYM Symbolic address mode of S7-1200
0xb0 DBREAD Kind of DB block read, seen only at an S7-400
0x82 NCK Sinumerik NCK HMI access
Byte[3] 02 为数据传输的大小、常见值如下表
0 NULL
3 BIT bit access, len is in bits
4 BYTE/WORD/DWORD byte/wordhttps://img.qb5200.com/download-x/dword access, len is in bits
5 INTEGER integer access, len is in bits
6 DINTEGER integer access, len is in bytes
7 REAL real access, len is in bytes
9 OCTET STRING octet string, len is in bytes
Byte[4]Byte[5] 00 01 即数据的长度
Byte[6]byte[7] 00 01 即 DB 编号,如果访问的不是DB区域,此处为0x0000
Byte[8] 84 即数据的区域常用的如下表
Byte[9] Byte[10]Byte[11] 要读取数据的地址
图示整体标注一下
回包
Header部分
除了红框内的其他都与发包一致
Error class 即错误类型
Error code 即具体错误码这两个在上面已经介绍了都有哪些错误类型,没有错误即0x00
Parameter部分
Byte[0] 04 功能码 Byte[1] 01 代表一个Item
Data部分
Byte[0] FF 为返回码 返回码常用值如下表
0x00 Reserved 未定义,预留
0x01 Hardware error 硬件错误
0x03 Accessing the object not allowed 对象不允许访问
0x05 Invalid address 无效地址,所需的地址超出此PLC的极限
0x06 Data type not supported 数据类型不支持
0x07 Data type inconsistent 日期类型不一致
0x0a Object does not exist 对象不存在
0xff Success 成功
Byte[1] 04 为数据传输大小 data数据传输大小值如下表
0 NULL
3 BIT bit access, len is in bits
4 BYTE/WORD/DWORD byte/wordhttps://img.qb5200.com/download-x/dword access, len is in bits
5 INTEGER integer access, len is in bits
6 DINTEGER integer access, len is in bytes
7 REAL real access, len is in bytes
9 OCTET STRING octet string, len is in bytes
Byte[2]Byte[3] 为data数据的长度
Byte[4] 即数据
有时候会有填充数据即在byte[4]之后、如果数据长度不满足length的话会填充0x00
列如 byte[2]byte[3] 的长度值为3 就会在byte[4]后填充两个0x00
还是整体在图示一遍吧
好了,这个功能算是啃完了,其他的功能也大致都一样,所以呢剩下的时候我可能会比较懒了哈哈。
3、0x05 写入数据
这就很好理解了吧,有读必有写。那写我们去推断一下,是不是在发包的时候比读数据会多一个Data段作为写入的值呢。答案是肯定的!
发包
Header 都与读取值一样的就不在说了
Parameter也一样图示一次吧
叮叮叮,Data段来了
Byte[0] 00 返回码未定义就为00
Byte[1] 04 数据传输的大小
Byte[2]Byte[3] 数据的长度
Byte[4] 数据
是不是感觉这些都差不多一样,
计算机跟人类也是一样的。
我对你说“你好帅啊” 你是不是也会回我一句“你也好帅”,假设说你回了一句“我很帅,你很丑”
这是不是不符合常理了,有可能你还要挨骂对吧。
那计算机也是啊,服务端发送数值,客户端不但不接受还骂服务端一句,那是不是服务端这边要报错呢。
可能例子不太恰当,意思到了就阔仪了。
言归正传,别爱我,没结果。
回包
引用上面我举的例子,那完全可以推断出来回包会会什么对吧。
发包写入了数据,那我回包是不是要回复写入成功或者失败呢。
Header部分和parameter部分都一样还是懒了些就不在描述了。
来看Data部分吧
Byte[0] FF 即为返回码
上面介绍有返回码的类型 整段的意思就是向0x000000地址写入成功
还有好多个功能码没有写,我会放到下一篇文章里。
原因:懒了懒了懒了
未完待续....
加载全部内容