DDS-RPC通信機制
基本概念
- 關於DDS的概念請見:DDS與OpenDDS
- 什麼是DDS-RPC:
OMG官網給出關於DDS-RPC概念的定義:OMG DDS-RPC
This specification defines a Remote Procedure Calls (RPC) framework using the basic building blocks of DDS, such as topics, types, DataReaders, and DataWriters to provide request/reply semantics. It defines distributed services, described using a service interface, which serves as a shareable contract between service provider and a service consumer. It supports synchronous and asynchronous method invocation. Despite its similarity, it is not intended to be a replacement for CORBA.
DDS-RPC又叫PRC over DDS,RPC指Remote Procedure Calls,關於RPC的概念請自行溫習。根據字面意思,已經OMG給出的定義。DDS-RPC可以總結爲:
DDS-RPC構建在DDS上,實現請求/應答通信機制。
- DDS-RPC概念模型(簡易)
請求端發送請求ID和請求信息,接收端通信請求ID和請求信息,調用相應的本地處理函數。然後,將結果,通過應答ID和請求ID和應答信息,告知給調用房。
DDS-RPC規範及實現方法
OpenDDS暫時沒有原生支持DDS-RPC。既然OMG給出了DDS-RPC這種通信機制,自然要定義一套規範(大家要遵循這個套規範實現之)。
由於DDS-RPC是構造在DDS之上的,因此DDS-RPC通信的實現過程,包括以下幾個關鍵點:
- 服務定義
- 服務映射(請求/應答主題)
- 發現/匹配RPC服務
- 請求/應答關聯
服務定義
所謂服務定義是指:如何描述RPC中的服務接口信息。
下面給出一個例子IDL文件(DDS使用IDL作爲接口文件)。
module robot { // 模塊
interface RobotControl // 接口
{
void command(Command com); // 函數
void getStatus(out Status status);
float setSpeed(float speed);
}
}
詳細請參考:https://www.omg.org/spec/DDS-RPC/1.0/PDF (7.3 Service Definition)
服務映射
- Mapping Service Specification To DDS Topics
服務映射指:將服務定義轉換爲DDS識別的Topic信息。
- Topic映射包括主題名映射與數據類型映射
- 主題名映射
DDS-RPC有三種映射機制:Default Topic Names、Specifying Topic Names using Annotations、Specifying Topic Names at Run-time。
這裏給出“Specifying Topic Names using Annotations”例子:
@DDSService
@DDSRequestTopic (name=“RobotRequestTopic”) // @DDSRequestTopic (Requset主題註釋關鍵字)
@DDSReplyTopic (name=”RobotReplyTopic”) // @DDSReplyTopic (Rely主題註釋關鍵字)
interface RobotControl
{
}
詳細請參考:https://www.omg.org/spec/DDS-RPC/1.0/PDF (Chapter 7.4)
- 數據類型映射
請求/應答主題(Topic)的結構由接口信息確定。根據DDS-DPC規定,主題包含消息頭與數據兩部分。
請求主題
struct RobotControl_Request
{
dds::rpc::RequestHeader header;
RobotControl_Call data;
};
應答主題
struct RobotControl_Reply
{
dds::rpc::ReplyHeader header;
RobotControl_Return data;
};
- 請求主題
如何將操作映射爲一個請求主題呢?
首先,將操作映射到In structure,然後再In structure中定義操作的輸入參數。
${interfaceName}_$ {operationName}_In
// 例:
RobotControl_setSpeed_In
- 應答主題:
首先,將操作映射到Out structure,然後在Out structure內定義操作的輸出參數以及”reture_”返回值。
${interfaceName}_${operationName}_Out
// 例
RobotControl_setSpeed_Out
關於請求與應答主題,如何映射,這裏只簡單介紹了一小部分。詳細規則,請參考
https://www.omg.org/spec/DDS-RPC/1.0/PDF
- Interface映射
上面,已經將操作映射爲DDS可以識別的結構體。根據DDS-RPC的服務定義,可以知道,一個Interface包含一系列接口。那麼如何對Interface進行映射?
請求(interface)映射:
${interfaceName}_Call
// 例
union RobotControl_Call switch(long)
應答(interface)映射:
union RobotControl_Return switch(long)
關於 服務映射,這裏只說了一小部分。更多的內容,請參考:
https://www.omg.org/spec/DDS-RPC/1.0/PDF
OMG給出的IDL定義實例,請參考:
https://www.omg.org/spec/DDS-RPC/About-DDS-RPC/
【RPC over DDS 1.0 IDL .zip file】
- 總結
根據上面所說內容,可以將RPC定義的服務,映射爲DDS可以識別的數據類型。
接下來,就需要調用端與服務提供端,進行RPC服務的發現與匹配。
發現與匹配RPC服務
請求與應答是兩個獨立的DDS Topic,因此不能保證兩個主題同時被發現。
例:
請求主題發現完成。應答主題未發現。此時,服務器能夠接收數據,但無法返回數據給服務的調用者。
DDS-RPC針對上述問題,定義了發現/匹配RPC服務機制,可以簡單總結爲:
- 服務器:激活服務器,初始狀態不可讀(不能接收請求)。當前請求與應答主題,兩段相互發現(匹配完成)時,正常工作。
- 客戶端:激活客戶端,初始狀態不可寫(不能發送請求)。當前請求與應答主題,兩段相互發現(匹配完成)時,正常工作。
詳細請參考:https://www.omg.org/spec/DDS-RPC/1.0/PDF(7.6)
請求與應答關聯
- 問題
- 解決方案:
請求主題實例數據與應答主題實例數據中添加某一個遠程調用的樣本身份。
服務請求ID(包含在請求主題消息頭,根據系統信息生成)。
服務應答ID(包含在應答主題消息頭,根據系統信息生成)
詳細內容請參考:https://www.omg.org/spec/DDS-RPC/1.0/PDF