故事作者:空果仁

最近创作

看看TA的故事

数据块字节排序的测试

已锁定

空果仁

官方工程师 西门子1847工业学习平台

  • 帖子

    210
  • 精华

    47
  • 被关注

    311

论坛等级:侠圣

注册时间:2011-07-11

普通 普通 如何晋级?

数据块字节排序的测试

6134

20

2022-05-23 09:55:15

star star star star star

S7-1500数据块的访问方式分为标准和优化两种,标准的数据块中,变量间可能存在间隔,如图1所示。

优化的数据块中大数据类型的变量位于块的开始处,实现数据结构的合理优化,如图2所示。

这些图是从胶片中剪辑的,说明优化的数据块中变量间是没有间隔的。

这几天在琢磨序列化指令,想着这个指令在什么地方使用,也做了一下测试,发现优化的数据块中变量也是有间隔的,这也推翻留存大脑中原有的想法。

在测试中,首先创建了一个PLC数据类型“Data_Type”,PLC类型中包含3个BOOL类型和3个DINT类型,结构如图3所示。

然后创建了一个数据块,在数据块中创建了一个变量,类型就是“Data_Type”,按照图2的说明,3个DINT变量应该排列在最前面,然后是3个BOOL变量,优化数据块每一个BOOL变量占用一个字节,那么数据类型为“Data_Type”的变量应该占用15个字节。

数据块实际的容量增加了多少呢?在创建数据块后先编译,除去预留的100字节后,一个空的数据块长度是68个字节,如图4所示。

然后在数据块中添加一个“Data_Type”类型变量后再编译,数据块长度变为84,增加了16个字节,说明变量间有一个字节的间隔。为了验证优化数据块中变量的排列次序,在新的数据块中分别增加1个BOOL变量、1个BOOL变量+1个DINT变量、1个BOOL变量+1个DINT变量+1个BOOL变量,最后到间隔排列3个BOOL变量和3个DINT变量进行测试,测试的结果为:

按照这样的规律,如果数据块中第一个变量是BOOL,则占用2个字节(偶数开始),如果后面排列的是DWORD变量,则占用8个字节;同样第一个是DWORD变量,后面是BOOL变量也要占用8个字节。那么为什么1个BOOL变量+1个DINT变量+1个BOOL变量还是占用8个字节呢?因为有间隔就插进去了,这样就可以解释“Data_Type”类型变量为什么占用16个字节空间了,如图5所示

也有可能是BDFACE排列方式,如图6所示。

注:

图5和6排列方式都是猜测的。

那么大家可能会问测试字节排列干什么?接下来就是测试的原因了。将包含“Data_Type”类型变量的数据块转换为标准数据块,空数据块也是占用68个字节空间。编译后再看看占用地址空间的大小,如图7所示。

数据类型相同的变量在标准数据块中占用了18个字节空间。这样问题就来了,两个变量占用的字节长度都不相同,如果将存储在优化数据块变量中的数据MOVE到标准数据块的变量中是不是会发生错位的现象?做了一个测试,发现使用MOVE指令没有问题,这也说明了两个PLC之间使用通信方式传递两个变量的数据也没有问题(一个是优化一个是标准)。这里感觉在使用MOVE指令前,数据经过了变化,否则就没法解释了,其实这个转换确实由系统完成了,是按照被调用块的格式进行转换,例如标准访问的变量在优化块中使用,先将数据复制到优化块的本地数据区,然后再将该数据以正确格式(优化访问)进行转换。

同一个CPU中或者相同类型的CPU之间的通信,数据的转换方式是相同的,所以操作不会出现问题。但是不同操作系统间的通信,例如PLC与PC或者不同品牌PLC间的通信可能就会出现问题,这时需要将原数据进行序列化后再发送吗?个人认为还是需要了解一下序列化和不使用序列化有什么不一样,否则发送了一个“Data_Type”类型变量,接收方会不知道对应关系。

标准数据块中变量的排序是固定的,可以根据字节的偏移地址判断起始地址,优化数据块中的变量排序不固定(无论是图5还是图6都是不固定的),也不使用绝对地址,所以无法判断。使用序列化指令将变量传送到一个元素为BYTE的数组后可以判断各个变量的排列顺序,程序及测试结果如图8所示。

16个字节长度的“Data_Type”类型变量(优化访问)序列化后变成了18个字节,与标准访问的变量长度相等(标准访问的变量序列化后与原排列顺序相同),对应关系也是一样。然后又在单一变量基础上嵌套多个结构体变量进行测试,发现两种访问方式变量的长度还是相同的,使用序列化可以确定变量的排列顺序。

如果不进行序列化而直接发送优化访问的“Data_Type”类型变量(TCP连接),是按照16个字节还是18个字节发送呢?使用抓包软件对发送报文进行了解析,居然是18个字节,与经过序列化后是一样(不知道这样的排列顺序是不是一个标准,如果通信双方发送和接收的数据排列顺序不一样,还是需要调整的),如图8所示。

测试了多种组合,好像发送前都已经序列化了,所以说可以不使用序列化直接发送了。

这就是一开始说的,不知道该指令在哪里应用。从自己的体会来说,认为主要有两点需要序列化:

1. PLC中的序列化指令与高级语言的序列化功能部分是近似的,其中一点就是把对象转化为可传输的字节序列。使用方法相同,有助于习惯高级语言开发的工程师熟悉PLC的编程环境。

2. 在S7-300/400 PLC中,通信的数据区是一个以字节为元素的数组,例如P#DB1.DBX0.0 BYTE 100,所以不需要序列化指令。在S7-1500 PLC 中变量使用的是符号地址,推荐的是对象化的编程方式,通常使用PLC数据类型或者结构体生成的变量作为对象的属性,这些属性数据大多数也是需要通信的数据,如果数据不连续或者不在相同的数据块中,要么建立多个连接(还得看通信伙伴是否可行),要么对数据进行整合,使用序列化和反序列化可以解决这样的问题,将数据转存到一个数据缓存区,这样又方便又保持原有的数据结构,这里序列化和反序列化的功能起到了转存的功能(参考图9),要不怎么放在“移动操作”指令子集中呢。

如果还有其它建议欢迎分享!


数据块字节排序的测试 已锁定
编辑推荐: 关闭

请填写推广理由:

本版热门话题

崔工谈博途与PLC

共有101条技术帖

相关推荐

热门标签

相关帖子推荐

guzhang

恭喜,你发布的帖子

评为精华帖!

快扫描右侧二维码晒一晒吧!

再发帖或跟帖交流2条,就能晋升VIP啦!开启更多专属权限!

top
您收到0封站内信:
×
×
信息提示
很抱歉!您所访问的页面不存在,或网址发生了变化,请稍后再试。