ミッドレンジマイコンでマルチタスク

処理性能がさほど高くないミッドレンジのマイコンを利用して、時間的要求がさまざまなタスクを上手に処理しようとする場合、単純なメインループ(+割り込み)のアーキテクチャでは苦しくなることがあります。
具体的には、私がここ数週間取り組んでいたWEM菅生用電気自動車のデータロガーの設計方針の失敗談です。

そういえば、大体似たようなことを以前senshu先生の掲示板に書きました。
少ピンマイコン用組込みOSのメリット


ごめんなさい


数週間ほど、私はWEM菅生に向けてデータロガーを設計・製作していましたが、ちょっとだらだらとしすぎて、完成に至りませんでした。単純にやる気と時間が不足していただけと言う話もありますが、電気自動車に全く興味が無い人にとっても読んでもらえるように概念的な話を書きます。

ロガーの仕様


電気自動車レース用データロガーなので、最低限計測しなければならないデータは「速度」「ラップタイム」「電流」「電圧」です。レギュレーションは2時間耐久レースに分類されるものなので、スタートからの「経過時間」も必要です。
これらのデータをドライバーが読み取れるように「表示」し、ログとしてメモリに「保存」する。これが、ロガーの仕様の核です。

ラップタイマと速度計はレシプロカル方式の周波数カウンタのようなものなので、エッジの検出からタイマの読み込みまでのタイムラグはできるだけ小さい方が好ましいです。このため、ラップタイマと速度計のプログラム全体の中での時間的要求(優先度)は最高です。

ADCのサンプリングレートは、1~10sps程度の超低速でかまわないので、優先度は高くありませんが、取りこぼしがあっては困ります。また、ドライバーのための表示器の更新レートは、「経過時間」の表示を0.1s単位まで見せるとすると、10HzとなるのでADCのサンプリングレートと同等となります。

メモリは、何を使ってもよいのですが、あとでPCをつかって処理することを考えると、SDカードにFATファイルシステムを使って書き込むのがポピュラーです。SDカードにSPIモードで書き込むのはかなり遅いので、ADCのサンプリングや表示機の表示のタスクをSDカーへの保存タスクよりも、一段階優先度を上げたいと考えます。

そんなわけで、優先度の割り振りは以下の三段階となりました。

  1. 速度計・ラップタイマ・経過時間
  2. ADC・表示機への表示
  3. ログデータの保存


優先度に応じたCPUの割り振り


すべてのタスクの優先度が高くないプログラムの場合は、単純にメインループの中ですべての処理が賄えます。

この単純なアーキテクチャに加えて、少数の高優先度のタスクがあるアーキテクチャでは、高優先度のタスクを割り込み処理とすれば、上手に処理することができます。
このメインループ+割り込みのアーキテクチャでは、優先度が上位と下位の2種類に分けられる場合に使われます。

これらの2パターンは、マイコンのプログラムをしている人なら無意識のうちにやっている手法です。そして、多くの場合これだけでうまく処理ができます。更に言うなら、これらの2パターンでうまく処理できるようにシステム全体を考える方が、難しいことをするより多分楽です。

しかし今回のロガーの例では、優先度が3段階必要なので、なんとか上手くごまかさなければなりません。以降は上手くごまかすための方法を思いつく限り列挙しました。

多重割り込みアーキテクチャ


多重割り込み機能を持ったマイコンを選べばスマートに実装できます。
上位割り込み・下位割り込み・メインループで三段階の優先度を賄うことができます。

実を言うと、以前PIC18F452を使って失敗しました。
多重割り込みに関してエラッタが出ていたことに気づかなかったのです。
以下、PIC18FXX2 Rev. B2 Silicon/Data Sheet Errataからの引用です。

4. Module: Interrupts
Under certain conditions, the use of dual priority
interrupts may cause a program instruction to be
skipped entirely. This has only been observed
when both of the following apply:
  • Both high and low interrupts are enabled, and
  • A high priority asynchronous interrupt occurs in

the following cycle after any low priority
interrupts.
The event causes the stack to get pushed twice,
and will eventually result in an overflow.


とはいえ、これは多重割り込みが正常に動作するマイコンなら、上手くいくはずの方法です。

ハードウエアで処理する


今回のロガーの例では優先度の高い処理は、処理内容自体は単純なもので、速度計・ラップタイマともに、トリガ信号を検出した瞬間のタイマの値をキャプチャするだけです。
ハードウエアの処理だけで、最高の優先度の処理を賄ってくれるのなら、CPUはそれ以外の2段階の優先度を持つプログラムだけですみます。

今回はPSoCのデジタルブロックにその役割を果たしてもらおうと考えていました。
できなかったのは単純に私の実力不足だと思います。

複数のCPUで処理する


優先度の異なる処理の一部を、他のハードウエアに分担してもらうと言う考え方自体はひとつまえの「ハードウエアで処理する」と同じです。処理の一部を他のマイコンに負担してもらうことを考えます。

今回の例で言うならば例えば、一番処理が重いSDカードへの書き込み処理を別のマイコンへ追い出します。メインのマイコンでは、データのサンプリング等を行い、書き込むべきデータを書き込み専用の別のマイコンにシリアル通信で送ります。

プログラマーの能力と言うのが、どれだけ限られたりソースに対して処理を詰め込めるのかで決まるのだとすれば、この方法は一番初級者でも上手くいく方法であろうと思います。

リアルタイムマルチタスクOS


マルチタスクOSというとずいぶんと大層に思えますが、PIC16F程度の単純なマイコンでは、ちょっと処理の単位をタスクとして意識しながらメインループを組むだけでもそれらしいものになります。2ちゃんねる電気・電子板のPICにOSは必要か?のはじめの方(PIC16Fより高度な18,24,32,dsPIC等がメジャーになる前)の書き込みはこの考え方のエッセンスです。

ただし、多重割り込み機能もスタックへのユーザによる操作もできないPIC16Fの場合は、タスクが自発的にタスクスイッチャへの復帰をすることが要求されます。
結局のところ、1つのタスクが長時間CPUを拘束してしまうと、リアルタイム性が失われてしまいます。この問題に対して、PICで有名な後閑哲也さんのPICROSをみると、タスクを複数のステージに分割することで1つのタスクが長くなりすぎないようにしているようです。とはいうものの、このステージの分割は人間がコーディングの段階で行わなければならないことなので、OSを使う/使わないの問題とは余り関係がありません。

参考URL




フィードバック



にほんブログ村 その他趣味ブログ 電子工作へ

 ↑ 電子工作ブログランキング参加中です。1クリックお願いします。


コメント・トラックバックも歓迎です。 ↓      


 ↓ この記事が面白かった方は「拍手」をお願いします。


tag: PIC PSoC 

comment

Secret

No title

引き受けておきながら凸凸も信頼性抜群に悪くてごめんなさいmm

現役時代とちがって、車体も離れたところにあるし
一人作業になってしまうから
「やる気」の継続も思いのほか大変なんだよね

グリッドスタートで1週以上する動画を撮りたいので、来年もやろうかなーっとは思ってるけど

Re: No title

のさん、こんばんは。

回路に取り組む前に、エネマネとか、バッテリの特性とか、作戦とかについて教えて欲しいなと思ったり思わなかったり・・・です。

インプット・キャプチャ

この部分だけコメントします。

> エッジの検出からタイマの読み込みまでのタイムラグはできるだけ小さい方が好ましいです。

フリースケール社のMCUに内蔵されているタイマの場合は、エッジを検出した時刻を記憶する「インプット・キャプチャ」という機能があります。時刻は、タイマ・チャネルごとに個別のレジスタに記憶されていますので、後からゆっくりと確認することができます。もちろん、エッジの発生と同時に割り込みも発生しますが、エッジの発生が頻繁でなければ、ポーリングでも対応できると思います。
こういう機能って、普通だと思っていたのですが、標準的な仕様ではないのかな?
他のMCUの勉強もしなくちゃね。

Re: インプット・キャプチャ

のりたんさん、おはようございます。

インプットキャプチャの機能は、PSoCにも間違いなく存在するはずです。私が上手いこと使えなかっただけで・・・。
ただ、古~いPIC(例えばPIC16F84Aなど)にはインプットキャプチャが無いものもあるようですね。

管理人のみ閲覧できます

このコメントは管理人のみ閲覧できます
FC2カウンター
カテゴリ
ユーザータグ

LTspiceAkaiKKRmachikaneyamaScilabKKRPSoC強磁性CPAPICOPアンプecalj状態密度常微分方程式モンテカルロ解析トランジスタodeDOSインターフェーススイッチング回路定電流PDS5022分散関係半導体シェルスクリプト乱数レベルシフトHP6632A温度解析ブレッドボード可変抵抗I2Cトランジスタ技術R6452A確率論バンド構造セミナーバンドギャップ反強磁性数値積分熱設計絶縁非線形方程式ソルバ偏微分方程式PWscfA/Dコンバータマフィンティン半径フォトカプラカオスISO-I2CGW近似LM358LEDシュミットトリガ三端子レギュレータ74HC4053アナログスイッチUSBサーボ数値微分直流動作点解析補間カレントミラーTL431PC817C発振回路FFT電子負荷VESTA開発環境量子力学単振り子bzqlty基本並進ベクトル2ちゃんねるチョッパアンプ標準ロジックパラメトリック解析アセンブラブラべ格子BSchQuantumESPRESSOイジング模型LDA状態方程式GGA仮想結晶近似VCA熱伝導SMPスイッチト・キャパシタキュリー温度Quantum_ESPRESSOスーパーリーグTLP621トレーナーバトルewidth最適化Maxima抵抗失敗談相対論コバルト繰り返し位相図六方最密充填構造ポケモンGOスピン軌道相互作用gfortranランダムウォークFETスレーターポーリング曲線cygwinQSGW不規則合金ラプラス方程式MCU条件分岐データロガーマントルUPS固有値問題格子比熱シュレディンガー方程式熱力学詰め回路ガイガー管QNAP井戸型ポテンシャルダイヤモンドOpenMPTLP521ハーフメタルLM555ubuntu平均場近似ブラウン運動フェルミ面NE555ZnOゼーベック係数TLP552xcrysdenCIF最小値最大値awkfsolveテスタ第一原理計算Ubuntu差し込みグラフFXA-7020ZR三角波過渡解析Writer509自動計測スーパーセル起電力トランスCK1026MAS830LフィルタPGAP-10MBEOPA2277ナイキスト線図ノコギリ波AACircuitEAGLE2SC1815PIC16F785LMC662CapSense負帰還安定性入出力固定スピンモーメントFSMTeX結晶磁気異方性全エネルギーc/a合金multiplotgnuplot非線型方程式ソルバL10構造正規分布等高線ジバニャン方程式初期値interp1fcc面心立方構造ウィグナーザイツ胞半金属デバイ模型磁気モーメント電荷密度重積分SIC不純物問題擬ポテンシャル状態図cif2cellPWgui二相共存ウルツ鉱構造edeltquantumESPRESSOフォノンリジッドバンド模型スワップ領域BaO岩塩構造ルチル構造ヒストグラム確率論マテリアルデザインフラクタルマンデルブロ集合キーボードRealforceクーロン散乱三次元疎行列縮退化学反応関数フィッティング最小二乗法Excel直流解析PCTS-110TS-112日本語パラメータ・モデル等価回路モデル文字列不規則局所モーメント陰解法熱拡散方程式HiLAPWCrank-Nicolson法連立一次方程式specx.fifort境界条件両対数グラフ片対数グラフGimp円周率ヒストグラムシンボル線種グラフの分割軸ラベル凡例トラックボール

最新コメント
リンク

にほんブログ村 その他趣味ブログ 電子工作へ