July 08, 2009

Super Sylphide 進捗状況(25) -- DSP航法ファームウェア バク取れた

前回の進捗記事で航法ファームウェアの開発遍歴についてふれたオートパイロットシステム Super Sylphideのその後のお話です。航法計算が正確に動くことは開発の過程で実証できていたのですが、最終的に組み合わせてリアルタイム動作させてみると色々と問題が発生しました。特にかなり以前の記事で書いた『McBSP(SPI)におけるCPU割込とEDMAの協調』の部分が強敵で、GPSやセンサなどの周辺機器を取り仕切っているマイコンC8051と、それからの情報を使って計算するDSP間の通信エラーが多発するという問題が発生していました。

結論から言うと、通信のタイミングの問題でした。以前の記事にもあるとおり、DSPは通信においてスレーブ、すなわち主導権を握っていない側であり、はじめの通信を受信割り込みで処理し、そこから得られた情報を元に以後自動的に送受信を行ってくれるEDMAを起動する設計としました。こうすることで通信によるDSPの負荷を軽減すること、ならびに可変長通信が可能になることを実現できました。しかしこの設計ではDSPの計算負荷が高いと、最初の割り込みからEDMAが起動されるまでに、より多くの時間がかかるようでした。そこで通信の主導権を握っているマイコンC8051側で、はじめの送信が終わった後にウェイトをいれて、送受信内容が破棄されないようにする必要がありました。

McBSP_EDMA_time_chart.png
タイミングチャート(Master=C8051, Slave=DSP)

結論を書いてしまうと、なんだそんな程度のことなのか、と思われるかもしれませんが、解決には相当の長い時間を要しました。通信は目に見えない部分、言い方を換えるとデバッカを使っても見えない部分であることがほとんどなので、大変恐ろしいものだということを改めて思い知らされました。今後の具体的な通信のトラブル事例に適用できるであろう、いくつかの指針を戒めとして残しておきたいと思います。

1) 割り込みはとにかく短く、とにかく短く
割り込みルーチン内での処理は、可能な限り短くする必要があります。実行時条件を同じにして分岐を少なくする、同期の問題はできるだけ割り込み外で処理するのが有効です。特に同期についてRTOSを使っている場合、割り込み内で使うにはコストが高すぎることがあるので注意です。

2) 割り込みの前と後で何が行われているか、よく調べる
割り込みに入る前ではレジスタの退避、後では復帰が行われるのが一般的ですが、今回のDSPで使ったRTOSのDSP/BIOSでは、dispatcherという機構を使うことで割り込み内での別の割り込みの可不可までも管理してくれます。しかしdispatcherに管理をお任せすると、割り込みルーチン内で別の割り込みの可不可を設定しても、割り込みから抜ける際に上書きされてしまうという仕様(spru423f.pdfの4-23、dispatcherはHWI_enterとHWI_exitで同じIERのMASKを取ると思われる)なのでした。

3) 通信のクロック速度を上げ下げしてみる
通信の速度を遅くしてみると、問題が解決することがよくあります。これが問題解決の糸口になるかもしれません。

4) DMAは気まぐれ
計算負荷があがると、キャッシュとメモリの間での転送量があがることが予想されます。ということはキャッシュとメモリ間での転送がDMAによって自動的に行われている場合、ユーザサイドで設定したDMAはどのタイミングで実行されることになるか、優先順位が高く設定できない場合は注意が必要ということです。

最後に完成したDSPファームを晒しておくことにします。リアルタイム50Hzで航法計算ができることを確認しました。いつの日か、もっと整理された解説記事を書きたいところです。

※その後、飛行試験の様子を書きました。

23:59 fenrir が投稿 : 固定リンク | | このエントリーを含むはてなブックマーク | トラックバック
このエントリーのトラックバックURL: https://fenrir.naruoka.org/mt/mt-tb.cgi/709
コメント
コメントする









名前、アドレスを登録しますか?
(次回以降コメント入力が楽になります)
  • 匿名でのコメントは受け付けておりません。
  • 名前(ハンドル名可)とメールアドレスは必ず入力してください。
  • メールアドレスを表示されたくないときはURLも必ず記入してください。
  • コメント欄でHTMLタグは使用できません。
  • コメント本文に日本語(全角文字)がある程度多く含まれている必要があります。
  • コメント欄内のURLと思われる文字列は自動的にリンクに変換されます。