RtORBにおけるリモートオブジェクトのメッソド呼び出し
CORBAでは、リモートオブジェクトのメソッドを呼び出しは、idlファイルからidlコンパイラによって生成されるStubファイルに定義された関数を介して行われる。
RtORBでは、下記のようなCORBAオブジェクトの定義があると
interface Echo {
string echoString(in string mesg);
};
次のようなStubファイルが生成される。
CORBA_string
Echo_echoString(CORBA_Echo _obj, const CORBA_char * mesg, CORBA_Environment * ev)
{
CORBA_string _ORBIT_retval;
void *_args[1];
_args[0] = (void *)&mesg;
invokeMethod(_obj, &Echo__impl.method[0], (void **)&_ORBIT_retval, _args, ev);
return _ORBIT_retval;
}
これからわかるように、リモートオブジェクトのメソッド呼び出しは、 invokeMethod関数を呼び出すことで、実施される。
invokeMethod関数は、rtorb.cの中で定義されており、
void invokeMethod(CORBA_Object obj,
CORBA_Class_Method *method,
void **retval,
void **args,
CORBA_Environment *env);
のように定義されている。第1引数は、CORBAオブジェクトであり、第2引数は、呼び出すオブジェクトがローカルにあった場合に呼び出す関数である。第3引数と第4引数は、それぞれメソッドの返り値とメソッド呼び出しのための引数になる。最後の第5引数である CORBA_Environmentは、呼び出し時にエラー等は発生した場合に、エラーオブジェクトをストアするための変数である。
invokeMethod関数は、次のような動作を行う。
- エラーハンドラのためにCORBA_Environmentをクリアする
- 呼び出すオブジェクトがリモートなのかローカルなのかをチェック(CORBA_ORB_find_object関数をコール)
- リモートオブジェクトの場合 → invokeMethod_via_GIOP関数をコールし、リモートオブジェクトと通信する。
- ローカルオブジェクトの場合 →
- getValue関数でobject keyをもつオブジェクトをTableから呼び出す。
- 対象となるオブジェクトから、呼び出す実装関数を見つけて、その実装関数を実行させる。
上記のinvokeMethod_via_GIOP関数は、次のような動作を行う。
- make_client_connection関数を呼びGIOP_ConnectionHandlerを取得する。
- オブジェクトの _url[0].location_flagが真でない場合には、その場所にリモートオブジェクトが存在するかをconfirmLocation関数を呼び出して、確認する。
- リモート呼び出しに必要な引数を Marshal_Args関数を使って CDRの符号化する。
- createRequest関数を使って、GIOPリクエストを生成する。
- GIOP_ConnectionHandler_send関数を実行し、リモートオブジェクトにGIOPリクエストを送る。
- リモートオブジェクトからの返り値等が入るバッファを初期化する。
- リモートオブジェクトからの実行結果を receiveMessage関数で得る。このとき返事がくるまでブロックされることになる。
- actionReply関数により返ってきたメッセージに応じた処理をする。
- env->_major が CORBA_NO_EXCEPTION であれば、エラーがなかったので、 deMarshal_Arguments関数を呼び出して、リプライメッセージから引数と返り値を復号化する。
- env->_major が CORBA_USER_EXCEPTIONの場合には、エラー情報が返ってきているので、それを復号化する。
- 上記の処理で使用した、通信用バッファを開放する。

