テストシステムのパフォーマンスが、製造ラインの生産性とコストに大きな影響を与えることがあります。テストシステムが遅いと、システムの重複が必要になって余分なコストが生じたり、テスト範囲の縮小が必要になったりする可能性があります。いずれも、品質への影響が懸念される事態です。テストソフトウェアのパフォーマンスを最適化すると、テスト時間を大幅に増やすことができるほか、より少数のテストステーションでさらに徹底したテストを実行できるようになります。
本稿では、NI TestStandソフトウェアでテストステーションを開発し、そのパフォーマンスを最適化するためのいくつかの最善策について説明します。重要なことは、1つのソリューションであらゆるテストシステムには対応できないということです。テストの方法によっては、特定のテストシステムでパフォーマンスが低下するものの、他のシステムではパフォーマンスが向上するということがあります。システムに変更を加える場合は、どのような変更であってもその前後にテスト結果をベンチマークとして評価する時間を取りましょう。これにより、システムの潜在的な長所と短所を判断できるようになります。
TestStandの構成オプションのうち、パフォーマンスに影響を与えるものがいくつかあります。このセクションでは、それらのオプションについて解説します。
シーケンストレースを設定すると、合格、不合格、エラー、スキップなど、テストの現況に関するフィードバックやステータスを即座に得ることができます。一方で、シーケンストレースは実行速度を低下させてパフォーマンスに影響を与えます。次の方法は、シーケンストレースの利点を損なわずに実行速度を上げるのに役立ちます。
シーケンストレースを有効にした状態でパフォーマンスを改善するには、トレース速度を高速に設定し、各ステップ間に余分な遅延が生じないようにします。構成(Configure)→ステーションオプション(Station Options)を選択し、ステーションオプション(Station Options)ダイアログボックスの実行(Execution)タブでトレースを構成してください。
たとえトレースを最速に設定しても、各ステップの実行後に実行ビュー(Execution View)ペーンが更新されるため、ステップごとに数ミリ秒のオーバーヘッドが付加されます。トレースを完全に無効にすれば、パフォーマンスを最速にすることができます。ただし、シーケンストレースを無効にすると、シーケンスの実行中に実行ビューは更新されません。
パフォーマンスの問題とトレースの利便性とのバランスをとるには、 シーケンス呼び出しトレース設定(Sequence call trace setting)を使用して、特定のサブシーケンスでトレースを無効にします。 そのためには、テストをいくつかの論理グループに整理し、それぞれのグループにサブシーケンスを作成します。 たとえば、モバイルデバイス用のテストシーケンスでは、セルラーデータ、ユーザー入力、オーディオシステムなどの各コンポーネントのテストを個別のシーケンスに実装することが可能です。各コンポーネントのSequenceCallステップについて、シーケンス呼び出し内部のトレースを無効にします。
このようにテストシーケンスを整理することで、すべてのサブステップをトレースしたときのようなパフォーマンスオーバーヘッドを避けながら、最上位のシーケンスに対してトレースを実行することができます。また、個々のサブシーケンスを非同期で呼び出すことができるため、このアプローチは並列テストにも簡単に適用できます。テストシーケンスの並列化について詳しくは、本稿の並列テストによってテストのパフォーマンスを向上させるセクションを参照してください。
シーケンス呼び出しの各ステップでトレースを無効にしてパフォーマンスを改善し、実行状況を確認する
TestStandでは、コードモジュールをメモリにロードするタイミングおよびメモリからアンロードするタイミングを設定できます。この設定は、テストシーケンスのメモリ使用量と実行速度に大きな影響を与えます。モジュールをメモリに長く保持するように構成すると、サブシーケンスの実行時にモジュールを再ロードする必要が無くなるため、実行時間が短縮されます。 ただし、あまりに多くのモジュールをメモリに保持すると、アプリケーションのメモリ制限や使用可能な物理メモリ量を超えてしまい、実行速度が遅くなることがあります。
テストシステムのパフォーマンスを改善する上で本来望ましいのは、メモリ制限を緩和することであり、メモリを節約するためにコードモジュールをアンロードすることではありません。たとえば次のとおりです。
それでもメモリの使用状況に問題がある場合は、ステップまたはシーケンスファイルのレベルでロード/アンロードのオプションを設定できます。ほとんどのテストシステムでは、シーケンスファイルを開くときにプリロードする(Preload when opening sequence file)または実行を開始するときにプリロードする(Preload when execution begins)オプションと、 シーケンスファイルを閉じるときにアンロードする(Unload when sequence file is closed)オプションを組み合わせることで最良のパフォーマンスが得られます。
目標 | 最適な設定 |
実行時間の最大化 | シーケンスファイルを開くときにプリロードする(Preload when opening sequence file)およびシーケンスファイルを閉じるときにアンロードする(Unload when sequence file is closed)を設定し、シーケンスが閉じるまでメモリ上にモジュール群を保持します。 モジュール群をメモリにロードしたままにすることで、後続の呼び出しを高速化します。 |
メモリ使用量の節約 | 動的にロード(Load Dynamically)およびステップ実行後にアンロード(Unload after Step Executes)を設定し、使われなくなったモジュール群をただちにメモリから削除します。ただし、ステップを実行するたびにモジュールを再ロードする必要があるため、パフォーマンスは低下します。また、この設定にはコードモジュールのアンロード時にその内部のグローバルデータが失われる可能性があるなど、別のリスクもあります。 |
サイズの大きいシーケンスファイルをロードするとき、そのファイル形式によっては速度とパフォーマンスに影響を与えることがあります。TestStandでは、以下の形式でシーケンスファイルを保存できます:XML、INI、バイナリ。
新規のシーケンスファイルの形式を指定するには、次の手順に従ってください。
既存のシーケンスファイルの形式を変更するには、次のようにします。
シーケンスファイルのロード時間を最短にするにはバイナリ形式を使用する
シーケンスファイルとコードモジュールファイルを相対パスで指定している場合、検索ディレクトリの設定方法が、これらのファイルのロード時間に直接影響を与えます。検索ディレクトリの設定方法がパフォーマンスに影響を与えるのは初回ロード時およびテスト実行時ですが、モジュールを動的にロードするよう設定している場合は、それ以降もロードが繰り返されるたびに影響が続きます。検索ディレクトリを確認および編集するには、検索ディレクトリの設定(search directory configuration)ダイアログボックスを使用します。設定(Configure)→ディレクトリの検索(Search Directories)を選択すると、 検索ディレクトリの編集(Edit Search Directories)ダイアログボックスが開きます。
TestStandは、以下の手順に従ってコードモジュールの相対パスを解決します。
TestStandは、検索ディレクトリのリストをチェックし、コードモジュールファイルへの相対パスを解決する
各検索ディレクトリに対して解決するパスは1つだけなので、このプロセスは通常、パフォーマンスに大きな影響を与えません。
しかし、検索ディレクトリにサブディレクトリの検索(Search Subdirectories)オプションが設定されていると、指定されたパス内のすべてのサブディレクトリに対して上記のプロセスが繰り返されます。 仮に、そのパス内部に広大なディレクトリ階層が存在していると、このオプションを設定したことでパフォーマンスに重大な影響を及ぼすことがあります。 また、階層内に同じ名前のファイルが複数存在すれば、誤ったファイルがロードされる可能性があります。これらの理由から、追加する検索ディレクトリにこのオプションは設定しないでください。 その代わりに、基本となる検索ディレクトリへの相対パスによって、すべてのコードモジュールのパスが決定されるようにしてください。
検索ディレクトリの順序をさらに最適化するには、次のガイドラインを参考にしてください。
テストシステムのディレクトリ構造を設計するときは、コードモジュール群をシーケンスファイルのパスのすぐ下に保存するか、またはコードモジュール用の特定の場所に保管することを検討してください。
TestStandは、さまざまな開発環境でコードモジュール群を呼び出してテストの各ステップを実行することができます。コードモジュールおよび開発環境をどのように構成するかによって、パフォーマンスに大きな影響を与えます。 どのようなコードモジュール環境であっても、必要なデータのみをコードモジュールとやり取りすることにより、パフォーマンスを向上させることができます。コードモジュールによってアクセスされず、また変更もされないデータを大量に渡すことは避けてください。
.NETアセンブリやC/C++のDLLのようにコンパイルされたコードモジュールを使う場合、リリースバージョンではなくデバッグバージョンのDLLを使うと、パフォーマンスの低下を招くことがあります。開発段階では通常、モジュール内部の問題を発見して修正し易いように、開発者はデバッグバージョンのDLLを使用します。テストシーケンスをデプロイする準備ができたら、パフォーマンスを向上させるためにリリースバージョンのDLLに切り替えてください。
LabVIEW VIは直接実行されるため、LabVIEW開発環境またはLabVIEWランタイムエンジンのどちらでも実行できます。 開発環境でLabVIEW VIを実行する場合、デバッグ機能を利用してコードモジュールの問題をトラブルシューティングできますが、実行速度は遅くなります。 実稼働のテストでは、LabVIEWランタイムエンジンを使ってVIを呼び出してください。以下に示すように、LabVIEWアダプタ(LabVIEW adapter)ダイアログボックスで、いずれかのLabVIEWサーバーを選んでLabVIEWコードを実行することができます。
さらにLabVIEWコードのロード時間を短縮するには、コードモジュールVI群をパックプロジェクトライブラリ(PPL)に含めてビルドします。 PPLにはコードモジュールVI群のあらゆる依存関係がコンパイル済みバージョンとして格納されるため、LabVIEWによるVI依存関係のメモリへのロードが高速化します。 または、TestStandデプロイメントユーティリティ(TestStand Deployment Utility)を使用してコードをデプロイすると、デプロイメントプロセスの一環としてそれらのVI用PPLを生成できます。
TestStandデプロイメントユーティリティ(TestStand Deployment Utility)でPPLを使用する方法の詳細については、ヘルプトピックのLabVIEWパックプロジェクトライブラリでテストプログラムファイルを整理する(Organizing Test Program Files with LabVIEW Packed Project Libraries) を参照してください。
多くの場合、並列テストを利用して複数のテストを同時に完了することで、テスト速度を改善できます。 TestStandは、単一UUT(テスト対象ユニット)のテストを並列化する際に役立つ機能や、複数のUUTを同時にテストする機能を提供します。
単一UUTのテストでは、システムの複数部分を同時にテストできる場合があります。 たとえば、モバイルデバイスのテストシーケンスを考えてみましょう。セルラーデータ、ユーザー入力、オーディオシステムなどの各コンポーネントのテストでは、それぞれを別のサブシーケンスに実装することが可能です。各シーケンスを順番に呼び出すのではなく、非同期で呼び出してテストを高速化するよう、シーケンス呼び出しのステップを構成することができます。
シーケンス呼び出しを非同期で実行するには、次のように設定します。
新規のスレッドでシーケンスを呼び出すと、UUTのさまざまな部分を同時にテストできる
非同期のシーケンス呼び出しを構成する場合、新規のスレッドと新規の実行ではどのような違いがあるかを検討してください。
新規のスレッド | 新規の実行 |
呼び出し側と同じ結果コレクションおよびレポートを共有 | 独自に結果コレクションおよびレポートを保持 |
直接実行される | プロセスモデルのエントリポイントを使用して実行可能 |
呼び出し側とシーケンスファイルのグローバル値を共有 | シーケンスファイルグローバル値の新しいコピーを保持 |
呼び出し側と共に終了または一時停止 | 単独で終了または一時停止 |
テストシーケンス内部の関連するテスト群には、通例、新規のスレッドオプションを使用する必要があります。 新規の実行オプションは、より自律的な機能のテストに適しています。たとえば、テストシーケンスから独立して実行する必要のあるステータスモニタなどです。
新規のスレッドまたは新規の実行を選択する際の詳細な情報は、新規の実行または新規のスレッドのどちらのオプションでシーケンスを実行するべきか(When to Run a Sequence in a New Execution versus in a New Thread)を参照してください。
非同期サブシーケンスの結果をレポート用またはデータベースへのデータロギング用に取得するには、起動シーケンスの最後の部分で待機ステップを使用し、非同期のシーケンス呼び出しが完了するまで待機します。サブシーケンスのスレッドが完了すると、TestStandは非同期サブシーケンスの結果を待機ステップの結果に付加します。これらの結果は、レポート生成やデータベースロギングで利用可能です。シーケンスの実行またはスレッドを待機するには、待機する対象(Wait for)セクションで実行(Execution)またはスレッド(Thread)を選択し、右ペーンで待機する実行またはスレッドを指定します。 このように待機を設定すると、呼び出しシーケンスがスレッドより先に完了したときに実行速度が遅くなる可能性があるので注意してください。そのため、この方法は新規スレッドの結果が必要な場合に限ってください。
待機ステップを使って非同期シーケンス呼び出しの結果を取得する
テストシーケンス内部で非同期呼び出しを使用する以外に、TestStandでは並列化プロセスモデルおよびバッチプロセスモデルを使って複数のUUTを並列化してテストすることができます。 これらのプロセスモデルでは、複数の実行プロセスを作成し、それぞれが別のUUTでテストシーケンスを実行します。 現在のテストステーションに対して、または個々のテストシーケンスファイルに対してプロセスモデルの変更が可能です。
並列化プロセスモデルおよびバッチプロセスモデルを使用して複数のUUTを同時にテストする
並列テストによってテスト時間を効率化するデモについては、TestStandに付属する並列テストの実践デモ(Parallel Test Strategies Demo)を参照してください。
並列化プロセスモデルでは、各UUTのテストを異なる時刻に開始および終了できますが、バッチプロセスモデルでは、すべてのUUTでテストシーケンスを同時に開始および終了するよう設計されています。
バッチプロセスモデルでは、すべてのバッチテストを同時に開始および終了できるほか、バッチ同期化ステップと設定を利用して、バッチ内の全UUT間でさらに細かくテストを同期化することができます。たとえば、テストの特定のセクションをすべてのUUTで同時に実行する必要がある場合、単一のステップではバッチ同期化ステップ設定によって、複数のステップではバッチ同期化ステップタイプによって同期化したいセクションを定義することができます。
バッチ同期化を使用すると、バッチ内のすべてのUUTでテストの特定部分を同期化できる
あらゆるタイプのバッチ同期化セクションで、すべてのソケットは一斉にそのセクションを開始し、終了します。 同期化をさらに設定することで、テストを順次実行したり、単一のスレッドでのみ実行したりすることもできます。
バッチ同期化の詳細については、同期化ステップタイプ-バッチ同期化(Synchronization Step Types – Batch Synchronization)の例を参照してください。
複数のUUTを並列化してテストする場合、テストに使用するハードウェアによってはパフォーマンスのボトルネックになる可能性があります。 テスト用ハードウェアを共用する場合、どの時点でも常に1つのスレッドのみがその共用ハードウェアリソースにアクセスするようにしてリソースの競合を回避してください。 通常、ロック(Lock)設定またはステップタイプを使用して共用ハードウェアリソースを予約します。 しかし、単一のハードウェアリソース上で複数のスレッドがテストの完了を待機するような状況では、テストの並列化によって本来見込めるはずの改善点の多くが実現できません。 この状況を緩和するには、次の方法があります。
自動スケジュールステップ(Auto Schedule Step)タイプでは、一連のテストの実行順序を自由に構成して、テスト時間とハードウェア利用率を最適化できます。 並列化プロセスモデルまたはバッチプロセスモデルを使用して自動スケジュールを設定したセクションを実行する場合、各ソケットは予約済みでリソースを必要としない最初のセクションを実行します。このため、同一テスト内のさまざまな実行プロセスの間で実行順序はどのようであっても構いません。
実行する順序が特に重要でない場合、自動スケジュールを使ってハードウェアの利用率を最適化できる
この方法は、テストの実行順序が重要でないときに利用できます。テスト結果が特定の順序で必要な場合は、自動スケジュールを使わないでください。
TestStandに付属するExecution Profiler(実行プロファイラ)は、テストシステムの実行速度を抑制しているテスト用ハードウェアを発見する際に役に立つツールです。 プロファイラを起動するには、シーケンスエディター(Sequence Editor)からツール(Tools)→プロファイルの実行(Profile Execution)を選択します。
プロファイラを使用すると、各ハードウェアリソースがアクティブでいる時間を確認できるため、テストシステムにハードウェアを追加したときに予期される影響について、情報に基づいた判断を下すことができます。 以下のプロファイル例では、DMMは十分に利用されていますが、Scopeは66%しか利用されていません。 この情報に基づいて、2つ目となるDMMを加えるか、またはより多くのチャネルを備えたDMMを加えることにより、このシーケンスのテスト時間を短縮できることが期待されます。
Execution Profiler(実行プロファイラ)は、テストの構成で潜在的なボトルネックとなるリソースを可視化する
ハードウェアとのインタフェースを可能な限り効率化することで、テスト時間を短縮することができます。 ここでは、パフォーマンス向上のためにハードウェアリファレンス情報および計測手法を管理する上での留意点について説明します。
どのようなハードウェア構成を採用していても、一般にテスト効率低下の原因となり得る要素がいくつかあります。たとえば、オシロスコープを使って、信号の立ち上がり時間、立ち下がり時間、RMS、およびピーク値を測定できます。プログラミングによってオシロスコープの波形全体を捕捉し、波形データをテストシステムに転送してからそのデータに後処理を施して目的の計測結果を抽出しようとすると、データ転送量が増加してパフォーマンスは低下します。また、通信バスのレイテンシにもパフォーマンスは影響されます。計測器にLANやシリアル接続などの高レイテンシのバス、あるいはPCIやPXIなどの低レイテンシのバスのどちらを装備するかについても考慮する必要があります。
立ち上がり時間の計測、収集のトリガ、計測器からの立ち上がり時間のリードバック、そして毎回の計測でこれらを繰り返すようオシロスコープを構成する場合、計測の度にオシロスコープの再構成と再トリガが必要となります。この方法もまた、テストを低速かつ非効率にする傾向があります。
昨今、多くのオシロスコープが複数の計測チャンネルを備えていることから、次の手順に従ってテストを高速化してください。
ハードウェアとのセッションを頻繁に開いたり閉じたりすると、パフォーマンスの低下を招くおそれがあります。これは、デバイスとの通信が初期化された後、通信と構成を検証するために大量のデータが多くのドライバーによって転送されるからです。このため、ハードウェアの初期化はテストごとに1回に限るのが賢明です。一方でセッションハンドルは維持し、テスト全体を通してハードウェアへのアクセスに利用します。
ハードウェアの初期化をテストごとに1回に限定するには、ProcessSetupプロセスモデルコールバックをすべてのテスト関連コードより先に実行します。 並列化プロセスモデルおよびバッチプロセスモデルでは、テスト用ソケットの数にかかわらずProcessSetupの実行は1回だけです。ハードウェアのリファレンス情報をクリーンアップするには、すべてのテストが完了した後にProcessCleanupコールバックを1回だけ実行します。プロセスモデルコールバックの作成と使用について詳しくは、TestStandでコールバックを使用する(Using Callbacks in NI TestStand)を参照してください。
プロセスモデルコールバックで開かれたハードウェアセッションにアクセスするには、コールバックシーケンスとMainSequenceが共有するファイルグローバル変数を使用します。 あるいは、セッションマネージャを使ってハードウェアセッションの有効期間をActiveXオブジェクトによって自動的に管理することもできます。 セッションマネージャの使用方法について詳細は、セッションマネージャの使用例(Session Manager Examples)を参照してください。
結果の収集がシステムパフォーマンスに与える影響を最適化するには、いくつかの方法があります。
ビルトインの結果プロセッサでは、On-The-Flyオプションを選択することで、テストシーケンスの最後ではなく、シーケンスを実行しながらロギングすることが可能です。 これを設定する際には、以下の長所と短所について考慮してください。
オンザフライ(On-The-Fly)ロギングの長所
オンザフライ(On-The-Fly)ロギングの短所
オンザフライ(On-The-Fly)ロギングのメリットを得るために、ある程度の速度低下は許容するという場合、オンザフライの設定を変えることでパフォーマンスへの影響を軽減できます。 この設定を変えるには、次の手順に従ってください。
パフォーマンスを向上させるには、処理間隔を広げるか、最大結果数(Maximum number of Results)を増やすなどして、TestStandが結果を記録する頻度を減らします。
結果の生成にかかる時間を短縮するために、オフラインのファイルに結果データを記録することができます。このファイルは、高速で得られるコンパクトで未処理のファイル形式の結果データですが、TestStandによるレポートの生成やデータベースへのログに必要となるすべての情報が含まれています。 このファイルが格納するのは未処理の結果データのみです。したがって、処理時間が短縮され、テストのスループットが向上します。
未処理の結果ファイルをテストリポートに加工したり、データをデータベースへロギングしたりするには、オフライン結果処理ユーティリティ(Offline Results Processing Utility)を使用します。これは別途用意されているユーティリティです。そのため、テストとは関係なく実行できます。また、後で結果を処理するのも別のコンピューターで処理するのも自由です。このユーティリティは、速やかなレポート生成よりテストシステムのパフォーマンスを重視するという状況でお使いください。詳細については、ヘルプのTestStandオフライン結果処理ユーティリティ(TestStand Offline Results Processing Utility)を参照してください。
ロギングに関してローカルハードディスクへデータを格納する方が、ネットワーク上のどこかに格納するより高速です。しかし、ネットワークデータ転送メカニズムが他の方法より高速な場合があります。たとえば、Microsoftメッセージ キュー(MSMQ)を利用してデータベースと通信する場合、ローカルディスクに中間データファイルがまず作成され、それがネットワーク経由で転送されます。一般に、この方法はリモートデータベースに直接書き込むより高速かつ安全です。TestStandにはMSMQを利用するためのネイティブな機能はありませんが、サードパーティ製ツールでこのタイプの通信を実装することができます。
もう1つ留意すべき点は、システムに記録するデータの量です。ログに記録されるデータの量が増えるに従って、パフォーマンスは低下します。個々のステップまたはシーケンスについて結果の記録を無効にすれば、必要なデータのみをログに記録することができます。
ステップ(Step)→プロパティ(Properties)→実行オプション(Run Options)を選択し、結果を記録(Record Result)オプションの選択を解除することで、ステップごとに結果の記録を無効にすることが可能です。また、シーケンスのプロパティ(Sequence Properties)ダイアログボックスのすべてのステップで結果の記録を無効にする(Disable Result Recording For All Steps)を設定し、シーケンス全体で結果の記録を無効にすることができます。
実稼働環境では、どのテストが不合格になったかを知る必要はなく、単にいずれかのテストでUUTが不合格になったという事実を知るだけでよい場合があります。こうしたケースでは、最初に不合格になった時点でテストを終了し、システムリソースを解放して、後から詳細な分析を手に入れることができます。
テストによっては不合格の評価に軽重があり、ある不合格事案は他の事案より重大である可能性があります。その場合、あるステップが不合格になったときにのみテストを終了することが可能です。 個々のステップまたはシーケンスについて、不合格が発生した時の動作を設定することができます。
特定のステップで何らかの不合格が発生したときにテストを終了するには、次の手順に従ってください。
特定のシーケンスで何らかの不合格が発生したときにテストを終了するには、次の手順に従ってください。
特定のテストステーションに対してこの動作を設定することもできます。たとえば、実稼働のテストマシンでのみ不合格発生初期にテストを終了し、生産ライン外の診断用マシンでは常にテストを完了する、といった設定が可能です。 特定のテストマシンを対象に、不合格が発生したときにテストを終了するよう設定するには、次の手順に従ってください。