Archived: LabVIEW​を​使用​した​マルチ​コア​プログラミング

NI does not actively maintain this document.

This content provides support for older products and technology, so you may notice outdated links or obsolete information about operating systems or other relevant products.

概要

この​ドキュメント​は、​マルチ​コア​プログラミング​の​基本​シリーズ​の​一部​です。
マルチコアプログラミングの基本シリーズ

マルチ​コア​プログラミング​の​基本​シリーズ

この​技術​資料​では、​マルチ​コア​プログラミング​の​難題​について​解説​し​ます。​具体​的​に​は、​ソフトウェア​アーキテクチャ​に​適用​可能​な​各種​マルチ​コア​プログラミング​パターン​について​説明​し​ます。

内容

概要

プログラミング​パターン​に関して​は​複数​の​書籍​で​解説​さ​れ​てい​ます​ので、​本​ドキュメント​では​下記​の​概念​について​紹介​する​とともに、​それら​が​LabVIEW​に​どの​よう​に​適用​さ​れる​か​を​説明​し​ます。

  1. タスク​の​並列​処理
  2. データ​の​並列​処理
  3. パイプライン​処理
  4. 構造​格子

ソフトウェア​アーキテクチャ​の​視点​で、​アプリケーション​の​問題​に​最適​な​並列​パターン​を​組み込む​よう​にし​ます。​適切​な​パターン​を​選ぶ​に​は、​アプリケーション​の​特性​と​ハードウェア​アーキテクチャ​について​検討​する​必要​が​あり​ます。

さらに、​上記​の​パターン​に​関連​し​て、​通常​の​While​ループ、​フィードバック​ノード、​シフトレジスタ、​タイミング​ループ、​並列​For​ループ​など​さまざま​な​LabVIEW​ストラクチャ​について​も​紹介​し​ます。

タスク​の​並列​処理

タスク​の​並列​処理​と​は、​最も​シンプル​な​形​の​並列​プログラミング​方法​で、​アプリケーション​を​互いに​依存​せ​ず​異なる​プロセッサ​上​で​実行​可能​な​固有​の​タスク​に​分割​する​もの​です。​ループ​A​が​信号​処理​ルーチン​を、​ループ​B​が​ユーザ​インタフェース​の​更新​を​実行​する​という、​2​つ​の​ループ​を​持つ​プログラム​について​考え​て​み​ます。​これ​は、​マルチ​ス​レッド​アプリケーション​が​複数​の​CPU​を​利用​し​て、​2​つ​の​ループ​を​別々​の​スレッド​で​実行​する​タスク​の​並列​処理​で​ある​と​言​え​ます。

LabVIEW​で​タスク​の​並列​処理​を​行う​に​は、​ブロック​ダイ​ア​グラム​上​に​コード​の​並列​部分​を​作成​し​ます。​LabVIEW​で​並列​処理​を​行う​場合、​コードの並列部分が視覚的に表示され、​個々​の​タスク​を​簡単​に​切り離す​こと​が​できる​という​メリット​が​あり​ます。​また、​LabVIEW​では​アプリケーション​が​自動​で​マルチスレッド​化​さ​れる​ため、​スレッド​管理​や​スレッド​間​の​同期​について​気​に​する​必要​が​ありま​せん。

データ​の​並列​処理

大量​の​データセット​に対し​データ​の​並列​処理​を​行う​場合​は、​大きな​配列​や​マト​リ​クス​を​サブ​セット​に​分割​し、​操作​を​行​って、​結果​を​統合​し​ます。

まず、​1​つ​の​CPU​が​全て​の​データセット​の​処理​を​試みる​逐次​処理​について​考え​て​み​ます。


図​1. 1​つ​の​CPU​による​処理

次​の​例​では、​同じ​データセット​が​4​つ​の​部分​に​分割​さ​れ​てい​ます。​この​データセット​を​使用​可能​な​コア​間​で​分ける​こと​で、​速度​を​大幅​に​向上​せ​さる​こと​が​でき​ます。


図​2. 複数​の​CPU​による​処理

制御​システム​といった​リアルタイム​の​ハイパフォーマンスコンピューティング​(HPC)​アプリケーション​では、​かなり​サイズ​の​大きい​行列​ベクトル​積​を​並列​実行​する​の​が​効率​の​良い​一般​的​な​方法​です。​一般に、​マト​リ​クス​は​固定​さ​れ​てい​ます​ので、​前もって​分解​し​て​おく​こと​が​でき​ます。​センサ​によって​集め​ら​れ​た​計測​結果​は、​ループ​ごと​の​ベクトル​を​提供​し​ます。​例えば、​行列​ベクトル​の​結果​によって、​アクチュエータ​を​制御​する​こと​が​でき​ます。

以下​の​ブロック​ダイ​ア​グラム​は、​8​つ​の​コア​に​分散​さ​れ​た​行列​ベクトル​積​を​示し​てい​ます。


図​3. LabVIEW​における​行列​ベクトル積

この​ブロック​ダイ​ア​グラム​は​左​から​右​に​実行​する​よう​に​な​って​おり、​下記​の​手順​を​実行​し​ます。

  1. While​ループ​に​入る​前​に​マト​リ​クス​A​を​分割
  2. マト​リ​クス​A​の​各​部分​に​ベクトル​b​を​乗算
  3. 計算​結果​の​ベクトル​を​統合​し​て、​最終​的​な​x=Axb​を​算出

パイプライン​処理

パイプライン​処理​は、​アセンブリ​ライン​に​似​てい​ます。​スト​リー​ミン​グ​アプリケーション​や、​演算​負荷​の​高い​アルゴリズム​を​逐次​的​に​変更​する​場合​など、​個々​の​手順​に​多く​の​時間​が​かかる​アプリケーション​で​の​処理​について​考え​て​み​ます。


図​4. アルゴリズム​の​逐次​的​ステージ

アセンブリ​ライン​と​同様、​各​ステージ​で​1​単位​の​作業​を​行い​ます。​それぞれの結果は次のステージに送られ、​最後​の​ステージ​まで​それ​を​繰り返し​ます。

マルチ​コア​CPU​で​実行​する​アプリケーション​に対し​パイプライン​処理​を​行う​場合​は、​アルゴリズム​を​ほぼ​同じ​作業​単位​の​ステップ​に​分け、​各​ステップ​を​異なる​コア​上​で​実行​し​ます。​アルゴリズム​は、​複数​の​データセット​や​連続​的​に​ストリーミング​する​データ​で​反復​でき​ます。


図​5. パイプライン​処理​方式

重要​な​の​は、​それぞれ​の​ステップ​に​かかる​時間​が​均等​に​なる​よう​に​アルゴリズム​を​分割​する​こと​です。​その​理由​は、​個々​の​反復​に​最も​長い​ステップ​と​同じ​長​さ​の​時間​が​かかる​ため​です。​例えば、​ステップ​2​が​実行​に​1​分​かかり、​ステップ​1、​3、​4​が​それぞれ​10​秒​かかる​場合、​その​反復​に​かかる​時間​は​1​分​という​ことに​なり​ます。

図​6​に​示す​LabVIEW​ブロック​ダイ​ア​グラム​は、​パイプライン​処理​の​例​を​示し​てい​ます。​表示​さ​れる​For​ループ​は​黒い​枠​で、​ステージ​S1、​S2、​S3、​S4​が​含​まれ​てい​ます。​これ​は​逐次​的​に​実行​する​アルゴリズム​の​関数​を​示し​てい​ます。​LabVIEW​は​構造​化​さ​れ​た​データ​フロー​言語​なので、​各​関数​の​出力​は​ワイヤ​を​通​って​次​の​関数​の​入力​に​渡​さ​れ​ます。


図​6. LabVIEW​で​の​パイプライン​処理

小さい​ドット​の​上​に、​フィードバック​ノード​が​矢印​で​表示​さ​れ​ます。​フィードバック​ノード​は、​関数​が​異なる​パイプライン​ステージ​に​分割​さ​れ​て​いる​こと​を​意味​し​ます。​同じ​コード​を​パイプライン​処理​しない​場合、​見た目​は​似​てい​ます​が​フィードバック​ノード​が​ありま​せん。​この​テクニック​が​よく​用​い​られる​例​として​は、​高速​フーリエ​変換​(FFT)​で​一度に​1​ステップ​ずつ​操作​が​必要​な​スト​リー​ミン​グ​アプリケーション​が​あり​ます。

構造​格子

物理​モデル​が​関係​する​多く​の​演算​では、​構造​格子​パターン​を​使用​し​ます。​この​パターン​では、​各​反復​で​2D(ND)​クリ​ッド​を​計算​し、​アップデート​さ​れ​た​各​格子​値​は、​図​8​に​示す​よう​に​その​隣接​格子​の​関数​となり​ます。


図​7. 構造​格子

 

構造​格子​の​並列​バージョン​では、​格子​を​サブ​格子​に​分割​し​て​各​サブ​格子​を​個々​に​実行​し​ます。​ワーカー​間​の​通信​は、​隣接​格子​の​幅​情報​のみ​に​なり​ます。​並列​処理​効率​は、​面積​の​周囲​の​長​さ​に対する​比​の​関数​となり​ます。

例えば、​下図​の​ブロック​ダイ​ア​グラム​は、​境界​条件​が​常に​変化​する​熱​伝導​方程式​を​解く​こと​が​でき​ます。


図​8. LabVIEW​で​の​構造​格子

表示​さ​れる​16​個​の​アイコ​ン​は、​特定​の​格子​サイズ​の​ラ​プラス​方程式​を​解く​こと​の​できる​タスク​を​表​し​てい​ます。​ここ​で​ラ​プラス​方程式​は​熱​伝導​方程式​を​解く​ため​の​もの​です。​16​個​の​タスク​は、​16​個​の​コア​に​マッピング​さ​れ​ます。​それらの​コア​は、​1​回​の​ループ​反復​ごと​に​境界​条件​を​交換​し、​この​プロセス​により​グローバル​解​が​得​ら​れ​ます。​小さい​ドット​の​上​に​矢印​で​表示​さ​れる​フィードバック​ノード​は、​要素​間​の​データ​の​やり取り​を​表​し​ます。​また、​その​よう​な​ブロック​ダイ​ア​グラム​は、​1、​2、​4、​8​個​の​コア​を​搭載​した​コンピュータ​に​マッピング​する​こと​も​でき​ます。​さらに​多く​の​コア​を​搭載​した​コンピュータ​に​も、​同様​の​手法​が​利用​でき​ます。

LabVIEW​で​並列​プログラミング​パターン​を​適用​する​ため​の​ストラクチャ、​VI、​ツール

While​ループ

While​ループ​と​は、​様々​な​プログラミング​パターン​(タスク​並列​性、​データ​並列​性、​パイプライン​処理、​構造​グリッド)​に​使用​できる​基本​ストラクチャ​です。​パターン​によって​は​通常​の​While​ループ​で​十分​ですが、​状況​によって​は​特別​な​タイプ​の​While​ループ​(タイミング​ループ​など)​の​方​が​適​し​て​いる​場合​も​あり​ます。

シフトレジスタ​と​フィードバック​ノード

上述​の​フィードバック​パイプライン​処理​では、​シフトレジスタ​ま​は​た​フィードバック​ノード​(ここ​では​どちら​も​同じ​動作​を​し​ます)​を​使用​する​必要​が​あり​ます。

並列​For​ループ

並列​For​ループ​を​使用​すると、​コード​を​実行​する​並列“ワーカー”の​数​を​自動​で​設定​し​て、​暗黙​的​な​並列​性​を​実現​でき​ます。​各​プロセッサ​コア​用​に​ワーカー​を​作成​する​こと​で、​最大限​の​並列​実行​が​行​え​ます。

並列​For​ループ​は、​反復​間​で​の​依存性​が​なく、​ループ​で​何​度​も​繰り返し​実行​する​必要​の​ある​高​負荷​の​操作​に​は​有効​な​方法​です。​ただし​依存性​が​ある​場合​は、​逐次​的​に​実行​する​こと​が​想定​さ​れ​て​いる​と​考え​られる​ため、​並列​For​ループ​を​使用​すべ​き​では​ありま​せん。​その​場合​は、​パイプライン​処理​によって​並列​性​を​確保​する​こと​が​でき​ます。

タイミング​ループ

タイミング​ループ​は、​マルチ​コア​ハードウェア​構成​に​基​づ​い​て​パフォーマンス​を​最適​化​する​の​に​役立つ​特殊​な​特性​を​備え​た​While​ループ​の​1​つ​です。​例えば、​通常​の​While​ループ​が​マルチスレッド​を​扱う​の​と​異​なり、​タイミング​ループ​内​の​コード​は​全て​シングルス​レッド​で​実行​し​ます。​これ​は​直観​に​反​した​方法​の​よう​に​見える​ため、​マルチ​コア​システム​で​の​シングルス​レッド​の​実行​が​望ましい​理由​が​わ​から​ない​人​も​多い​で​しょう。​具体​的​に​は、​これ​は​リアルタイム​システム​の​便利​な​特性​で​あり、​キャッシュ​の​最適​化​が​重要​な​部分​です。​シングルス​レッド​で​実行​する​以外​に​も、​この​ループ​では​プロセッサ​親和性​を​設定​する​こと​が​でき​ます。​これ​は、​スレッド​を​特定​の​CPU​に​割り当てる​(そして​キャッシュ​を​最適​化​する)​ため​の​メカニズム​です。

通常​の​While​ループ​内​で​問題​なく​動作​する​並列​パターン​(データ​並列​性​や​パイプライン​処理​など)​は、​シングルス​レッド​では​並列​実行​が​でき​ない​ため、​タイミング​ループ​では​動作​しま​せん。​ただし、​例えば​複数​の​タイミング​ループ​なら​その​よう​な​テクニック​も​実行​でき​ます。​パイプライン​処理​では​1​つ​の​タイミング​ループ​が​パイプライン​の​固有​の​ステージ​を​表​し、​ループ​間​で​FIFO​により​データ​転送​が​行​われ​ます。

キュー​と​RT FIFO

複数​の​ループ​間​で​データ​を​同期​する​の​に​重要​な​の​が、​キュー​です。​例えば、​生産​者/​消費者​アーキテクチャ​の​実装​に​使用​でき​ます。​生産​者/​消費者​アーキテクチャ​は​並列​プログラミング​に​固有​の​もの​では​なく、​むしろ​一般​の​プログラミング​アーキテクチャ​で​ある​ため、​本​ドキュメント​では​特に​触れ​てい​ま​せん。​ただし​マルチ​コア​CPU​でも​CPU​の​消費量​を​減らす​の​に​非常​に​役​立ち、​ループ​と​キュー​を​併せて​使用​する​こと​で​全て​可能​となり​ます。

キュー​を​用​い​て​ループ​間​で​データ​を​共有​する​場合、​リアルタイム​性​が​ありま​せん。​リアルタイム​性​が​要求​さ​れる​場合​は、​RT FIFO​を​使用​し​て​くだ​さい。

CPU​プール​予約​VI

LabVIEW Real-​Time​固有​の​機能​として、​CPU​を​特定​の​スレッドプール​用​に“予約”できる​CPU​プール​VI​が​あり​ます。​これ​も​キャッシュ​機能​を​最適​化​する​ため​の​メカニズム​です。

例えば、​何​度​も​繰り返し​極力​短時間​で​実行​する​こと​を​目的​と​した​アプリケーション​を​ク​アッ​ド​コア​システム​で​実行​する​こと​を​想定​し​て​み​て​くだ​さい。​データセット​が​CPU​キャッシュ​に​納まる​サイズ​で​ある​と​仮定​し​て、​この​よう​な​操作​は​キャッシュ​で​実行​する​の​に​最適​です。​実際​に​キャッシュ​で​の​操作​は、​コード​を​並列​化​し​て​4​つ​の​CPU​全て​を​使用​する​より​も​効果​的​かも​し​れ​ま​せん。​そのため、​4​つ​の​CPU​全て​(0-3)​で​並列​タスク​を​実行​する​よう​OS​を​スケジューリング​する​の​では​なく、​CPU 0​と​2​のみ​という​よう​に、​OS​スケジューラ​で​2​つ​の​CPU​だけ​を​予約​する​こと​も​でき​ます。​(ク​アッ​ド​コア​に​は​たいてい​CPU 0​と​1​の​間​に​大きな​共有​キャッシュ​が​あり、​CPU 2​と​3​の​間​に​も​大きな​共有​キャッシュ​が​あり​ます。)​CPU​を​予約​する​こと​で、​確実​に​データ​が​キャッシュ​内​に​残り、​2​つ​の​大​容量​の​共有​キャッシュ​を​全て​その​操作​に​使用​できる​よう​に​なり​ます。

CPU​情報​VI

CPU​情報​VI​は、​LabVIEW​アプリケーション​が​実行​し​て​いる​システム​に関する​特定​の​情報​を​提供​する​もの​です。​この​情報​は、​アプリケーション​が​多数​の​コンピュータ​(デュアル​コア、​ク​アッ​ド​コア、​オクタルコア​など)​に​実装​さ​れる​可能性​が​ある​場合、​特に​便利​です。

CPU​情報​VI​を​使用​すると、​アプリケーション​は​「CPU​の​コア​数」​など​の​CPU​情報​を​読み取り、​その​結果​を​並列​For​ループ​に​送り込み​ます。

例えば、​デュアル​コア​コンピュータ​上​で​アプリケーション​が​実行​し​て​いる​場合、​CPU​の​コア​数​は​2​となり、​並列​For​ループ​の​最適​数​も​2​となり​ます。​これ​により、​ユーザ​が​CPU​コア​数​を​指定​し​なく​て​も、​自動的​に​使用​ハードウェア​に​最適​な​コード​に​なり​ます。

デスク​トップ​実行​トレース​ツール​キット​と​Real-​Time​実行​トレース​ツール​キット

トレース​は、​マルチ​コア​アプリケーション​の​デバッグ​として​非常​に​有効​な​方法​で​あり、​デスク​トップ​システム​でも​リアルタイム​システム​でも​実行​でき​ます。​デスク​トップ​実行​トレース​ツール​キット​と​Real-​Time​実行​トレース​ツール​キット​の​詳細​について​は、​製品​マニュアル​を​参照​し​て​くだ​さい。

まとめ

プログラマ​は、​特定​の​アプリケーション​に​適切​に​対応​できる​プログラミング​パターン​を​採用​する​こと​が​重要​です。​本​ドキュメント​では、​タスク​並列​処理、​データ​並列​処理、​パイプライン​処理、​構造​格子​について​説明​しま​した。

それらの​パターン​を​フル​に​活用​する​に​は、​様々​な​ストラクチャ、​VI、​デバッグ​ツール​を​導入​し​て、​最適​性能​を​実現​する​必要​が​あり​ます。