NT-Loggerでお気楽デバッグ
リアルタイム性を要求されるような、小規模組み込みシステムにおいて、要求される時間に処理が間に合っているのかどうかは非常に重要な問題です。
一見すると「うまく動作しているように見える」場合でも、どの程度の余裕度をもって処理されているのか知る必要もあります。
市販の高機能なトレーサーを用いると、かなりの精度でターゲットの実行状態を知ることができますが、高価なものが多く、100万円を下らないのが実状です。
NT-Loggerは、小規模組み込みシステムの全体処理を手軽に可視化する事のできるツールです。
ターゲットに必要なのはUARTポートのみ。
アプリケーションの特定区間の処理にどの程度の時間を要するのかを簡単に確認する事ができます。
カーネルのタスクスイッチングのような動作を確認する必要はないけど、アプリケーションの特定区間の実行時間を知りたいなどと言った場合に便利です。
測定結果の確認はブラウザで簡単
NT-Loggerを使ったシステム全体挙動の確認は、最終的に得られるhtmlファイルをブラウザで見る事で可能です。
以下は、あるオーディオシステムにおける全体挙動を表示した例です。
マウスのホイールをグルグル回せば、時間軸を拡大して見ることができます。
開発のきっかけ
数年前(2010年前半頃)にTOPPERSプロジェクトのTrace Log Visualizerを使用したのですが、その時からNT-Loggerのプロジェクトがスタートしました。
Trace Log Visualizerのデフォルトの動作は、ターゲット側のメモリにイベント情報を記録します。
最終的にあるタイミングでホスト側に記録したデータを出力するという仕組みです。
この場合、ターゲット側に巨大なメモリが存在していなくてはなりません。
TOPPERSのように小規模組み込みシステムで使用したいOSのロギングツールとして魅力をあまり感じませんでした。
実は後日、このデフォルトの動作を変更できる事を知ったのですが。
NT-Loggerの特徴
本ツールの特徴を挙げます。
-
シリアルポートのある組み込みシステムなら、どんなシステムでも使用可能。
-
組み込みシステム側に巨大なメモリが不要。
-
記録時間はホスト側のストレージの容量に依存。長時間の記録が可能。
-
1イベントあたり1バイトの送信のみで動作が非常に軽量。
-
導入の敷居が低く、小規模組み込みシステムの動作確認や教育用途に最適。
-
シンプルな設計で移植や改造が容易。
-
ホスト側プログラムはWindows, Mac OS, Linuxと3つのプラットフォームに対応。
-
Natural Tiny Logger (NT-Logger)による最終出力はブラウザ上で確認する事ができます。
-
マウスホイールで時間軸を伸ばしたり縮めたりしながら、システムの全体挙動を確認できます。
NT-Loggerの対象外
NT-Loggerは「無いより遥かに便利!」、「しかも無償で使える!」をコンセプトに開発しました。
幾つかのトレードオフについて、使用前に事前に説明する必要があります。
-
ターゲットとホスト間の通信経路においてのバッファリング等による遅延などの影響は考えない。
-
ターゲットとホスト間の通信経路に存在するであろうバッファリング等による遅延やジッタの影響は、測定対象単位時間に対して十分に小さく無視できるものとして扱う。
-
絶対時間情報を必要とするようなデバッグには使用できないが、メッセージパッシングで駆動するリアルタイムシステムにおいて、通常は因果関係が明らかであるので問題ないものとして扱う。
-
非同期システムのデバッグに使用できない事を意味するが、因果関係のはっきりしないような不確定要素を含むリアルタイムシステムは、そもそも設計してはならないものとして、これを無視する。
-
ロギングのためのオーバーヘッドは無視できるほどに小さいものとして扱う。
どんな組み込みシステムでも使える
組み込みシステムの全体挙動を確認するためのツールは、市販品を中心に星の数ほど存在します。
多く見られる実現形態の一つが、ターゲットとホストの間に専用のハードウェアを介入させて、忠実にイベントをロギングする形態です。
確かに忠実なイベントのロギングには、これが一番信頼性の高い方法でしょう。
中間装置が正確な時刻情報を付与すると共に、データをバッファリングし、ホストコンピュータの処理能力に影響されずに正確にロギングする事ができます。
これらの中間装置を必要とするロギングツールの場合、導入コストがかなりかかる事が多いです。
実際の開発では、システムの全体挙動の概要を確認するだけで、どんな問題があるのかわかる事も多々あります。
少し調べたいだけの時に高価なロギングツールを購入できるかどうかは状況によります。
先のトレードオフでも述べたとおり、組み込みシステムの場合はイベント駆動型で設計するのが普通のアプローチです。
あるイベントがある動作を引き起こすという因果関係を明らかにするのと同時に、 原因と結果の依存関係を緩い依存関係で留める事ができるわけです。
NT-Loggerは、多くの組み込みシステムに搭載されているシリアルポートを有効に活用し、必要最低限のロギング機能で最大限の効果を挙げることを目的に設計されています。
因果関係が明らかになっている組み込みシステムの場合、簡単なロギングメカニズムを追加するだけでも十分な効果が得られるというわけです。
設計と概念
ここで、設計や概念などを記しておきます。
-
イベントは、「イベント発生源」から発生する。
-
イベントは、イベント情報で表現される。
-
イベント情報には、「始まり」と「終わり」を示す「タイプ番号」がある。
-
イベント情報には、「イベント発生源」を示す「トラック番号」がある。
-
イベント情報には、イベント内容を示す「イベント番号」がある。
-
ターゲットから送られるイベント情報には、「トラック番号」と「イベント番号」と「タイプ番号」が含まれる。
-
ホストは、ターゲットから送られるイベント情報に時間情報を付与して記録する。
-
ホストは、記録されたデータを基にした可視化データを生成する事ができる。
使用手順
-
ターゲット側プログラムにロギング用APIを埋め込み動作させる。
-
ホスト側でキャプチャプログラムを実行する。
-
キャプチャされたデータからHTMLを生成するジェネレータを実行する。
-
ブラウザで結果を確認する。
仕様
-
最大トラック数は16トラック。
-
1トラックあたり8つのイベントを記録可能。(16x8=128事象の取り扱いが可能)
-
記録イベントの分解能はマイクロ秒単位。
-
RAMが1KBを切るようなシステムでも使用可能。
-
ターゲット側は最小限のAPIの実装のみで移植可能。
-
データはブラウザで閲覧可能。
事前準備
以下の手順で事前準備を行います。
ntlser.cの実装提供
ntlser.cは、NT-Loggerを使うために必要なターゲット側の実装です。
提供時には以下のようなコードになっています。
/**
* @brief NT-Loggerの機能を有効にする場合には真に設定する。
*/
#define NTL_ENABLED (0)
/**
* @brief シリアルポートを初期化する。
*
* @retval 0 成功。
* @retval -1 失敗。
*/
int ntlser_init(void)
{
#if NTL_ENABLED
/*
* @todo ここでシリアルポートを初期化する。
*/
return 0;
#else
/*
* 無効化されているので何もしないで成功した事にする。
*/
return 0;
#endif
}
/**
* @brief シリアルポートにデータを書き込む。
*
* @param buf 送信要求データ。
* @param siz 送信要求バイト数。
*
* @return 実際に送信したバイト数。
*/
int ntlser_write(const unsigned char *buf, const int siz)
{
#if NTL_ENABLED
/*
* @todo ここでシリアルポートに送信する。
*/
return siz;
#else
/*
* 無効化されているので何もしないで成功した事にする。
*/
return siz;
#endif
}
ターゲット側に必要な唯一の実装は非常に小規模です。
シリアルポートの初期化と書き込みの関数を提供するだけで済みます。
@todoで示された処理を追加する事でNT-Loggerを使用する準備が完了です。
使用方法
マクロ埋め込み
確認したいアプリケーションの特定区間にロギング用マクロを埋め込みます。
#include "ntl.h"
int main(void)
{
ntl_init();
while (1) {
NTL_EVENT_START(トラック番号, イベント番号);
/*
* この間の時間を計測。
*/
NTL_EVENT_END(トラック番号, イベント番号);
}
}
測定したい区間に対して同じ「トラック番号」と「イベント番号」を割り当て、NTL_EVENT_STARTとNTL_EVENT_ENDで囲います。
ログ収集
ホストとターゲットを接続し、ターゲットを動作させてログを収集します。
ログの収集はホストでntlcapを実行するだけです。
ntlcap -p シリアルポート名 -b ボーレート -o ログファイル.ntl -c 記録イベント数
ログファイルは以下のように日付と時刻、ターゲットが送信したイベント情報をが記録されています。
2012/07/26 19:46:03.633153 01
2012/07/26 19:46:03.633169 00
2012/07/26 19:46:03.633184 53
2012/07/26 19:46:03.633201 23
2012/07/26 19:46:03.633217 19
2012/07/26 19:46:03.633232 18
2012/07/26 19:46:03.633248 22
2012/07/26 19:46:03.633264 52
2012/07/26 19:46:03.633280 51
2012/07/26 19:46:03.633296 50
2012/07/26 19:46:03.633312 01
2012/07/26 19:46:03.633328 00
2012/07/26 19:46:03.633343 53
htmlファイル生成
ntlcapで取得したログファイルを、ブラウザで閲覧可能な形式に変換します。
ntlgen -i ログファイル.ntl -o htmlファイル.html -d 詳細ファイル.ntd
詳細ファイルとは、トラック番号とイベント番号に対して名称を付けるためのファイルです。
以下に例を示します。
0 0 Audio Play
0 1 Audio Cancel
0 2 Audio Volume
1 0 Display Clear
1 1 Display DrawBox
1 2 Display DrawLogo
1 3 Display DrawText
1 4 Display DrawProg
1 5 Display LedOn
1 6 Display LedOff
1 7 Display LedToggle
2 0 Menu Filename
2 1 Menu Location
2 2 Menu Rotary
2 3 Menu Switch
2 4 Menu Remote
5 0 FileIO Reading
5 1 FileIO Others
htmlファイル閲覧
htmlファイルの閲覧の前に、timelineディレクトリにtimeline-2.1.2.zipを展開して下さい。
ntlgenで生成したhtmlファイルをブラウザで開くとタイムラインを見ることができます。
現在のバージョンでは、閲覧時にネットワーク接続を必要とします。
Download
History
Date |
Description |
2012/09/27 |
Initial version |
戻る