![]() ![]() ![]() | 投稿するにはまず登録を |
スレッド表示 | 新しいものから | 前のトピック | 次のトピック | 下へ |
投稿者 | スレッド |
---|---|
C2913 | 投稿日時: 2013/6/24 15:39 |
新米 ![]() ![]() 登録日: 2013/6/24 居住地: 投稿: 3 |
PHY_SetTransmissionChannelの使い方について 現在,マルチチャネルMACを作ろうと思っています.
具体的には,RTS/CTS交換のあとにDATA送信チャネルを切り替えようとしているのですが,エラーは出ないものの,実際に切り替え後のチャネルでパケットが送信されません. 具体的には,mac_dot11.cppのMacDot11ProcessMyFrame( )において,CTS受信直後の処理として,DATA送信直前に以下のように追加しました. MacDot11StationTransmitDataFrame(node, dot11);の呼び出し後も複数の関数呼び出し処理を確認し,Phy802_11StartTransmittingSignal()まで呼び出されていることを確認しましたが.どうやらその直後でシミュレータが止まってしまっているようです. 何が原因なのか,全く分かりません. お分かりの方がおられましたら,教えてくださいませんでしょうか.よろしくお願いいたします. 【MacDot11ProcessMyFrame( )内の追加部分】 switch (hdr->frameType) { case DOT11_CTS: { (省略) int Specified = 1; //DATA送信用のチャネル番号 //まずは,指定チャネルをリスニング状態にする.■ if( PHY_CanListenToChannel( node, dot11->myMacData->interfaceIndex, Specified) && !PHY_IsListeningToChannel( node, dot11->myMacData->interfaceIndex, Specified) ){ //指定チャネルがlistenableでありかつ,現在listeningじゃなければ,listeningにする. PHY_StartListeningToChannel( node, dot11->myMacData->interfaceIndex, Specified); } int NowTxch; PHY_GetTransmissionChannel( node, dot11->myMacData->interfaceIndex, &NowTxch); printf("NowTxch:%d, sltch:%d\n", NowTxch, Specified); //指定チャネルを送信チャネルにしていなければ,送信チャネルにする. if( NowTxch != Specified){ PHY_SetTransmissionChannel( node, dot11->myMacData->interfaceIndex, Specified); printf("NowTxch:%d, sltch:%d\n", NowTxch, Specified); } MacDot11StationTransmitDataFrame(node, dot11); |
hiro | 投稿日時: 2013/6/30 16:28 |
長老 ![]() ![]() 登録日: 2005/7/16 居住地: 投稿: 452 |
Re: PHY_SetTransmissionChannelの使い方について 申し訳ないですが、情報が少なくて、よくわからないです。
『シミュレータが止まって』 というのは、具体的にどのような状況なのかもう少し詳しい説明が欲しいです。 それから、再現可能な最小限のシナリオが欲しいです。 1)『int Specified = 1; //DATA送信用のチャネル番号』 という事は、チャネルは1番に固定という事ですね。 2)『Phy802_11StartTransmittingSignal()まで呼び出されていることを確認しました』 呼び出されるとすぐに StartTransmittingSignal()を呼び出しますが、呼び出されていますか。 3)呼び出されている場合、 StartTransmittingSignalのどこで『シミュレータが止まって』しまいますか。 |
C2913 | 投稿日時: 2013/7/1 21:34 |
新米 ![]() ![]() 登録日: 2013/6/24 居住地: 投稿: 3 |
Re: PHY_SetTransmissionChannelの使い方について ※改変したコードを添付させていただきました.
Hiro様,ご返信くださいまして誠にありがとうございました. また,情報が少なすぎ大変失礼いたしました. #お力になって頂けますと,非常に助かります.ご助言くださいますよう #お願い申し上げます. 実装しようと思っていますは,RTS-CTS-DATA-ACKを通常,同じチャネルで送受信するMACを変更し,DATA-ACKをRTS-CTSとは別チャネルで送信するMACです. 全てのチャネルは全チャネルをListenableに,ただし,ListeningとTransmittingのチャネルを0にしておきます.(Transmittingは設定せずとも,最も若いListening Channelが設定されるようですが.) さて,まず,送信端末はチャネル0でRTSを送信します.そのとき,RTSには,MESSAGE_AddInfoによって,int型の整数を入れます.(xとします.) その整数は,Listenableな複数のChannel番号からランダムに1を 選んでいます. 受信端末はRTS受信後に,その中から整数xをMESSAGE_ReturnInfoで取り出します. (もちろん,printfにて正しく取り出していることを確認済みです.) 受信端末はその後,CTS返信を行いますが,その完了後に,チャネルxがListeningでなければ,まずStartListeningします. #併せて,xをPHY_setTransmissionchannelしますが,しなくてもエラー終了の状態は変わりません. CTSを受信完了した送信端末は,xをstartlisteningし,次にxをSetTransmissionchannelし,DATAの送信を開始します. その後,Qualnetは停止します(詳細はもう少し下で書かせて頂きます). つまり,送受信端末はどちらも,CTS返信完了後,CTS受信完了後に共に,同じチャネルをListening,SetTransmissionChannelすると停止してしまうという具合です. ただし,おかしなことに,どちらか一方のみが,チャネルxにListening,Transmissionchannelに移動しただけでは,Qualnetは停止しません.(当然,相手端末は反応してくれなくなりますが,何度も,繰り返し相手端末に問い合わせる送信を返事も無いまま繰り返しますが,設定したシミュレーション時間終了まで実行できます.) どこもエラーは出ずにいきなりシミュレータが止まるので,コードが公開されていないPhy部分のエラーだと思い,バージョンも,5.2,6.1と変えてみましたが,上記の動作は全く同じです. さて,チャネル変更後に動作を確認した関数呼び出しは以下の通りです. #全て呼び出しの前後でprintfを挿入し呼び出し,復帰を確認しています. #また,併せてgetsimtime(node)でメッセージのシミュレーション時間に矛盾が #無いことも確認しています. 1)チャネル変更後にDATA送信前に送信端末が,MacDot11ProcessMyFrame()の中で, MacDot11StationTransmitDataFrame()を呼ぶ. 2) MacDot11StationStartTransmittingPacketが呼ばれる. 3)PHY_StartTransmittingSignalが呼ばれる. 4)Phy802_11StartTransmittingSignalが呼ばれる ここまで追えたのですが,ここから先はコードが提供されておらず,追えていません. 送受信同時に同じチャネルに遷移せずにどちらか一方のみの遷移では問題なく動作する というのも,合点がいかず困惑しております. なお,現在は送受信端末2台のみで動かしていますので,余計な干渉は周辺から 飛んで来ていないと思います. 何か,お気づきの点がございましたら,どうぞ,ご教示くださいますようお願い申し上げます. ![]() |
hiro | 投稿日時: 2013/7/2 11:24 |
長老 ![]() ![]() 登録日: 2005/7/16 居住地: 投稿: 452 |
Re: PHY_SetTransmissionChannelの使い方について 第3者の立場で現象を確認することしかできないので、
QualNetで何が起きているのか(何故終了しているのか)を まず確認しようと思っています。以下3点、お願いします。 1) 確認用のシナリオを下さい。 2) QualNetのバージョンは5.2ですか? 3) CH_NUM_INFO が未定義ですが、 ./include/message.hのMessageInfoTypeに 追加したという理解で良いですか。 |
C2913 | 投稿日時: 2013/7/2 11:40 |
新米 ![]() ![]() 登録日: 2013/6/24 居住地: 投稿: 3 |
Re: PHY_SetTransmissionChannelの使い方について ご返信大変ありがとうございます.また,何度も疑問点の残る書き方で済みませんでした.
1)シナリオを添付いたしました. 2)先ほどのソースは5.2です. 3)CH_NUM_INFOのメッセージはMessageInforTypeに定義しました. 大変にお手数を御かけいたしますが,どうぞ,よろしくお願い申し上げます. ![]() |
hiro | 投稿日時: 2013/7/2 16:12 |
長老 ![]() ![]() 登録日: 2005/7/16 居住地: 投稿: 452 |
Re: PHY_SetTransmissionChannelの使い方について 具体的に実装したい内容とは別に、
QualNetが異常終了する原因とその見かけ上の対処です。 見かけ上と言うのはソースコードを修正せずに、 シナリオ設定で回避しているからです。 ソースコードの妥当性は確認していません。 ちょっと長いので、じっくり読んでください。 なお、Linux環境を前提としています。 ./snt/qualnet/5.2/main/Makefile の以下の部分を修正して下さい。 旧 #DEBUG = -g OPT = -O3 新 DEBUG = -ggdb OPT = -O0 この設定でgdbが使えるようになります。 gdbがインストールされていなければ、使用しているLinuxの ディストリビューション手順に従いインストールして下さい。 make clean で一旦全てのオブジェクトを削除します。 make all でQualNetを作り直します。 シナリオフォルダに移動して、 gdb ~/snt/qualnet/5.2/bin/qualnet としてgdbを起動します。 gdbが起動すると、プロンプトが(gdb) になるので、 (gdb) run testByc2913.config でQualNetを実行します。 すると、以下の表示が出てQualNetの実行が止まるはずです。 qualnet: ../addons/kernel/phy_private.cpp:170: void PHY_StartListeningToChannel(Node*, int, int): Assertion `node->phyData[phyIndex]->channelListenable[channelIndex] == (1)' failed. Program received signal SIGABRT, Aborted. これは、QualNet内部で異常を検出してQualNetが中断したことを示します。 ちなみに、Makefileを変更しない状態で実行しても、下記の表示でQualNetが 止まりませんでしたか? qualnet: ../addons/kernel/phy_private.cpp:170: void PHY_StartListeningToChannel(Node*, int, int): Assertion `node->phyData[phyIndex]->channelListenable[channelIndex] == (1)' failed. アボート (coreを出力しました) 実は、最初に確認したかったのは、どのようにQualNetが終了したのか、でした。 上記のAssertionメッセージを最初に教えて頂くだけで、かなり手間が省けました。 このメッセージが表示されるという事は、 node->phyData[phyIndex]->channelListenable[channelIndex] の値が1ではない、という事です。 さて、(gdb) に戻ります。 where とコマンドを入力すると、以下のような表示になるはずです。 具体的な数値は若干異なると思います。 (gdb) where #0 0x0000003d77635935 in raise () from /lib64/libc.so.6 #1 0x0000003d776370e8 in abort () from /lib64/libc.so.6 #2 0x0000003d7762e6a2 in __assert_fail_base () from /lib64/libc.so.6 #3 0x0000003d7762e752 in __assert_fail () from /lib64/libc.so.6 #4 0x0000000000b5b529 in PHY_StartListeningToChannel(Node*, int, int) () #5 0x000000000092d8a7 in MacDot11ProcessMyFrame (node=0x129b0f0, dot11=0x12bf0d0, msg=0x1301d90) at ../libraries/wireless/src/mac_dot11.cpp:1478 #6 0x000000000092e8f9 in MacDot11ReceivePacketFromPhy (node=0x129b0f0, dot11=0x12bf0d0, msg=0x1301d90) at ../libraries/wireless/src/mac_dot11.cpp:1978 #7 0x00000000004a7a2a in MAC_ReceivePacketFromPhy (node=0x129b0f0, interfaceIndex=0, packet=0x1301d90, phyNum=0) at ../main/mac.cpp:7622 #8 0x0000000000a42776 in Phy802_11SignalEndFromChannel (node=0x129b0f0, phyIndex=0, channelIndex=0, propRxInfo=0x1304aa0) at ../libraries/wireless/src/phy_802_11.cpp:1588 #9 0x0000000000a285ac in PHY_SignalEndFromChannel (node=0x129b0f0, phyIndex=0, channelIndex=0, propRxInfo=0x1304aa0) at ../libraries/wireless/src/phy.cpp:2919 #10 0x0000000000b5f6ae in PROP_ProcessEvent(Node*, Message*) () #11 0x000000000047d482 in NODE_ProcessEvent (node=0x129b0f0, msg=0x12d2790) at ../main/node.cpp:276 #12 0x0000000000b4e839 in PARTITION_RunPartition(PartitionData*) () #13 0x0000000000b4ecfa in PARTITION_ProcessPartition(PartitionData*) () #14 0x0000000000b91cec in main () (gdb) これを見ると、#5 の部分で、 ../libraries/wireless/src/mac_dot11.cppファイルの1478行目で PHY_StartListeningToChannel関数を呼び出し、その関数から __assert_fail が呼び出されていることがわかります。 PHY_StartListeningToChannelの呼び出し部分は、 PHY_StartListeningToChannel( node, dot11->myMacData->interfaceIndex, dot11->sltch); なので、引数の値が正しくない、と推察されます。 なお、PHY_StartListeningToChannelの引数は、 ./include/phy.h によれば、 // API :: PHY_StopListeningToChannel // LAYER :: Physical // PURPOSE :: // PARAMETERS :: // + node : Node* : Node that is being // instantiated in // + phyIndex : int : interface number // + channelIndex : int : channel index // RETURN :: void : です。 ここで、以下の2つの値を確認します。ついでにnode->nodeIdの値も。 dot11->myMacData->interfaceIndex dot11->sltch gdbで止めても良いのですが、場所が特定できているので デバッグログを入れて確認すると、 node-nodeId は 1 dot11->myMacData->interfaceIndex は 0 dot11->sltch は 2 でした。 シナリオを見ると、nodeは2つ、interfaceは1つですが、 channelが1つしか定義されていません。 という事で3番目の引数(channel index)の値が正しくないことになります。 channel indexは0から開始するので、2 と指定するためには、 3チャネル 指定する必要があります。 シナリオ設定でチャネルを1つから3つにすると、結果の是非はともかくとして QualNetは正常に終了します。 とりあえず、ここまでを確認してみて下さい。 |
スレッド表示 | 新しいものから | 前のトピック | 次のトピック | トップ |