4_SOMEIP 协议处理
SOME/IP 协议处理
本章节描述了远程过程调用(RPC)、事件通知和错误处理。
传输协议绑定
为了传输SOME/IP消息,可以使用不同的传输协议。SOME/IP目前支持UDP和TCP。
[PRS_SOMEIP_00138] 如果服务器运行同一服务的不同实例,属于实例的消息应通过服务器端传输协议端口映射到服务实例。
[PRS_SOMEIP_00535] 所有传输协议绑定应支持在传输层PDU(udp pkg or tcp pkg)中传输多个SOME/IP消息。
[PRS_SOMEIP_00142] 接收SOME/IP消息的实现端应该能够接收由UDP或TCP传输的未对齐的SOME/IP消息。
原因:当在UDP或TCP中传输多个SOME/IP有效负载时,如果每个有效负载的长度是对齐大小的倍数(例如32位),有效负载的对齐才能得到保证。
[PRS_SOMEIP_00140] Header格式允许在单个包中传输多个SOME/IP消息。SOME/IP实现应该通过SOME/IP长度字段来识别SOME/IP消息的结束。SOME/IP根据数据包长度字段来确定数据包中是否有额外的SOME/IP消息。这将适用于UDP和TCP传输。
[PRS_SOMEIP_00141] 每个SOME/IP有效负载应该有自己的SOME/IP报头。
[PRS_SOMEIP_00940] 单服务实例可以使用以下设置配置:(为通信,所有方法、事件和通知):
- 最多一个TCP 连接
- 最多一个UDP 单播连接
- 对多一个UDP 组播连接
UDP 绑定
[PRS_SOMEIP_00139] SOME/IP的UDP绑定需要通过UDP报文传输SOME/IP消息来实现。
[PRS_SOMEIP_00137] SOME/IP协议不限制UPD分片的使用。
[PRS_SOMEIP_00943] 服务实例被配置为使用UDP单播通信时,客户端和服务器应该使用单个UDP单播连接所有方法、事件和通知。
[PRS_SOMEIP_00942] 服务实例被配置为使用UDP组播通信时,客户端和服务器应该使用单个UDP组播连接的所有事件和通知。
TCP 绑定
SOME/IP的TCP绑定严重依赖于UDP绑定。与UDP绑定相反,TCP绑定允许更大的SOME/IP消息,并使用了TCP的健壮性特征(应对丢失、重新排序、复制等)。
为了降低延迟和反应时间,应该关闭Nagle的算法(TCP_NODELAY)。
[PRS_SOMEIP_00706] 当TCP连接丢失时,未完成的请求将作为超时处理。
[PRS_SOMEIP_00707] 当配置为使用TCP通信时,客户端和服务器应该使用单个TCP连接来处理服务实例的所有方法、事件和通知。
[PRS_SOMEIP_00708] 当传送第一个方法调用或客户端尝试接收第一个通知时,TCP连接将由客户端打开。当TCP连接失败时,客户端负责重新建立连接。
[PRS_SOMEIP_00709] 当不再需要TCP连接时,TCP连接将被客户端关闭。
[PRS_SOMEIP_00710] 当所有使用TCP连接的服务不再可用(停止或超时),TCP连接将被客户端关闭。
[PRS_SOMEIP_00711] 服务器在停止所有服务时,不应停止TCP连接,给客户端足够的时间来处理控制数据以关闭TCP连接本身。
合理性:在客户端意识到TCP不再需要之前,服务端关闭了TCP连接,客户端将尝试重新建立TCP连接。
允许使用魔术cookie重新同步到TCP流。
[PRS_SOMEIP_00154] 为了允许测试工具识别SOME/IP TCP传输的消息边界,SOME/IP魔术Cookie消息可以定期插入SOME/IP消息。
[PRS_SOMEIP_00160] Magic Cookie信息的布局应包括以下字段:
- 从客户端到服务器的通信:
- Message ID (Service ID/Method ID): 0xFFFF 0000
- Length: 0x0000 0008
- Request ID (Client ID/Session ID): 0xDEAD BEEF
- Protocol Version: 0x01
- Interface Version: 0x01
- Message Type: 0x01
- Return Code: 0x00
- 从服务器到客户端的通信:
- Message ID (Service ID/Method ID): 0xFFFF 8000
- Length: 0x0000 0008
- Request ID (Client ID/Session ID): 0xDEAD BEEF
- Protocol Version: 0x01
- Interface Version: 0x01
- Message Type: 0x02
- Return Code: 0x00
多实例服务
[PRS_SOMEIP_00162] 同一个服务的服务实例通过不同的实例ID进行标识。应该支持多个服务实例驻留在不同的ECU上,以及一个或多个服务的多个服务实例驻留在一个ECU上。
[PRS_SOMEIP_00163] 不同服务的多个服务实例应该能够共享使用传输层协议的相同端口号,同一个ECU上的同一个服务的多个实例应该使用不同的端口。
原因:虽然实例ID用于服务发现,但它们不包含在SOME/IP报头中。
通过将服务ID与套接字(即IP-address、传输协议(UDP/TCP)和端口号)组合,可以识别一个服务实例。建议UDP和TCP使用相同的端口号,如果一个服务实例使用UDP端口x,只有该服务的这个实例,应该为其服务使用完全相同的TCP端口x,而同一服务的另一个实例则不必如此。
传输大的UDP SOME/IP消息(SOME/IP-TP)
SOME/IP的UDP绑定只能传输一些直接适合IP包的消息;如果较大的SOME/IP消息需要通过UDP传输(例如32kb),SOME/IP传输协议(SOME/IP- tp)应使用,SOME/IP消息太大,不能直接通过UDP绑定传输的称为“原始”SOME/IP消息, 在SOME/IP-tp消息中传输原始SOME/IP消息有效载荷的“片段”称为“段”。
只有当需要传输非常大的数据块(> 1400字节),并且在存在错误的情况下没有硬延迟要求时,才使用TCP。
[PRS_SOMEIP_00720] 使用SOME/IP- tp的SOME/IP消息将激活会话处理(会话ID对于原始消息必须是唯一的)。
[PRS_SOMEIP_00721] 所有的SOME/IP-TP段应该携带原始消息的会话ID; 因此,它们具有相同的会话ID。
[PRS_SOMEIP_00722] SOME/IP-TP段的消息类型的TP-Flag必须设置为1。
[PRS_SOMEIP_00723] SOME/IP-TP段应该有一个TP头在SOME/IP报头(即在SOME/IP有效载荷之前)具有以下结构(从高到低的比特):
- Offset [28 bits]
- Reserved Flag [3 bit]
- More Segments Flag [1 bit]
图1:SOME-IP-TP-Header
[PRS_SOMEIP_00931] SOME/IP-TP报头应该按照网络字节顺序进行编码(大端字节)。
[PRS_SOMEIP_00724] 偏移字段应该传输uint32的上28位。较低的4位总是被解释为0。NOTE:注意:这意味着偏移字段只能传输16个字节的偏移值。
[PRS_SOMEIP_00725] TP报头的偏移字段应该设置为原始消息中被传输段的偏移量(以字节为单位)。
[PRS_SOMEIP_00726] 保留标志将被发送方设置为0,接收方将忽略(不检查)保留标志。
[PRS_SOMEIP_00727] 对于除最后一个片段外的所有片段,将More Segments标志设置为1。对于最后一段,它将被设置为0。
[PRS_SOMEIP_00728] 前面指定的SOME/IP长度字段应使用。这意味着它覆盖了SOME/IP头的前8个字节以及之后的所有字节。
NOTE:这意味着对于传输段的SOME/IP-TP消息,SOME/IP长度包括SOME/IP报头的8个字节、TP报头的4个字节和段本身。
[PRS_SOMEIP_00729] 一个段的长度必须反映基于偏移字段的下一个段的对齐。因此,除最后一个段外的所有段的长度都应该是16字节的倍数。
[PRS_SOMEIP_00730] 由于基于udp的SOME/IP消息的有效负载被限制为1400字节,正确对齐的段的最大长度是1392字节。
[PRS_SOMEIP_00731] SOME/IP-TP消息应该使用相同的消息ID(即:服务ID和方法ID)、请求ID(即客户端ID和会话ID)、协议版本、接口版本以及作为原始消息的返回代码。
注意:如上所述,长度、消息类型和有效负载由SOME/IP-TP调整。
示例:这个示例描述了如何传输5880字节有效负载的原始SOME/IP消息。这个原始SOME/IP消息的长度字段被设置为8 + 5880字节。
图2:示例:原始SOME/IP消息头
这个原始的SOME/IP消息现在将被分割成5个连续的SOME/IP段。在本例中,这些段的每个有效负载最多携带1392字节。
对于这些段,SOME/IP TP模块添加了额外的TP字段(标记为红色)。
SOME/IP的Length字段携带了SOME/IP段的总长度,包括请求ID、协议版本、接口版本、消息类型和返回码的8个字节。由于添加了TP字段(4个字节),这个长度信息被额外的4个SOME/IP TP字节扩展。下图提供了每个SOME/IP段的相关SOME/IP报头设置的概述:
图3:示例:分段TP报文头
请注意Offset字段中的值是以16字节为单位给出的,也就是说:Offset值87对应1392字节的有效负载。
完整的SOME/IP段消息的SOME/IP头如下图所示:前4段包含1392个有效负载字节,每个字节包含“more segments flag”设置为1。
图4:示例:Some/IP消息分段
最后一个片段(即#5)包含原始5880字节有效负载的剩余312个有效负载字节。最后一个段用“More Segments flag”标记为“0”。
发送方特定行为
[PRS_SOMEIP_00732] 发送方应仅对配置为分段的消息进行分段。
[PRS_SOMEIP_00733] 发送方应按升序发送片段
[PRS_SOMEIP_00734] 发送方应以一种方式分段,使所有具有较多分段标志设置为1的分段具有相同的大小
[PRS_SOMEIP_00735] 发送方应在本规范规定的限制范围内尽量扩大线段的大小
[PRS_SOMEIP_00736] 发送方不得发送重叠、重复的线段
接收方特定行为
[PRS_SOMEIP_00738] 接收端需要根据配置的Message-ID、Protocol-Version、Interface-Version和Message type(w/o TP flag)进行报文段进行重组
[PRS_SOMEIP_00740] 支持对来自不同客户端(不同IP port or client ID)、具有相同消息ID的多条并行消息进行重组,这应该由配置控制,并确定“重组缓冲区”的数量。
[PRS_SOMEIP_00741] 会话ID用于检测下一个要重新组装的原始消息
[PRS_SOMEIP_00742] 如果接收到一个具有不同Session-ID的新段,接收端将开始一个新的重组(并可能丢弃没有成功重组的旧段)
[PRS_SOMEIP_00743] 接收方应该只重新组装到其配置的缓冲区大小,并跳过消息的其余部分
[PRS_SOMEIP_00744] 只有正确地重新组装的、大小不超过配置大小的消息才能传递给应用程序
NOTE:这意味着实现必须确保消息的所有字节必须是正确接收并重新组装。计数非重叠、非重复的字节并将其与长度进行比较可能是有效的检查
[PRS_SOMEIP_00745] 用于为重新组装的消息重新组装应使用的最后一个段的返回代码
[PRS_SOMEIP_00746] 将SOME/IP TP段重组为大的未分段消息时,需要调整消息类型,将TP标志位重置为0
[PRS_SOMEIP_00747] 接收方应当支持按照升序、降序接收的片段进行重组
[PRS_SOMEIP_00749] 在组装过程中检测到一个缺失的段SOME/IP消息,当前装配过程应取消
NOTE:这意味着不支持重新排序
[PRS_SOMEIP_00750] 不支持交叉使用相同缓冲区的不同分段消息(例如,只有会话id和有效负载不同)。
NOTE:这阻止相同的事件(相同的消息id、ip地址、端口号和传输协议)在某些段重新排序时以错误的顺序到达。
[PRS_SOMEIP_00751] 重新排序完全不同的原始消息的片段(例如消息ID不同)不需要担心,因为这些片段将进入不同的缓冲区。
[PRS_SOMEIP_00752] 接收端应基于上一个接收的段,通过覆盖正确地重新组装重叠和重复的段
[PRS_SOMEIP_00753] 如果重叠或重复的片段改变了缓冲区中已经写入的字节,如果这个特性可以通过配置关闭,接收端可以取消重组
[PRS_SOMEIP_00754] 接收方应能优雅地发现和处理明显的错误。例如,如果MS=1的段的长度不是16的倍数,则取消重新组装。
NOTE:这意味着接收代码应该防止缓冲区溢出或其他故障
Request/Response 通信
最常见的通信模式之一是请求/响应模式。一个通信伙伴(客户机)发送请求消息,该消息由另一个通信伙伴(服务器)响应。
[PRS_SOMEIP_00920] 对于SOME/IP请求消息,客户端必须做以下有效载荷和头:
- 构建有效载荷
- 根据客户端希望调用的方法设置消息ID
- 将Length字段设置为8字节(用于Length字段后的SOME/IP头部分)+序列化有效负载的长度
- 可选择设置请求ID为一个唯一的号码(仅对客户端是唯一的)
- 设置协议版本
- 根据接口定义配置接口版本
- 将消息类型设置为REQUEST(i.e. 0x00);
- 将返回代码设置为 0x00
[PRS_SOMEIP_00921]为了构造请求消息的有效载荷,方法的所有输入或inout参数应该按照方法签名中参数的顺序进行序列化。
[PRS_SOMEIP_00922]服务器基于客户端的请求头构建响应头,再做其他工作:
- 构建有效载荷
- 从相应的请求中接管消息ID
- 将长度设置为8字节+新的有效负载大小
- 从相应的请求中接管请求ID
- 将消息类型设置为RESPONSE(即0x80)或ERROR(即0x81)
- 将“返回码”设置为被调用方法的返回码,或在出现错误消息时设置为有效的错误码。
[PRS_SOMEIP_00923]为了构造响应消息的有效载荷,方法的所有输出或inout参数必须按照方法签名中参数的顺序进行序列化。
[PRS_SOMEIP_00927]在接收到相应的请求消息之前,服务器不得对具有特定请求ID的请求发送响应消息。
[PRS_SOMEIP_00928]当相应的请求消息尚未完全发送时,客户端应该忽略接收带有特定请求ID的响应消息
fire/forget 通信
没有响应消息的请求称为“fire&forget”。
[PRS_SOMEIP_00924] 对于SOME/IP request-no-return消息,客户端必须对载荷和头部做以下操作:
- 构建有效载荷
- 根据客户端希望调用的方法设置消息ID
- 将Length字段设置为8字节(用于Length字段后的SOME/IP头部分)+序列化有效负载的长度
- 可选择设置请求ID为一个唯一的号码(仅对客户端是唯一的)
- 设置协议版本
- 根据接口定义配置接口版本
- 设置消息类型为REQUEST_NO_RETURN(即0x01)
- 将返回代码设置为 0x00
[PRS_SOMEIP_00171] Fire & Forget消息不会返回错误。错误处理和返回代码应在需要时由应用程序执行。
通知事件
通知事件描述了一个通用的发布/订阅概念。通常,服务器发布客户端订阅的服务。在某些情况下,服务器将向客户端发送一个事件,该事件可能是一个更新的值或已发生的事件。
SOME/IP仅用于传输更新的值,而不用于发布和订阅机制。这些机制是由SOME/IP-SD实现的。
[PRS_SOMEIP_00925] 对于SOME/IP通知消息,服务器必须做以下有效载荷和头:
- 构建有效载荷
- 根据服务器想要发送的事件设置消息ID。
- 将Length字段设置为8字节(用于Length字段后的SOME/IP头部分)+序列化有效负载的长度。
- 将客户端ID设置为0x00。设置会话ID[PRS_SOMEIP_00932], [PRS_SOMEIP_00933]和[PRS_SOMEIP_00521]。如果是活动会话处理,会话ID应在每次传输时增加。
- 设置协议版本
- 根据接口定义配置接口版本
- 将消息类型设置为NOTIFICATION(即0x02)
- 将返回代码设置为 0x00
[PRS_SOMEIP_00926]通知消息的有效负载应该由事件的序列化数据组成
[PRS_SOMEIP_00930]当同一ECU上存在多个订阅客户时,系统应处理通知的复制,以节省通信媒体上的传输, 当通知使用多播消息传输时,这一点尤其重要。
通知发送策略
对于不同的用例,发送通知的不同策略是可能的。下面是一些常见的例子:
- 循环更新-以固定间隔发送更新值(例如,每100毫秒发送与安全相关的Alive消息)
- 变更的更新——一旦“值”发生变化(例如:门打开),就发送更新
- 变化-仅当与上一个值的差值大于某个值时才发送更新。这个概念可能是适应性的,即预测是基于历史的;因此,只有当预测值和当前值之间的差异大于时,才会传输更新
Fields
字段表示状态并具有有效值。订阅该字段的使用者,立即获得该字段的初始值event
[PRS_SOMEIP_00179] 字段应该是getter、setter和notification事件的组合。
[PRS_SOMEIP_00180] 没有setter、getter和通知器的字段不存在。该字段至少应该包含一个getter、setter或通知器。
[PRS_SOMEIP_00181]字段的getter应该是一个请求/响应调用,请求消息中有一个空的有效负载,响应消息的有效负载中有字段的值。
[PRS_SOMEIP_00182]字段的setter应该是一个请求/响应调用,该请求/响应调用具有请求消息有效载荷中字段的期望值和响应消息有效载荷中字段的设置值
NOTE:如果修改了请求有效负载的值(例如,因为它超出了限制),修改后的值将在响应有效负载中传输
[PRS_SOMEIP_00909]当客户端订阅该字段时,通知程序将发送一个事件消息传送到客户端
[PRS_SOMEIP_00183]在更改字段的值时, 通知程序应该发送一个事件消息,并遵循事件规则
错误处理
错误处理可以在应用程序或下面的通信层中进行。因此SOME/IP支持两种不同的机制:
- 在方法的响应消息中返回代码
- 明确的错误信息
使用哪一种,取决于配置。
[PRS_SOMEIP_00901] 一个方法调用的回复消息中的Return Code ,将应用程序错误和方法的响应数据从提供者传输到方法的调用者。
NOTE:请注意,从SOME/IP的角度来看,请求和响应方法的返回码不会被视为错误。这意味着,如果请求/响应方法退出时返回代码不等于0x00,则消息类型仍然是0x80 (如果AUTOSAR ClientServerOperation的ApplicationError与E_OK不同,消息类型仍然是0x80)
[PRS_SOMEIP_00902]显式错误消息应使用来传输应用程序错误和响应数据,或者将SOME/IP错误从提供者传递给方法的调用者。
[PRS_SOMEIP_00903]如果需要传输更详细的错误信息,则错误消息(消息类型0x81)的有效载荷应填满特定于错误的数据,例如一个异常字符串。将发送错误消息而不是响应消息。
这可以用来处理服务器中可能发生的所有不同的应用程序错误。此外,通信媒介或中间组件的问题(例如开关)可能发生,必须通过可靠的运输方式来处理。所有消息的头部都有一个返回码字段。
[PRS_SOMEIP_00904]只有响应(响应消息(消息类型0x80)和错误消息(消息类型0x81)应该使用返回码字段来携带返回码到它们所响应的请求(消息类型0x00)。
[PRS_SOMEIP_00905] 除了0x80和0x81之外的所有其他消息都将该字段设置为0x00
Return Code
[PRS_SOMEIP_00187] 返回代码为UINT8类型。
[PRS_SOMEIP_00191] 当前定义的返回码如下表所示
ID | Name | Description |
---|---|---|
0x00 | E_OK | No error occurred |
0x01 | E_NOT_OK | An unspecified error occurred |
0x02 | E_UNKNOWN_SERVICE | The requested Service ID is unknown. |
0x03 | E_UNKNOWN_METHOD | The requested Method ID is unknown. Service ID is known. |
0x04 | E_NOT_READY | Service ID and Method ID are known. Application not running. |
0x05 | E_NOT_REACHABLE | System running the service is not reachable (internal error code only). |
0x06 | E_TIMEOUT | A timeout occurred (internal error code only). |
0x07 | E_WRONG_PROTOCOL_VERSION | Version of SOME/IP protocol not supported |
0x08 | E_WRONG_INTERFACE_VERSION | Interface version mismatch |
0x09 | E_MALFORMED_MESSAGE | Deserialization error, so that payload cannot be deserialized. |
0x0a | E_WRONG_MESSAGE_TYPE | An unexpected message type was received (e.g.REQUEST_NO_RETURN for a method defined as REQUEST). |
0x0b | E_E2E_REPEATED | Repeated E2E calculation error |
0x0c | E_E2E_WRONG_SEQUENCE | Wrong E2E sequence error |
0x0d | E_E2E | Not further specified E2E error |
0x0e | E_E2E_NOT_AVAILABLE | E2E not available |
0x0f | E_E2E_NO_NEW_DATA | No new data for E2E calculation present. |
0x10 - 0x1f | RESERVED | Reserved for generic SOME/IP errors. These errors will be specified in future versions of this document. |
0x20 - 0x5E | RESERVED | Reserved for specific errors of services and methods. These errors are specified by the interface specification. |
Error Message
错误处理概述
通信错误和处理
4_SOMEIP 协议处理相关推荐
- 常用开源协议介绍以及开源软件规范列表
1. 开源协议介绍 GPL: General Public License,开源项目最常用的许可证,衍生代码的分发需开源并且也要遵守此协议.该协议也有很多变种,不同变种要求会略微不同. MPL: MP ...
- Redis 笔记(11)— 文本协议 RESP(单行、多行字符串、整数、错误、数组、空值、空串格式、telnet 登录 redis)
RESP 是 Redis 序列化协议Redis Serialization Protocol 的简写.它是一种直观的文本协议,优势在于实现异常简单,解析性能极好. Redis 协议将传输的结构数据 ...
- HTTP 协议入门 — (TCP/IP协议族、通信传输流、URI 与 URL 的区别、Cookie 状态管理、HTTP 支持的方法、状态码类别、HTTP 首部字段)
TCP/IP协议族 在介绍 HTTP 协议之前,我们先对 TCP/IP 协议族有个大概的了解,TCP/IP 协议从上到下主要分为应用层.传输层.网络层和数据链路层,各层的主要功能如下表所示: 协议层 ...
- 【JavaWeb】servlet与http请求协议
Servlet: 概念: server applet (服务端小程序)运行在服务器端的小程序 Servlet就是一个接口,定义了Java类被浏览器访问到(Tomcat识别)的规则. 将我我们自定义一个 ...
- synopsys PCIE IP协议解析
synopsys PCIE IP协议解析 1.Overview Core支持单个Pcie内核的Loopback功能,该功能主要为了做芯片验证,以及在没有远程接收器件的情况下完成自己的回环.同时,Cor ...
- 用户自定义协议client/server代码示例
用户自定义协议client/server代码示例 代码参考链接:https://github.com/sogou/workflow message.h message.cc server.cc cli ...
- Thrift协议与传输选择
1 协议 Thrift 可以让用户选择客户端与服务端之间传输通信的消息协议类别,如我们前面所讲总体划分为文本 (text) 和二进制 (binary) ,为节约带宽,提高传输效率,一般情况下使用二进制 ...
- TCP/UDP协议基本概念
TCP和UDP协议是TCP/IP协议的核心. TCP 传输协议:TCP 协议是一TCP (Transmission Control Protocol)和UDP(User Datagram Protoc ...
- 【网站汇总】单片机常用通讯协议
1.UART UART协议快速扫盲(图文并茂+超详细)_GREYWALL-CSDN博客 UART串口协议详解 - 知乎 基于STM32之UART串口通信协议(一)详解 - LLLIN000 - 博客园 ...
最新文章
- highcharts加载数据库数据(java版)
- [POJ-3237] [Problem E]
- 数据结构与算法 | 用栈实现队列
- 2021年SWPUACM暑假集训day4KMP算法
- 【转】XP远程桌面连接2008提示:远程计算机需要网络级别身份验证,而您的计算机不支持该验证 ....
- 【POJ 2279】Mr. Young’s Picture Permutations【线性DP】
- java 保留原始顺序的有序map的新思路:List<Map.Entry<?,?>>
- Matlab计算相关系数
- Kafka:增加Topic的分区数
- 『已解决』0/1 nodes are available: 1 node(s) had taints that the pod didn‘t tolerate.
- 题解 CF940A 【Points on the line】
- 渗透测试:XSS实验集合
- 利用bind方便多域应用的开发
- 给一个朋友创业公司商业计划书的建议
- 7-1 水仙花数 (10 分)
- JavaScript前端开发第一次课内实训
- rigol 普源MSO5104数字示波器技术参数
- python五子棋游戏大作业_python-大作业之五子棋游戏(附代码)
- 中国夜视监控摄像机市场趋势报告、技术动态创新及市场预测
- 柏楚电子晶晨股份正式在科创板上市 柏楚电子开盘价高达217元