目录
- [1 摘要](#1 摘要)
- [2 SOME/IP-报文格式](#2 SOME/IP-报文格式)
-
- [2.1 **Service ID / 16 bits**](#2.1 Service ID / 16 bits)
- [2.2 **Method ID / Event ID / 16 bits**](#2.2 Method ID / Event ID / 16 bits)
- [2.3 **Length / 32 bits**](#2.3 Length / 32 bits)
- [2.4 **Client ID / 16 bits**](#2.4 Client ID / 16 bits)
- [2.5 Session ID / 16 bits](#2.5 Session ID / 16 bits)
- [2.6 Protocol Version / 8 bits](#2.6 Protocol Version / 8 bits)
- [2.7 Interface Version / 8 bits](#2.7 Interface Version / 8 bits)
- [2.8 Message Type / 8 bits](#2.8 Message Type / 8 bits)
- [2.9 Return Code / 8 bits](#2.9 Return Code / 8 bits)
- [2.10 通信过程示例](#2.10 通信过程示例)
- [3 总结](#3 总结)
1 摘要
本专题接着上一专题对SOME/IP进行介绍,主要对SOME/IP报文格式以及定义的字段进行详细介绍,有助于在实际项目过程中对SOME/IP报文的理解。
上文回顾:
车载以太网网络测试 -24【SOME/IP概述】
2 SOME/IP-报文格式
通过上个专题介绍,SOME/IP是一个通信中间件,位于传输层之上,因此SOME/IP的数据封装在传输层头部的后面。如下图所示,SOME/IP也有帧头部分。
SOME/IP报头的总长度为16个字节,共有9个字段。
各字段说明:
2.1 Service ID / 16 bits
服务标识,Service ID 是一个核心标识符,用于唯一标识车载网络或分布式系统中的服务(Service)。
唯一标识服务
Service ID 是一个16位的无符号整数(0x0000~0xFFFF),用于在系统中唯一区分不同的服务。例如:
- 0x1234 可能代表"车速服务",
- 0x5678 可能代表"电池管理服务"。
通过Service ID,客户端和服务端可以明确识别通信的目标服务,避免混淆。
2.2 Method ID / Event ID / 16 bits
Method ID 和 Event ID 是用于标识服务通信中不同操作和事件的关键标识符。
- Method ID(方法标识符)
作用 :唯一标识服务接口中的可调用方法 (远程过程调用,RPC)。
功能 :- 客户端通过发送包含
Method ID
的请求报文,调用服务端的特定方法。 - 服务端根据
Method ID
确定需要执行的方法,并返回响应(如方法返回值或状态)。
示例场景: - 车辆ECU提供"获取车速"服务,客户端通过
Method ID = 0x1234
调用该方法,服务端返回当前车速值。
- 客户端通过发送包含
- Event ID(事件标识符)
作用 :唯一标识服务接口中的事件 (由服务端主动通知客户端的数据)。
功能 :- 服务端通过
Event ID
标记特定事件(如传感器数据变化、状态更新)。 - 客户端订阅(Subscribe)指定
Event ID
后,服务端会在事件触发时推送通知(Notification)。
示例场景: - 车载温度传感器服务通过
Event ID = 0x5678
定期发布温度数据,客户端订阅后即可接收实时更新。
- 服务端通过
说明 :
这个字段的第一个bit是标志位 ,如果标志位为0 ,表示后面15位为Method ID(Method、Field.Getter及Field.Setter);如果标志位为1 ,表示后面15位为Event ID(包括Event和Field.Notify)
Method/Event ID部分:
若最高位=0(ID < 0x8000)→ Method ID
若最高位=1(ID ≥ 0x8000)→ Event ID
因此,Method和Event可以从该字段的值来区分:
- Method ID的范围为0x0000 ~ 0x7FFF
- Event ID的范围为0x8000 ~ 0xFFFF。
Method和Event为SOME/IP的两种通信方式,后面专题介绍。
Service ID和Method ID/Event ID 两个字段可以组成Message ID,每个Message ID在车内网络都是唯一的,可以用来标识某个服务的某个接口。
2.3 Length / 32 bits
-
位置 :位于SOME/IP Header的第5-8字节(即从第4字节开始,前4字节为Message ID和Length字段本身)。
-
数据类型:32位无符号整数(大端序,Big-endian)。
-
单位:字节(Byte)。
-
计算范围 :从
Client ID
字段开始到整个报文结束(包括Payload)的总字节数。
服务 ID(Service ID) 和 方法/事件 ID(Method/Event ID) 属于 SOME/IP 报文头 的一部分,位于 Length 字段之前,因此不被计入 Length。 -
作用:
- 报文边界识别:接收方通过Length字段确定报文的结束位置,尤其在TCP等流式传输中区分多个连续的SOME/IP报文。
- 完整性校验:验证接收到的数据是否完整(实际接收的字节数是否与Length字段匹配)。
- 协议解析:帮助解析器正确分离Header和Payload部分
2.4 Client ID / 16 bits
Client ID是一个用于标识客户端实例的唯一标识符,服务器可通过该字段区分不同的客户端,在多个客户端同时请求或使用同一个服务器中的同一个服务时可使用。Client ID也可以设置为车内网络唯一的,这样可以直接用于标识出具体的节点。它是一个16位的字段。
-
Client ID的作用
Client ID在SOME/IP通信中扮演着重要角色:
- 服务实例识别:帮助服务端识别和区分不同的客户端实例
- 会话管理:在请求-响应交互中维护客户端与服务端之间的会话状态
- 消息路由:确保响应能够正确返回到发起请求的客户端
- 负载均衡:在多个服务实例场景下,帮助实现请求的合理分配
- 状态跟踪:服务端可以跟踪不同客户端的状态和生命周期
-
分配方式:
- 可以由客户端自行生成(需确保唯一性)
- 可以由中间件或服务端分配
- 通常采用递增或随机方式生成
-
应用场景:
- 服务发现:在服务发现过程中,客户端使用Client ID标识自己
- 方法调用:在RPC调用中标识调用方
- 事件订阅:标识事件订阅的客户端
- 错误处理:帮助定位问题发生的客户端
Client ID是SOME/IP实现多客户端并发访问同一服务的基础机制之一,确保了服务端能够正确处理来自不同客户端的并行请求。
2.5 Session ID / 16 bits
会话标识,可以用来区分来自同一发送者的多条请求,表示请求或消息的顺序。如果使用,应在每次调用后递增,其范围为0x0001到0xFFFF,当达到0xFFFF后,则循环至0x0001重新开始计数。对于请求/响应的method,客户端可通过Session ID来识别正确的响应,如果响应的Session ID与其发送的请求中不一致,应忽略。对于Event,有多种不同场景下的应用,如果不使用该字段,可置为0x0000,接收端直接忽略即可。
-
Session ID的作用
- 会话标识:唯一标识客户端与服务端之间的特定交互会话
- 请求-响应匹配:帮助客户端将响应与正确的请求关联起来
- 多路复用支持:允许多个并发会话通过同一连接进行
- 状态跟踪:协助跟踪长时间运行的交互状态
-
对于不同的通信模式有不同的使用方式:
- 请求/响应模式:用于匹配请求和响应
- 事件/通知模式:可能用于标识订阅会话
- 字段通信:可能用于跟踪字段更新会话
在SOME/IP-SD(服务发现)中,Session ID可能有特殊用途,用于标识服务实例
- 实际应用
在汽车电子系统中,Session ID帮助管理复杂的服务交互,特别是在以下场景:- 多个ECU之间的并发服务调用
- 长时间运行的操作(如固件更新)
- 需要保持状态的交互序列
2.6 Protocol Version / 8 bits
协议版本,表示SOME/IP协议的版本,即SOME/IP的头部格式版本。发送端和接收端所支持的协议版本应一致,如果不一致则无法处理,主要用于版本控制和兼容性管理。以下是其详细定义与作用:
长度 :1字节(8位)。
取值 :通常为 0x01
(表示SOME/IP协议版本1),这是当前广泛实现的版本。
标准参考:根据AUTOSAR规范,SOME/IP协议版本需严格定义以确保互通性。
- 作用
(1) 协议版本标识 - 标识数据包遵循的SOME/IP协议版本,确保通信双方使用相同的协议规则(如消息格式、序列化方式等)。
- 例如:
0x01
表示版本1,可能支持基础RPC和事件通知;未来版本可能扩展新功能(如增强的QoS机制)。
(2) 兼容性控制 - 接收方检查 :若接收方不支持该版本,可拒绝处理或触发错误响应(如返回
NOT_OK
状态)。 - 多版本共存 :网关或中间件可能根据此字段对消息进行转换或路由(如版本1与版本2互通时)。
(3) 未来扩展性 - 保留字段为未来协议升级提供可能(例如:
0x02
可能引入新的头部字段或优化序列化效率)。
实际应用示例:
- 场景:ECU A(版本1)向ECU B(版本2)发送请求。
- 处理流程 :
- ECU B检测到
Protocol Version=0x01
,判断自身是否支持向后兼容。 - 若不支持,通过SOME/IP错误响应通知ECU A;若支持,则按版本1规则处理消息。
- ECU B检测到
2.7 Interface Version / 8 bits
接口版本,用于标识服务接口的版本号,在AUTOSAR等车载系统中,Interface Version通常与服务接口描述文件(ARXML)中定义的版本一致,确保通信双方对接口定义的理解一致。
- 作用
-
版本控制:标识服务接口的版本,允许服务接口在不破坏向后兼容性的情况下进行演进。
-
兼容性管理:客户端和服务端可以通过版本号判断是否兼容,避免因版本不匹配导致的通信问题。
-
多版本支持:系统可以同时部署同一服务的多个版本,通过版本号区分。
- 使用场景
-
当服务接口有重大变更时(如新增方法、事件或字段),递增主版本号。
-
当服务接口有向后兼容的修改时(如bug修复或性能优化),递增次版本号。
-
客户端在请求时可以指定它能处理的最高版本,服务端可以选择使用兼容的版本进行响应。
-
注意事项
-
版本号递增策略应由服务接口设计者明确定义
-
版本号比较通常采用简单的数值比较
-
版本不匹配时应定义明确的错误处理机制
2.8 Message Type / 8 bits
报文类型,用于表示SOME/IP报文的类型。它在SOME/IP协议头中占据重要位置,直接影响通信双方对消息的处理逻辑,通过该字段可以识别该报文是请求、响应、通知或者错误等。其中第三位为分段标志位(TP-Flag),用于表示该条报文是否被分段。
说明:
TP指SOME/IP-TP(Transport Protocol),是SOME/IP的传输协议,可以简单的理解为是分段传输机制,在后续专题中会详细介绍。
以下是完整的Message Type取值及其含义(十六进制表示):
Type Value | 名称 | 描述 |
---|---|---|
0x00 |
REQUEST | 客户端到服务的请求(请求并期望响应)。 |
0x01 |
REQUEST_NO_RETURN | 客户端到服务的请求(不期望响应)。 |
0x02 |
NOTIFICATION | 事件通知(无响应)。 |
0x40 |
REQUEST_ACK | REQUEST的ACK确认。 |
0x41 |
REQUEST_NO_RETURN_ACK | REQUEST_NO_RETURN的ACK确认。 |
0x42 |
NOTIFICATION_ACK | NOTIFICATION的ACK确认。 |
0x80 |
RESPONSE | 服务端对REQUEST的响应(Bit 7=1表示响应)。 |
0x81 |
ERROR | 响应中包含错误。 |
0xC0 |
RESPONSE_ACK | RESPONSE的ACK确认。 |
0xC1 |
ERROR _ACK | ERROR的ACK确认。 |
0x20 |
TP_REQUEST | 分块传输(TP)的请求报文(期待响应)。 |
0x21 |
TP_REQUEST_NO_RETURN | 分块传输(TP)的请求报文(无响应)。 |
0x22 |
TP_NOTIFICATION | 一个TP通知/事件回调的请求,不期待有响应。 |
0xA0 |
TP_RESPONSE | TP请求的响应报文。 |
0xA1 |
TP_ERROR | TP请求的错误响应。 |
关键说明:
- Bit 7 (最高位) :
0
: 表示请求或通知(客户端→服务端)。1
: 表示响应或错误(服务端→客户端)。
- Bit 6 :
1
时表示响应(如RESPONSE
或ERROR
)。
- TP前缀 :
- 标识报文使用分块传输(Transport Protocol),用于超过SOME/IP默认MTU的数据。
2.9 Return Code / 8 bits
Return Code 字段是一个8位(1字节)的无符号整数,用于表示远程方法调用(RPC)或事件通知的处理结果状态。它的定义和作用类似于HTTP状态码,用于指示请求是否成功、失败或需要进一步处理。所以只会在响应或者错误类型的报文中才有意义。对于请求和通知类报文(REQUEST, REQUEST_NO_RETURN, NOTIFICATION) 该字段不使用,应置0x00。
SOME/IP协议规范(如AUTOSAR标准)定义了以下常见的Return Code值:
值(十进制) | 名称 | 描述 |
---|---|---|
0x00 (0) | E_OK |
请求成功完成。 |
0x01 (1) | E_NOT_OK |
通用错误(未明确指定的失败)。 |
0x02 (2) | E_UNKNOWN_SERVICE |
请求的服务ID不存在。 |
0x03 (3) | E_UNKNOWN_METHOD |
请求的方法ID在服务中不存在。 |
0x04 (4) | E_NOT_READY |
服务/方法尚未准备好(例如初始化未完成)。 |
0x05 (5) | E_NOT_REACHABLE |
服务端不可达(网络或通信问题)。 |
0x06 (6) | E_TIMEOUT |
请求超时(未在指定时间内收到响应)。 |
0x07 (7) | E_WRONG_PROTOCOL_VERSION |
协议版本不匹配。 |
0x08 (8) | E_WRONG_INTERFACE_VERSION |
接口版本不匹配。 |
0x09 (9) | E_MALFORMED_MESSAGE |
消息格式错误(如字段长度或类型不符)。 |
0x0A (10) | E_WRONG_MESSAGE_TYPE |
消息类型不匹配(如期望请求但收到响应)。 |
0x0B--0x7F | 保留 | 协议规范保留的代码,未来可能扩展。 |
0x80--0xFF | 供应商特定 | 供厂商自定义使用(如特定ECU或中间件的扩展错误码)。 |
Return Code的作用:
-
反馈调用状态
客户端通过Return Code快速判断请求是否成功,或定位失败原因(如服务不可用、参数错误等)。
-
错误处理与恢复
客户端可根据不同Return Code采取不同策略(如重试、回退、日志记录等)。例如:
- 遇到
E_NOT_READY
可延迟重试。 - 遇到
E_UNKNOWN_METHOD
需检查方法ID配置。
- 遇到
-
协议兼容性
- 版本不匹配(如
E_WRONG_PROTOCOL_VERSION
)提示双方升级协议。 - 供应商特定代码(0x80以上)支持私有扩展。
- 版本不匹配(如
-
调试与诊断
在开发和测试阶段,Return Code帮助快速定位通信或逻辑问题。
示例场景:
-
成功请求
客户端调用方法
0x1234
,服务端返回Return Code = 0x00 (E_OK)
,表示执行成功。 -
服务不存在
客户端请求一个未注册的服务(如ID
0x9999
),服务端返回0x02 (E_UNKNOWN_SERVICE)
。 -
超时处理
客户端未在设定时间内收到响应,本地SOME/IP栈生成
0x06 (E_TIMEOUT)
。
注意事项:
- AUTOSAR兼容性:不同AUTOSAR版本可能扩展Return Code,需参考对应标准文档(如AUTOSAR_SWS_SOMEIPProtocol)。
- 自定义代码:供应商特定代码需确保收发双方约定一致,避免冲突。
- 与Response Code区别:Return Code是协议层状态,而Response Code可能用于应用层错误(如参数校验失败)。
2.10 通信过程示例
以下是一个详细的SOME/IP报文通信过程示例,包含报头结构解析和交互流程:
1. SOME/IP报文头结构(12字节)
字段 | 长度(字节) | 示例值 | 说明 |
---|---|---|---|
Message ID | 4 | 0x12345678 | 高16位:Service ID (0x1234) |
低16位:Method ID (0x5678) | |||
Length | 4 | 0x00000010 | 从Request ID开始的剩余长度 |
Request ID | 4 | 0xDEADBEEF | 高32位:Client ID (0xDEAD) |
低32位:Session ID (0xBEEF) | |||
Protocol Version | 1 | 0x01 | SOME/IP版本(通常为1) |
Interface Version | 1 | 0x02 | 服务接口版本 |
Message Type | 1 | 0x00 (REQUEST) | 0x80=REQUEST, 0x40=RESPONSE |
Return Code | 1 | 0x00 (E_OK) | 0x00=成功,其他为错误码 |
2. 通信流程示例(客户端调用服务端方法)
步骤1:客户端发送REQUEST
plaintext
SOME/IP Header:
Message ID: 0x12345678 (Service ID=0x1234, Method ID=0x5678)
Length: 0x00000010 (16字节,含Request ID后的数据)
Request ID: 0xDEADBEEF (Client ID=0xDEAD, Session ID=0xBEEF)
Protocol Ver: 0x01
Interface Ver: 0x02
Message Type: 0x80 (REQUEST)
Return Code: 0x00
Payload:
0x11223344 (示例数据:输入参数)
步骤2:服务端回复RESPONSE
plaintext
SOME/IP Header:
Message ID: 0x12345678 (与请求匹配)
Length: 0x0000000C (12字节,仅含返回值)
Request ID: 0xDEADBEEF (与请求匹配)
Protocol Ver: 0x01
Interface Ver: 0x02
Message Type: 0x40 (RESPONSE)
Return Code: 0x00 (E_OK)
Payload:
0xAABBCCDD (示例数据:计算结果)
3. 异常场景示例
场景:方法调用失败(服务不可用)
plaintext
SOME/IP Header:
Message Type: 0x40 (RESPONSE)
Return Code: 0x07 (E_NOT_READY)
# 其他字段与请求匹配
Payload: 无
4. 关键字段说明
- Message ID :唯一标识服务和方法(如
0x1234:0x5678
表示服务A的Method X)。 - Request ID:匹配请求与响应(同一Client ID + 自增Session ID)。
- Message Type :
0x80
= REQUEST(需要响应)0x40
= RESPONSE0x20
= ERROR
- Return Code :常见值:
0x00
(E_OK):成功0x01
(E_NOT_OK):通用错误0x07
(E_NOT_READY):服务未初始化
5. 通信流程图示
Client Server
| --- REQUEST (0x80) ---> |
| <-- RESPONSE (0x40) --- |
| (ReturnCode=0x00) |
通过上述示例,可以清晰理解SOME/IP协议中报头如何标识服务、匹配请求/响应及处理异常。实际应用中需结合服务发现(SOME/IP-SD)实现动态服务订阅。
3 总结
以上是对SOME/IP报文的格式以及各字段的定义进行了介绍,并且通过列举实例来帮助大家对SOME/IP通信过程的理解,希望能有所帮助!