[openrtm-users 00279] 動的な入出力ポートの変化について

9 posts / 0 new
Last post
root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00279] 動的な入出力ポートの変化について

中央大学の小島と申します。先日はご教授ありがとうございました。

現在、接続数が増加したときに、接続させるポート数を
増やしていけるようなサーバのような形態をとるモジュールを
作成するために、試行錯誤をしています。

Outportや、Inportを静的に変化させるには、C++の記述の仕方と同様に
ヘッダファイル内のpublic,protectedなどの部分において
TimedLong test;
InPort testOut;
とし、コンストラクタ内で、
testOut("test",test)
と付け加え、
registerOutPort("test",testOut);
と、することによって実現することはできました。

しかし、管理を簡単化するために配列等をつかって管理をしたいと思い行ってみたところ配列として宣言すると、初期化がうまくいきません。

実現したいコードの簡単な例としては、下記のようになります。

-----module.h-----

protected:
TimedLong m_in[2];
InPort m_inIn[2];

----module.cpp------

modele()
: ...
m_inIn[0]("in0",m_in[0]),
m_inIn[1]("in1",m_in[1]),
{
registerInPort("in0",m_inIn[0]);
registerInPort("in1",m_inIn[1]);
}

エラーには、
expected '{' before '[' token
expected unqualified-id before '[' token

と出ており配列による初期化時に、コンパイル時に解釈ができない用に思えます。

どのようにしたらエラーを回避可能かどうか、ご教授お願いいたします。

また、将来的には、動的にポート数を変更したいので
(vector型などを使い、自由に増やせるようにしたいと考えています)
こちらについても、何か方法などがございましたらお教え願います。

Undefined
root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00280] 動的な入出力ポートの変化について

産総研 安藤です

> 現在、接続数が増加したときに、接続させるポート数を
> 増やしていけるようなサーバのような形態をとるモジュールを
> 作成するために、試行錯誤をしています。
> 中略
> しかし、管理を簡単化するために配列等をつかって管理をしたいと思い行ってみたところ配列として宣言すると、初期化がうまくいきません。
>
> 実現したいコードの簡単な例としては、下記のようになります。
>
> -----module.h-----
>
> protected:
> TimedLong m_in[2];
> InPort m_inIn[2];
>
> ----module.cpp------
>
> modele()
> : ...
> m_inIn[0]("in0",m_in[0]),
> m_inIn[1]("in1",m_in[1]),

通常、初期化リストで配列を初期化することは出来ません。

> エラーには、
> expected '{' before '[' token
> expected unqualified-id before '[' token

ですので、このようなエラーが出ます。
データポートはコンストラクタにポート名と変数を与えなくてはいけないので、
メンバ変数の配列として持たせることは出来ません。

ポートを動的に変化させる方法を知りたいとのことでしたので、
以下のような方法はどうでしょうか?

以下は、SimpleIOサンプルのConsoleInCompに対して修正を加えて、
数値を入力するたびに、OutPortが一つ増えるというコードです。
(使いようがあるのかわからないですが)

[ConsoleIn.h]
ヘッダにて以下のように変数を宣言
std::vector m_outv;
std::vector* > m_outOutv;
int count; //ポートのインスタンス番号を管理するカウンタ

[ConsoleIn.cpp]
コンストラクタ
ConsoleIn::ConsoleIn(RTC::Manager* manager)
: RTC::DataFlowComponentBase(manager),
count(0), dummy(0)
{
countのみ初期化

onExecute()にて

RTC::ReturnCode_t ConsoleIn::onExecute(RTC::UniqueId ec_id)
{
// 入力を格納する一時変数
TimedLong out;

std::cout << "Please input number: ";
std::cin >> out.data;
std::cout << "Sending to subscriber: " << out.data << std::endl;

// OutPortにつける名前を作成
std::string out_name("out");
out_name += otos(count); // otos(): StringUtil.h

// 変数を一つ増やす
m_outv.push_back(out);
// OutPort を一つ増やす
m_outOutv.push_back(new OutPort(out_name.c_str(), m_outv.back()));
// OutPortを登録
registerOutPort(out_name.c_str(), *(m_outOutv.back()));

// 全部のOutPortから値を出力
for (int i(0), len(m_outv.size()); i < len; ++i)
{
m_outv[i] = out;
m_outOutv[i]->write();
}

++count; // カウンタを増やす。
return RTC::RTC_OK;
}

これで、動的にOutPortが増やせます。
ConsoleInでOutPortを増やしたときのRtcLinkの画像(笑)と、
このコードの完全版を添付します。
example/SimpleIOのしたにコピーして、コンパイルすれば動くはずです。

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00281] 動的な入出力ポートの変化について

中央大学の小島と申します。
非常に迅速な対応ありがとうございます。

> 通常、初期化リストで配列を初期化することは出来ません。
>
> > エラーには、
> > expected '{' before '[' token
> > expected unqualified-id before '[' token
>
> ですので、このようなエラーが出ます。
> データポートはコンストラクタにポート名と変数を与えなくてはいけないので、
> メンバ変数の配列として持たせることは出来ません。

わかりました。c++で配列の初期化はしたことがなかったのですが、
やはり無理矢理でしたか。
ただ、OutPortなどは宣言すると初期化をおこなわないとエラーがでてしまって
いたので、そのような手段にでていました。
むしろ、例のように初期化が行えるのですね。

> ポートを動的に変化させる方法を知りたいとのことでしたので、
> 以下のような方法はどうでしょうか?
(中略)
> これで、動的にOutPortが増やせます。
> ConsoleInでOutPortを増やしたときのRtcLinkの画像(笑)と、
> このコードの完全版を添付します。
> example/SimpleIOのしたにコピーして、コンパイルすれば動くはずです。

ありがとうございます。例は、まさに求めていたものです!!
この使い方を参考に進めていけそうです。ありがとうございました。

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00295] 動的な入出力ポートの変化について

中央大学の小島です。
先日は迅速な対応、及びサンプルをいただきありがとうございました。

安藤さんにいただいた、サンプルをさらに改良し、
デアクティブ時に動的にポートを削除するようなサンプルとしてみました。
(現在のところ私の環境で問題なく利用はできていますが、
問題ないコードかの確証はありませんので確認をお願いします)

利用される方がいらっしゃるかわかりませんが、利用される方がいらっしゃれば
ご自由にご利用ください。

また、ここからは要望となりますが、動的なポートを削除するにあたり、
deletePortByNameという関数を利用しましたが、registartInPortのように、
deleteInPortのような関数があると便利なのではないのでしょうか?

それともそれに対応するような関数があったのでしょうか?
deletePortが近いように思いますが、実現することはできませんでした。

ご検討よろしくお願いいたします。

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00296] 動的な入出力ポートの変化について

小島様

産総研 安藤です

お世話になっております。

> 中央大学の小島です。
> 先日は迅速な対応、及びサンプルをいただきありがとうございました。
>
> 安藤さんにいただいた、サンプルをさらに改良し、
> デアクティブ時に動的にポートを削除するようなサンプルとしてみました。
> (現在のところ私の環境で問題なく利用はできていますが、
> 問題ないコードかの確証はありませんので確認をお願いします)

コードを見せていただきましたが、特に問題ないようです。

> 利用される方がいらっしゃるかわかりませんが、利用される方がいらっしゃれば
> ご自由にご利用ください。
>
> また、ここからは要望となりますが、動的なポートを削除するにあたり、
> deletePortByNameという関数を利用しましたが、registartInPortのように、
> deleteInPortのような関数があると便利なのではないのでしょうか?

ご要望ありがとうございます。
次のバージョンではそういった関数を用意したいと思います。

>
> それともそれに対応するような関数があったのでしょうか?
> deletePortが近いように思いますが、実現することはできませんでした。

0.2.0のときはデータポートのオブジェクトを渡して削除する関数があったと思うのですが、
現在、データポートはポートのオブジェクトには直接触れないようになっているので、
deletePortでは削除できないはずです。

また、何か面白いテクニックなどをお考えになったら、
メーリングリストに投稿してみてください。

ありがとうございました。

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00309] 動的な入出力ポートの変化について

小島様

安藤です

> お世話になっております。
> 動的なポートで問題が2点おこり、質問があります。
>
> 1つめとしては、ポートが接続されている場合、
> ポートを削除することができなくなるようです。
> (現象からみると、deletePortByNameは実行されているが
> 実際には削除されていないようです)

削除されていないと判断された理由は何でしょう?
RtcLinkのアイコンでしょうか?

> クラスリファレンスを探しましたが、disconnect_all関数かと
> 思ったのですが、継承していないようで、利用することができませんでした。

データポートクラスは、ポートそのものではないので、disconnect_allは使えません。
以下のようにすれば、disconnect_allを呼ぶことはできると思います。

m_portAdmin.getPort("データポートのポート名").disconnect_all();

> それとも、これはバグでしょうか?何かアイデアがあればお願いします。

ちょっと調べてみます。

> 2つめとしては、動的なポートを接続し、データを送信したところデータが
> おかしくなります。
> 一度、ポートを削除し、もう一度作成すると、現在はたいていなおります。
> 何か考えられるような原因はありますでしょうか?

この辺も原因はわかりません。
これについても調査してみます。
そちらでも何かわかりましたらお知らせいただけませんか。

よろしくお願いいたします。

>
> <環境>
> OS: Fedora core 6 (kernel:2.6.18-1.2798)
> コンパイラ:gcc 4.1.1-30
> CORBA:omniORB 4.0.7
> ACE: ace 5.5.4
> OpenRTM-aist:OpenRTM-aist-0.4.1-RELEASE
>
> 以上2点、何か情報等ございましたらお願いいたします。
>

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00310] 動的な入出力ポートの変化について

中央大学の小島です。

お世話になっております。

> > 動的なポートで問題が2点おこり、質問があります。
> >
> > 1つめとしては、ポートが接続されている場合、
> > ポートを削除することができなくなるようです。
> > (現象からみると、deletePortByNameは実行されているが
> > 実際には削除されていないようです)
>
> 削除されていないと判断された理由は何でしょう?
> RtcLinkのアイコンでしょうか?

そうですね、アイコンで判断してしまおります。
もしかして切断されてるのでしょうか?

しかし、何も接続されていなかったポートに関しては、
RtcLink上では問題なく消えますので、なんとなく納得がいかない感じがしました。

また、この問題は毎回おこるわけではなく、
起こる場合と起こらない場合があり、その境目もよくわかりませんが、
少なくとも接続されていたポートのみにおこっています。

そのときには、複数のポートが接続されているときによくおこることから、
切断がうまくいかず、登録の削除がうまくいってないのではと推測いたしました。

> > クラスリファレンスを探しましたが、disconnect_all関数かと
> > 思ったのですが、継承していないようで、利用することができませんでした。
>
> データポートクラスは、ポートそのものではないので、disconnect_allは使えません。
> 以下のようにすれば、disconnect_allを呼ぶことはできると思います。
m_portAdmin.getPort("データポートのポート名").disconnect_all();

ありがとうございます。試してみます。

> > それとも、これはバグでしょうか?何かアイデアがあればお願いします。
>
> ちょっと調べてみます。
>
> > 2つめとしては、動的なポートを接続し、データを送信したところデータが
> > おかしくなります。
> > 一度、ポートを削除し、もう一度作成すると、現在はたいていなおります。
> > 何か考えられるような原因はありますでしょうか?
>
> この辺も原因はわかりません。
> これについても調査してみます。
> そちらでも何かわかりましたらお知らせいただけませんか。
>
> よろしくお願いいたします。

承知いたしました。
こちらでも、何かわかりましたらご連絡差し上げようと思います。

> > <環境>
> > OS: Fedora core 6 (kernel:2.6.18-1.2798)
> > コンパイラ:gcc 4.1.1-30
> > CORBA:omniORB 4.0.7
> > ACE: ace 5.5.4
> > OpenRTM-aist:OpenRTM-aist-0.4.1-RELEASE
> >
> > 以上2点、何か情報等ございましたらお願いいたします。
> >

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00323] 動的な入出力ポートの変化について

中央大学の小島です。
いつもお世話になっております。

先日の、送信したデータがおかしくなることの原因がおそらくわかりました。

07/12/10 に Takashi Kojima さんは書きました:
> 中央大学の小島です。
>
> お世話になっております。
>
> > > 動的なポートで問題が2点おこり、質問があります。
> > >
> > > 1つめとしては、ポートが接続されている場合、
> > > ポートを削除することができなくなるようです。
> > > (現象からみると、deletePortByNameは実行されているが
> > > 実際には削除されていないようです)
> >
> > 削除されていないと判断された理由は何でしょう?
> > RtcLinkのアイコンでしょうか?
>
> そうですね、アイコンで判断してしまおります。
> もしかして切断されてるのでしょうか?
>
> しかし、何も接続されていなかったポートに関しては、
> RtcLink上では問題なく消えますので、なんとなく納得がいかない感じがしました。
>
> また、この問題は毎回おこるわけではなく、
> 起こる場合と起こらない場合があり、その境目もよくわかりませんが、
> 少なくとも接続されていたポートのみにおこっています。
>
> そのときには、複数のポートが接続されているときによくおこることから、
> 切断がうまくいかず、登録の削除がうまくいってないのではと推測いたしました。
>
>
> > > クラスリファレンスを探しましたが、disconnect_all関数かと
> > > 思ったのですが、継承していないようで、利用することができませんでした。
> >
> > データポートクラスは、ポートそのものではないので、disconnect_allは使えません。
> > 以下のようにすれば、disconnect_allを呼ぶことはできると思います。
> m_portAdmin.getPort("データポートのポート名").disconnect_all();
>
> ありがとうございます。試してみます。
>
> > > それとも、これはバグでしょうか?何かアイデアがあればお願いします。
> >
> > ちょっと調べてみます。
> >
> > > 2つめとしては、動的なポートを接続し、データを送信したところデータが
> > > おかしくなります。
> > > 一度、ポートを削除し、もう一度作成すると、現在はたいていなおります。
> > > 何か考えられるような原因はありますでしょうか?
> >
> > この辺も原因はわかりません。
> > これについても調査してみます。
> > そちらでも何かわかりましたらお知らせいただけませんか。
> >
> > よろしくお願いいたします。
>
> 承知いたしました。
> こちらでも、何かわかりましたらご連絡差し上げようと思います。
>

原因としましては、vector型を用いたポートにバインドする変数の動的追加が
原因だと考えられます。

vector型はあらかじめ容量を確保している領域が足りなくなると、
そのメモリの内容をコピーして、別の場所に確保するという性質が
あることを思い出しました。

すなわち、ポートが持っている先のアドレスは、push_backされたことにより
そこにはかつてあったが、全く関係ない場所に、取り残されていると考えられます。

そこで、起こっていた現象を詳しく調べてみると
「一度目のポートの動的追加ではデータがおかしい」
「二度目にポートを増やすと正しいデータ」
「データがおかしいくなるのは、決まって前に増やしたポート群(3個増やすと1,2個目)」
という現象でした。
初めて動的変化を行ったときには、領域が確保されていませんが、
2度目では1度目で、領域が確保されているため別領域にメモリを確保するという現象がおこらなくてすみ、
正しいデータになるのではないかと考えられます。

しっかりとした確認はできておりませんが、サービスポートで同じようなことを
していたときに、セグメンテーション違反等のエラーが発生していたのですが、解決できたので、おそらく、こちらも同様のことが原因だと思います。
(論理的には間違っていないとは思うのですが、もし違っていたらすいません)

>
> > > <環境>
> > > OS: Fedora core 6 (kernel:2.6.18-1.2798)
> > > コンパイラ:gcc 4.1.1-30
> > > CORBA:omniORB 4.0.7
> > > ACE: ace 5.5.4
> > > OpenRTM-aist:OpenRTM-aist-0.4.1-RELEASE
> > >
> > > 以上2点、何か情報等ございましたらお願いいたします。
> > >

root
Offline
Last seen: 2 days 18 hours ago
Joined: 2009-06-23 14:31
[openrtm-users 00326] 動的な入出力ポートの変化について

小島様

安藤です

情報ありがとうございました。

では、vectorに変数のポインタを格納するようにすればどうでしょうか?

あるいは、本質的解決ではありませんが、データポートへの/からの読み書きの際に、
データポートにバインドした変数経由ではなくデータポートにたいして
直接読み書きしてはどうでしょう?

> 先日の、送信したデータがおかしくなることの原因がおそらくわかりました。
>
> 07/12/10 に Takashi Kojima さんは書きました:
> > 中央大学の小島です。
> >
> > お世話になっております。
> >
> > > > 動的なポートで問題が2点おこり、質問があります。
> > > >
> > > > 1つめとしては、ポートが接続されている場合、
> > > > ポートを削除することができなくなるようです。
> > > > (現象からみると、deletePortByNameは実行されているが
> > > > 実際には削除されていないようです)
> > >
> > > 削除されていないと判断された理由は何でしょう?
> > > RtcLinkのアイコンでしょうか?
> >
> > そうですね、アイコンで判断してしまおります。
> > もしかして切断されてるのでしょうか?
> >
> > しかし、何も接続されていなかったポートに関しては、
> > RtcLink上では問題なく消えますので、なんとなく納得がいかない感じがしました。
> >
> > また、この問題は毎回おこるわけではなく、
> > 起こる場合と起こらない場合があり、その境目もよくわかりませんが、
> > 少なくとも接続されていたポートのみにおこっています。
> >
> > そのときには、複数のポートが接続されているときによくおこることから、
> > 切断がうまくいかず、登録の削除がうまくいってないのではと推測いたしました。
> >
> >
> > > > クラスリファレンスを探しましたが、disconnect_all関数かと
> > > > 思ったのですが、継承していないようで、利用することができませんでした。
> > >
> > > データポートクラスは、ポートそのものではないので、disconnect_allは使えません。
> > > 以下のようにすれば、disconnect_allを呼ぶことはできると思います。
> > m_portAdmin.getPort("データポートのポート名").disconnect_all();
> >
> > ありがとうございます。試してみます。
> >
> > > > それとも、これはバグでしょうか?何かアイデアがあればお願いします。
> > >
> > > ちょっと調べてみます。
> > >
> > > > 2つめとしては、動的なポートを接続し、データを送信したところデータが
> > > > おかしくなります。
> > > > 一度、ポートを削除し、もう一度作成すると、現在はたいていなおります。
> > > > 何か考えられるような原因はありますでしょうか?
> > >
> > > この辺も原因はわかりません。
> > > これについても調査してみます。
> > > そちらでも何かわかりましたらお知らせいただけませんか。
> > >
> > > よろしくお願いいたします。
> >
> > 承知いたしました。
> > こちらでも、何かわかりましたらご連絡差し上げようと思います。
> >
>
> 原因としましては、vector型を用いたポートにバインドする変数の動的追加が
> 原因だと考えられます。
>
> vector型はあらかじめ容量を確保している領域が足りなくなると、
> そのメモリの内容をコピーして、別の場所に確保するという性質が
> あることを思い出しました。
>
> すなわち、ポートが持っている先のアドレスは、push_backされたことにより
> そこにはかつてあったが、全く関係ない場所に、取り残されていると考えられます。
>
> そこで、起こっていた現象を詳しく調べてみると
> 「一度目のポートの動的追加ではデータがおかしい」
> 「二度目にポートを増やすと正しいデータ」
> 「データがおかしいくなるのは、決まって前に増やしたポート群(3個増やすと1,2個目)」
> という現象でした。
> 初めて動的変化を行ったときには、領域が確保されていませんが、
> 2度目では1度目で、領域が確保されているため別領域にメモリを確保するという現象がおこらなくてすみ、
> 正しいデータになるのではないかと考えられます。
>
> しっかりとした確認はできておりませんが、サービスポートで同じようなことを
> していたときに、セグメンテーション違反等のエラーが発生していたのですが、解決できたので、おそらく、こちらも同様のことが原因だと思います。
> (論理的には間違っていないとは思うのですが、もし違っていたらすいません)
>
> >
> > > > <環境>
> > > > OS: Fedora core 6 (kernel:2.6.18-1.2798)
> > > > コンパイラ:gcc 4.1.1-30
> > > > CORBA:omniORB 4.0.7
> > > > ACE: ace 5.5.4
> > > > OpenRTM-aist:OpenRTM-aist-0.4.1-RELEASE
> > > >
> > > > 以上2点、何か情報等ございましたらお願いいたします。
> > > >

Log in or register to post comments

Download

latest Releases : 2.0.0-RELESE

2.0.0-RELESE Download page

Number of Projects

Choreonoid

Motion editor/Dynamics simulator

OpenHRP3

Dynamics simulator

OpenRTP

Integrated Development Platform

AIST RTC collection

RT-Components collection by AIST

TORK

Tokyo Opensource Robotics Association

DAQ-Middleware

Middleware for DAQ (Data Aquisition) by KEK