RTミドルウエアとROSについて,ysugaも比較してみました.
まず,
RTミドルウエアとROSは比較しても・・・ね?
RTミドルウエアという言葉は,ロボット用のミドルウエアの総称のようなものです.細かく言えば,RTミドルウエアって言葉が指すものは,RTミドルウエアプロジェクトで提案された通信規格に準拠しているミドルウエアの総称でしょうから,つまり,OpenRTM-aistやOpenRTM.NET,OROCOS,Gostai-RTC,RTC-Liteなど,RTミドルウエア規格に準拠/一部準拠するソフトウエアの総称なので,実装レベルで動いているROSと比較するのは結構ナンセンスだと思っています.
RTミドルウエアはCORBAだからなぁ,とか言っている人はこの辺を勘違いしているんだと思います.産総研のジェフさんによって,DDSなどの高速な通信規格に対応したデータポートを実装することもできます.RTミドルウエアはただの規格なんです.
この規格は今のところRTコンポーネントに関する規格一つですが,OMGで管理されている以上は結構長く残るものだと思っています.
規格があるってこと自体が持つ意味はかなり大きいです.
RTC規格に準拠したソフトウエア間では,かなり簡単に接続ツールを作ることが出来ます.OpenRTM.NETやRTC-Lite(軽量版RTC)は,相互に通信できるようです.僕もRTnoというArduino用のRTM的なものを作りましたが,ポートや状態マシンの概念さえそろっていれば,変換ツールは簡単に出来ちゃいます.
ROSにもAPIやTCPROSなどの通信規格と呼べるものがありますが,この辺の後方互換性についてはどこかでしっかりと宣言してほしいですし,もう少し抽象化した規格があれば,XML-RPCではなく,独自のAPIサービスを実装して超軽量版ROSを作成することも可能になると思います.この辺がROSの弱み.
OpenRTM-aistとROSの比較
さて,実装レベルではOpenRTM-aistとROSで比較するとどうでしょうか.
分散システム
まず,OpenRTM-aistもROSも同じ分散システム指向なシステム開発を行います.
分散システムはシステムの一部がエラー等で終了した場合においても,システム全体のシャットダウンなどにつながらない堅牢なシステムを提供する枠組みです.
OpenRTM-aistはRTコンポーネントという単位
OpenRTM-aistではRTコンポーネント(RTC)という単位の組み合わせで実行されます.
RTCは他のRTCと接続するためのエンドポイントとなる「ポート」を持っており,これで分散システムを構築します.
RTCは必ずしも一つのプロセスに一つのRTCではありません.これはCORBA上にRTミドルウエアを実現したOpenRTM-aistの特徴の一つといえます.
ROSはノード
ROSはノード単位です.
ノードは一つのプロセスに一つのノードが一般的です.Pythonコード側(rospy)しか読んでませんが,シングルトンを多用しているので,一つのプロセスに複数のノードを実現するのは難しいと思います.
違い
対応プラットフォームと言語
ROSもOpenRTMも,どちらもミドルウエアとしての性格を持っています.
ミドルウエアとは,OSや実装言語の違いを吸収して,ユニバーサルに通信を行うためのライブラリを指しています.
OpenRTM-aistは対応するOSや言語が広い
OpenRTM-aistは対応するOSがWindows, Linux, Mac OSと幅広いです.さらに,Toppers (TRON系OS)や,VxWorksへのポーティングが報告されていますので,リアルタイムシステム上での実行が可能です.
言語はC++,Java,Pythonに対応しています.一応,OpenRTM-aist互換のライブラリとして,OpenRTM.NETがあり,.NET Frameworkを使ってプログラミング出来ます.(つまり,VB,C#,F#などでの実装が可能).
拙作のRTC-scilabを使えば,scilab言語(フリーのMATLABといえばわかりやすいですかね?)でのRTC作成が可能です.
ROSは対応OSの幅が狭いか?
ROSは基本的にLinux上での運用を前提としています.
もちろんMacやWindows (Cygwin) にもインストールすることが出来ますが,ROSの恩恵を一番に受けるのはCUIでのスピーディなプロトタイピングだと思います.
開発言語はC++, Python, Java (rosjava)ですが,これ以外にもoctave (フリーのMATLAB)から利用が可能です.僕はC++とPythonしか試したことがありませんが・・・
比較
開発する言語は,OpenRTM-aistではC++, Python, Java.で,互角といえるでしょう.
OpenRTM-aistの方が動作するプラットフォームとしては充実しています.Windowsが必要なのか?という議論もあると思いますが,使いこなしてみれば,逆にLinuxじゃなきゃいけない理由もないです.リアルタイムカーネルとか使うときぐらいだと思います.
Windowsでロボットを動かしているという人も,すくなくとも日本国内では少なくありません.Visual Studioはかなり優秀なツールだと思いますけどどうですか?図書館の案内システムとかWindowsで作られていますよね?いずれサービスロボットがそういう世界に触れるときのことを考えると,Windowsは無視できませんよ.
開発方法
この辺でROSとOpenRTM-aistの違いが浮き彫りになってきます.
OpenRTM-aist
OpenRTM-aistのツールはグラフィカルな開発ツールが非常に充実しています.
基本的にすべてEclipse上で動くGUIツールですが,設計,ドキュメント作成,スケルトンコードの生成,コーディング,運用がEclipseに統合されています(一部 Visual Studioでコンパイルする必要がありますが,最新バージョン1.1ではEclipseでコンパイルできるようになるらしい).
OpenRTM-aistではまず,RTCをEclipse上のツールで設計し,スケルトンコードを作成します (RTC-Builder).
スケルトンコードはRTCの状態マシンを実装してあるクラスを継承したクラスのコードであり,このクラスの特定のメソッドが,RTCの状態マシンのコールバックになっています.
なので,開発者は特定のタイミングで呼ばれるコールバック関数上に機能を実装します.
RTCにメイン関数はありません.RTCを実行する実行ファイルを生成するコードも同時に排出されますが,RTCは後述するマネージャから実行すると使いやすいものになります.
ROSの場合はパッケージ
ROSではパッケージという単位で開発を行います.ROSではコマンドラインから実行できるツールが非常に充実しています.
まず,パッケージを作成,管理するためのコマンドroscreate-pkgやrospackなどがあります.また,パッケージの特定のノードを実行するためのrosrunコマンドや,マスターに登録されているトピックやサービスを確認するためのrostopic, rosservice,トピックやサービスに関する情報を収集するためのrosmsg, rossrvなどがあります.
*この辺のコマンドラインから実行できるツールとしてはOpenRTM-aistにもrtshellなどのツールが生まれてきましたが,ROSとは前提としている部分が違うので,使い心地は異なります.
ROSではまず,パッケージを作成してから,パッケージ内にノードとなるコードを作成します.パッケージを作成した時点で,コンパイル用のMakefileや依存関係を表すmanifest.xml,サービスやトピックを宣言するための仕組みなどが作成され,rosmakeコマンドでパッケージごとビルドすることが出来ます.
パッケージには複数のノードを作ることが出来,roslaunchの設定ファイルを使って,同時に複数起動したりすることもできます.
ただし,ノードのスケルトンとなるコードが生成されることはありませんので,自分でmainから記述する必要があります.
rosで提供されるのは,基本的にサービスやトピックを利用するための仕組みであり,それ以外の部分,たとえばノードごとのデプロイサービスなどはパッケージを管理するOSやシェルのレベルでのツールで提供されます.
通信の仕組み
OpenRTM-aistはポートを使って通信
OpenRTM-aistにはポートというデータ通信用のエンドポイントとして,「サービスポート」と「データポート」が提供されています.
データポートはデータを送受信するためのポートです.データポートは「型」を持っており,同じ型同士のデータポートは接続することが出来ます.データ型はLongやFloatなどの組み込みのデータ型だけでなく,独自にIDLというファイルを使ってデータ型を宣言することが出来ます.IDLはオブジェクト指向言語のインターフェース設計のためのメタ言語であり,CORBAやRMIのサービスを宣言するときに使うのが一般的でしょうか(僕はその程度しか使わないけど?)
サービスポートはデータの送受信だけでなく,特定の関数をリモートから実行させる仕組みと考えて下さい.サービスのリクエストに対して,その成否結果を返すことが出来ます.
また,コンフィグレーションという機能を使えば,RTCの実行時におけるパラメータを編集することが出来ます.簡単な例だと,モーターコントローラのゲインなどを実行中に変更する仕組み,でしょうか.データポートでも数値を変更する仕組みを提供できますが,コンフィグレーションはもっと簡易で,通信頻度の低い通信を指向しており,ツールなどから変更することを前提としています.
ROSではトピックで通信
ROSでは,データの送受信はトピックを使います.トピックはROSの世界に漠然と存在するクラウド的サービスと考えて下さい.ですので,ROSの世界にはノード間の接続という概念はありません(正確に言うとあるんですが).ノードは必要なトピックにアクセスして,データを受け取ります.マスターを中心としたシステムにカメラ画像などのサービスが存在していれば,それをサブスクライブすることで受け取ることが出来ます.
同種のトピックが多数あるときは,トピックのネームスペースを変更して対応します.たとえばロボットの左右のカメラを/left/image, /right/imageなどに分けてトピックとして立てておくことが出来ます.
また,「サービス」という仕組みが提供されています.これは,データの送受信ではなく,ある操作に対して,そのレスポンスを受け取るような場合に使います.
サービスも同様のクラウド的な仕組みを提供しています.サービスポートのように接続を必要とするものではありません.
またパラメータという仕組みはOpenRTM-aistにおけるコンフィグレーションと同じようなサービスを提供します.
比較
提供する機能としては大きな差はありません.データの送受信にはデータポートとトピック,それ以外のやり取りにはサービスポートやサービスという枠組みがあり,コンフィグレーションやパラメータの仕組みで細かい調整が出来ます.
トピックを使った発行購読モデルのROSには接続の面倒さが無いようですが,実際は実行時にネームスペースを指定したりするので面倒さは同じです.roslaunchなどのツールで自動化できますが,これもrtshellがありますし,自作の接続ツールを作るのは簡単です.このサイトの入門記事をご覧くださいね.

実行
OpenRTM-aistではManager
OpenRTM-aistではRTCを実行する仕組みとしてManagerというツールがあります.
Managerで実行する場合は,C++ではDLLとしてRTCを作成し,ManagerからRTCを読み込み,実行します.PythonではPythonスクリプトを直接読み込めます.JavaではJarファイルにしてManagerから読みだします.
このManagerが提供するサービスは複数のRTCを同時に実行する場合に非常に強力で,マネージャーのコンフィグレーションファイルを編集することで設定できます.
ただ,これだけではOpenRTM-aistのシステムは実行されません.RTC間の接続やコンフィグレーション,状態マシンのアクティベーションが必要で,この部分はEclipse上のグラフィカルなツールを使うか,rtshellというコマンドラインツールを使います.どちらも接続やコンフィグレーションを記述してあるRTシステムプロファイルというxml形式のファイルに対応しているので,一度システムを接続してプロファイルを保存しておけば,実行はそれほど大変ではありません.
ROSはroslaunch
ROSには接続という概念がありませんので(正確にはある),ノードの実行と,ネームスペースのリマッピングがすべてです.これを行うroslaunchという仕組みがあります.
そのほか
OpenRTM-aistの強みは,RTコンポーネントという国際規格に準拠しているだけあって,用語の整理や実行管理の仕組みが非常に洗練されています.特に実行コンテキストを使った実行状態管理が秀逸です.
OMGが管理するので,多くのオブジェクト指向言語からこのRTコンポーネントモデルを利用することが可能であり,コーディングスタイルまで共有することが出来ます.
実行コンテキストはRTCの実行をつかさどるオブジェクトで,RTCの状態変化時や周期実行タイミング時に呼ばれる各種のコールバックを呼び出します.実行時に実行コンテキストを変更することにより,作成されたRTCをシミュレータと同期しながら実行したり,リアルタイム周期実行したりすることが出来ます.
状態マシンを持っていることも重要で,RTCを遠隔から管理することが出来ます.
ROSは反対に,通信の仕組みを提供しているのみであり,状態管理などは各ノードの開発者に任せられています.多くのコードはPythonで書かれているため,通信の仕様自体もPython言語に親和性が高いようです.
チュートリアルを見ると,Pythonで書かれた場合と,C++で書かれた場合によってコードのスタイルが大きく異なります.Pythonの仕組みをC++に持ってくることはかなり面倒ですし,PythonはPythonなりに書ければいいんだというのは,Pythonプログラマの観点からは同意しますが,これから先,多くの,しかも玉石混交の後輩たちにROSを勧めるには二の足を踏む部分です.
特に僕のようなメカ系出身のロボット屋にROSに入りこませるのはかなりハードルが高いのでは,と思うのです.
OpenRTM-aistはPython版も提供していますが,こっちは逆にC++のRTCのコーディングに準拠した形になっていて,Python初心者でも見やすいです.
この辺で,プログラミングのモデル,コードの両方のレベルでOpenRTM-aist(RTミドルウエア)の方が持続性を感じるのです.未来に残るソフトウエアになる可能性を感じるのです.



