[openrtm-users 00307] Re: サービスポートで非同期呼出し

Ando Noriaki n-ando @ aist.go.jp
2007年 12月 7日 (金) 09:00:33 JST


千代様

安藤です

> 安藤様
>
> 慶応義塾大学の千代です。
>
> > コンポーネントのメンバ変数を操作したいということでしょうか?
> > コンストラクタなり、他のメンバ関数を作成するなどすれば、
> > アクセスできるのではないでしょうか?
> この実装についてですが、先程のサンプルを例にすると、
>
> - MyServiceProviderクラスはMyServiceSVC_implクラス変数を所持
> - MyServiceSVC_implクラスはdo関数を所持
>
> という前提で、do関数の中から、MyServiceProviderクラスの
> メンバ変数(Ex. コンフィグパラメータ)を操作したいと考えています。
> 実装としては、MyServiceSVC_implクラスにポインタ変数を定義して、
> MyServiceProviderクラスのコンストラクタでMyServiceSVC_implクラスの
> ポインタ変数にMyServiceProviderクラスのメンバ変数のアドレスを
> 代入するということでしょうか。
>
> ソースコードとしては、(必要がないところは省略)
>
> MyServiceSVC_impl {
>                                                                                                                                                int *x;
>                                                                                                                                                void _cxx_do();
> };
>
> MyServiceProvider {
>                                                                                                                                                int m_x;
>                                                                                                                                                MyServiceSVC_impl m_myservice0;
> };
>
> MyServiceProvider::MyServiceProvicer(RTC::Manager* manager)
> {
>                                                                m_myservice0.x = &m_x;
> }
>
> ということでしょうか。

そうですね。私が考えていたのは、おおよそこういう方法です。
この方法で千代さんがやりたいことは実現できますでしょうか?

> > やりたいことのイメージがつかめないので、はずしているかもしれません。
> 私の説明不足で申し訳ありません。
>
> コンポーネント間での分散処理と、スケジューリング機構を
> 実装したいと考えています。
>
> (タスク1の優先度) < (タスク2の優先度)とすると、
>
> 1) あるコンポーネントで、タスク1が実行中の場合でサービスポートで
> do関数が呼び出された場合(タスク2)、タスク1の実行を中断して
> タスク2を実行する。

これは、ちょっと面倒ですね。
というのも、(タスク2)do関数はCORBAのスレッドから呼ばれるので、
優先度を設定するには、do関数内でart_enterを呼ぶしか方法がありません。
art_enterが呼ばれるまでは、あるいはdo関数に到達するまでは
ARTのタスクではありませんので、タスク1の優先度の方が高いことになる
のではないでしょうか?

ARTタスクと非ARTタスクがある場合の優先度はどのように扱われるのか
詳しく知らないのですが、どなたかご存知の方いらっしゃいませんか?
>清水さんわかります?

常に、 (ARTタスクの優先度) > (非ARTタスクの優先度) という前提ですと、
タスク1の周期が非常に短かければ、タスク2にすぐにCPU時間が与えられるので、
こういう方法でもあまり気にならないかもしれませんが、
タスク1の周期が非常に長い場合、タスク2にCPU時間が与えられるまでは、
(タスク1の優先度) > (タスク2の優先度)
になってしまうので、期待する結果が得られないと思われます。


> 2) サービスの呼び出し元のコンポーネントではなく、
> 他のコンポーネントのdo関数をイベント駆動で呼び出す。
>
> 具体的な呼び出し手順例は下記のようになります。
> Comp0->do() (Req)-> Comp1->do() (Req)-> Comp2->done()
>    (CallBack)-> Comp1->done() (CallBack)-> Comp0
>
> Comp: Component
> Req: Request

これは、上記のような方法で、Comp0のimplクラスに、MyServiceのCorbaConsumer
変数の参照なりポインタを持たせ、Comp1のMyServiceと接続してやれば、
Comp0からComp1のdo()関数を呼ぶことは出来ますね。

> このような機構を、ART-Linuxで優先度を付けることによって実装したいと
> 考えています。
>
> よろしくお願いします。
>
>
>  "Ando Noriaki" <n-ando @ aist.go.jp> wrote:
> / ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄
> > 千代様
> >
> > 産総研 安藤です
> >
> > > 安藤様
> > >
> > > 慶応義塾大学の千代です。
> > > いつもお世話になっております。
> > >
> > > 質問への返答やサンプルを作成していただき、ありがとうございます。
> > >
> > > サンプルを読んで動かすことで、どのようにサービスポートで
> > > 非同期で関数呼出しをするかを理解できました。
> > > しかし、他の部分でいくつか質問があります。
> > >
> > > このサンプルを例にすると、do関数でそのサービスポートを所有している
> > > オブジェクトのメンバ変数を操作することはできるのでしょうか。
> >
> > コンポーネントのメンバ変数を操作したいということでしょうか?
> > コンストラクタなり、他のメンバ関数を作成するなどすれば、
> > アクセスできるのではないでしょうか?
> >
> > > また、do関数からシグナルを送信する等をすることで、
> > > 実行中のコンテキストをreturn文を待たずに状態遷移
> > > (Ex. onExecute -> onAbort)させるか、
> > > もしくは例外を発生させることはできるのでしょうか。
> >
> > 具体的にどのようになさりたいのかイメージがつかめないのですが、
> > Active状態(onExecuteなど)から他の状態に遷移するには、
> > onExecuteから必ずreturnしなければなりません。
> > もし、onAbortを実行しERROR状態に移行したければ、
> > return RTC::RTC_ERROR;
> > を返せば可能です。
> >
> > > つまり、do関数が呼び出されたら、実行中のコンテキストに
> > > イベントを送ることで、決められた操作を即座に実行する。
> > > その後に元のイベントを受け取る前の動作に戻る、もしくは他の状態に
> > > 遷移したいと考えています。
> >
> > ただし、コンポーネントの状態遷移は、あくまでコンポーネントとしての
> > 状態遷移ですので、ご自分で作られるロジックで幾つかの状態を取る必要が
> > あるのであれば、そのロジック内で状態を管理するのが正しい方法ですね。
> >
> > やりたいことのイメージがつかめないので、はずしているかもしれません。
> > もう少し詳しく説明していただければ、何らかの回答をすることも出来るかもしれません。
> > 宜しくお願いいたします。
> >
> > >
> > > よろしくお願いします。
> > >
> > >
> > >  "Ando Noriaki" <n-ando @ aist.go.jp> wrote:
> > > / ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄
> > > > 千代様
> > > >
> > > > 産総研 安藤です
> > > >
> > > > ためしに、サンプルを作成してみましたのでお送りいたします。
> > > >
> > > > MyServiceProviderCompとMyServiceConsumerCompを起動して、
> > > > ポート同士を接続して、その後両者をActivateしてください。
> > > >
> > > > MyServiceConsumerCompの方で、
> > > > do? (push any key and enter)
> > > > と出ますので、適当な文字とenterを押してください。
> > > > Provider側への呼び出しはすぐにもどって、MyServiceProviderCompの方では、
> > > > 1秒間隔で、
> > > >
> > > > processing
> > > >
> > > > と10回出ます。
> > > > その後、MyServiceProviderCompの方でdoneと表示されると同時に、
> > > > MyServiceConsumerCompの方でもdoneと表示されます。
> > > >
> > > > 参考にしてみてください。
> > > >
> > > > 07/12/01 に Ando Noriaki<n-ando @ aist.go.jp> さんは書きました:
> > > > > 千代様
> > > > >
> > > > > 産総研 安藤です
> > > > >
> > > > > > 慶応義塾大学の千代と申します。
> > > > > >
> > > > > > Service Portを用いて非同期でリモートオブジェクトの呼出しを
> > > > > > したいと考えています。
> > > > > >
> > > > > > 具体的には、Service Portから非同期でリモートオブジェクトの関数を
> > > > > > 呼出して、その処理が終わったらイベントをPushする。
> > > > > >
> > > > > > 呼出元がイベントを受け取ったら、呼出元のオブジェクトで
> > > > > > あらかじめ登録しておいたイベントハンドラの関数を
> > > > > > 実行するというような手順を考えています。
> > > > > >
> > > > > > 戻り値の書き込みはデータポートのようにコールバックオブジェクトで
> > > > > > OnWriteConvert関数を利用するような形で実装することを考えています。
> > > > > >
> > > > > > Service Portで非同期呼出しをするにはどのように実装すれば
> > > > > > よいのでしょうか。
> > > > >
> > > > > 現在のOpenRTMではそのようなことを行う標準的な方法はありません。
> > > > > しかしながら、サービスポートをうまく使えば、おっしゃるようなことは実現可能です。
> > > > > まず、前提として、一つのポートにはプロバイダインターフェースとコンシューマ
> > > > > インターフェースを任意の数だけ持たせることが可能です。
> > > > >
> > > > > あるサービスポートののプロバイダ側で、
> > > > >
> > > > > interface MyService
> > > > > {
> > > > >  oneway void do();
> > > > > };
> > > > >
> > > > > という、サービスプロバイダを持たせ、かつ同じポートに、
> > > > >
> > > > > interface Callback
> > > > > {
> > > > >  void done();
> > > > > };
> > > > >
> > > > > のような、コンシューマを持たせます。
> > > > >
> > > > > サービスコンシューマの方は、これと逆にプロバイダとコンシューマを持たせます。
> > > > > つまり、
> > > > > - MyService のコンシューマ
> > > > > - Callbackのプロバイダ
> > > > > を持つことになります。
> > > > > これらのプロバイダとコンシューマはポートを接続することにより相互に接続されます。
> > > > >
> > > > > MyServiceのプロバイダ側では、do()の処理が終わったら、
> > > > > そのコンシューマのdone()を呼んでやることで、呼び出し側に
> > > > > 処理が終わったことを知らせることが可能です。
> > > > >
> > > > > このような方法でどうでしょうか?
> > > > > --
> > > > > 安藤慶昭@独立行政法人産業技術総合研究所 研究員
> > > > >                   知能システム研究部門 タスクインテリジェンス研究グループ
> > > > >                   〒305-8568 茨城県つくば市梅園1-1-1 中央第2
> > > > >                   TEL: 029-861-5981 FAX: 029-861-5971
> > > > >                   n-ando @ aist.go.jp, n-ando @ ieee.org
> > > > >
> > > >
> > > >
> > > > --
> > > > 安藤慶昭@独立行政法人産業技術総合研究所 研究員
> > > >                    知能システム研究部門 タスクインテリジェンス研究グループ
> > > >                    〒305-8568 茨城県つくば市梅園1-1-1 中央第2
> > > >                    TEL: 029-861-5981 FAX: 029-861-5971
> > > >                    n-ando @ aist.go.jp, n-ando @ ieee.org
> > >
> > > ---------------------------------------------------
> > > Hiroyuki Chishiro <chishiro @ ny.ics.keio.ac.jp>
> > > Keio University
> > > ---------------------------------------------------
> > >
> >
> >
> > --
> > 安藤慶昭@独立行政法人産業技術総合研究所 研究員
> >                    知能システム研究部門 タスクインテリジェンス研究グループ
> >                    〒305-8568 茨城県つくば市梅園1-1-1 中央第2
> >                    TEL: 029-861-5981 FAX: 029-861-5971
> >                    n-ando @ aist.go.jp, n-ando @ ieee.org
> >
> >
>
> ---------------------------------------------------
> Hiroyuki Chishiro <chishiro @ ny.ics.keio.ac.jp>
> Keio University
> ---------------------------------------------------
>
>


-- 
安藤慶昭@独立行政法人産業技術総合研究所 研究員
                   知能システム研究部門 タスクインテリジェンス研究グループ
                   〒305-8568 茨城県つくば市梅園1-1-1 中央第2
                   TEL: 029-861-5981 FAX: 029-861-5971
                   n-ando @ aist.go.jp, n-ando @ ieee.org



openrtm-users メーリングリストの案内