汎用プログラミング環境を用いたGPGPU に関する研究

汎用プログラミング環境を用いた GPGPU
に関する研究
大島 聡史
電気通信大学 大学院情報システム学研究科
博士 (工学) の学位申請論文
2009 年 3 月
汎用プログラミング環境を用いた GPGPU
に関する研究
博士論文審査委員会
主査 本多 弘樹 教授
委員 曽和 将容 教授
委員 多田 好克 教授
委員 吉永 努 准教授
委員 近藤 正章 准教授
著作権所有者
大島 聡史
2009 年
Study of GPGPU Using Commodity Programming Environment
Satoshi OHSHIMA
Abstract
GPU (Graphics Processing Unit) is suitable for parallel processing and has high
performance than existing CPU (Central Processing Unit), so GPU is now being
used for various applications. Many applications are getting speed-up using GPGPU
(General-Purpose computation using GPUs), while the difficulty of GPU programming is under problem.
Application programmer must use special programming languages and libraries
for GPGPU programming to create programs running on GPUs, but using such
languages and libraries are difficult for programmers because it is necessary to learn
GPU’s architecture, execution model of GPU, and programming language’s specification. Therefore it is a challenge of GPGPU to make GPGPU programming
easy.
In this paper, two approaches which make using GPGPU easy with commodity
parallel programming environments are proposed.
The first approach is a “parallel computation library” which hides parallel programming from application programmers by offering parallelized computation kernels. This library has APIs similar to CPU’s libraries and computes using CPUs
and GPUs. To get a high performance in anytime, this library divides the problem and executes them in parallel using CPUs and GPUs when problem size is
big enough and a balance between CPU’s performance and GPU’s performance is
suitable, and uses an only CPU in other cases with appropriate balance suggested
by a tuning-script and a divide-module. “GPUPC GEMM Library” is a parallel
matrix-matrix multiplication library based on this approach. This library can get a
high performance with GPGPU systems without parallel programming.
The second approach is a “parallel programming environment” which offers a parallel programming environment like as existing parallel programming environments
used on CPU. “OMPCUDA” is an OpenMP implementation for CUDA based on
this approach. OMPCUDA can execute parallel regions of OpenMP programs on
a GPU, so that programmers can execute parallel programs on a GPU without
learning and writing GPU-specific parallel programs.
Contributions of this study are proposal of new approaches which make using
GPGPU easy for many application programmers and evaluation of the effectiveness
of approaches by implementing a library (GPUPC GEMM Library) and a system
(OMPCUDA). Results of this study are significant from the perspective of indicating
how easy-to-use environment for application programmers in computing systems
having GPU should be.
汎用プログラミング環境を用いた GPGPU に関する研究
大島 聡史
概要
GPU (Graphics Processing Unit) は既存の CPU (Central Processing Unit) と比
べて並列処理による高い演算性能を持つため,画像処理以外の処理を含めた様々な
用途への利用が進められている.GPU を用いた汎用演算 GPGPU (General-Purpose
computation using GPUs) により様々なアプリケーションの高速化が行われている
中,GPU プログラミングの難しさが問題となっている.
現在アプリケーションプログラマが GPU 上で動作するプログラムを作成するに
は,GPU (GPGPU) 専用のプログラミング言語やライブラリ (プログラミング環境)
を用いる必要があり,GPU のアーキテクチャや GPU 向けのプログラミング環境で
利用される実行モデルについて理解する必要がある.このようにアプリケーション
プログラマにとって GPGPU プログラミングは難しく手間がかかるため,GPGPU
を容易に利用できるようにすることは GPGPU の大きな課題である.
本研究では,現在 CPU を対象とした並列化プログラミングに利用されている汎
用プログラミング環境を GPGPU でも利用可能としアプリケーションプログラマに
対する GPGPU の利用を容易にすることを提案する.
また提案に対する具体的なアプローチとして “並列計算ライブラリによるアプロー
チ” と “並列プログラミング環境によるアプローチ” の 2 つのアプローチを挙げ,そ
れぞれのアプローチに基づきライブラリや処理系を実装して有効性の検証を行った.
各アプローチの概要と得られた成果は以下の通りである.
1. 並列化された計算カーネルを提供することで並列化プログラミング自体を隠
蔽する並列計算ライブラリ (並列計算ライブラリによるアプローチ)
• CPU 単体で実行されるライブラリと同様の API を持つ GPU 向けのライ
ブラリを提供し,GPU に関する知識がないアプリケーションプログラマ
でも GPU の持つ高い並列演算性能を活用可能とすることを目的とした.
• 既存の GPU 向け並列計算ライブラリには “CPU 単体で実行されるライ
ブラリと同様の API を持つ GPU 向けのライブラリを提供するだけでは
対象問題のデータ規模や CPU-GPU 間での負荷分散に関する課題があり
良い性能が得られない可能性がある” という問題点があることを指摘し
た.また解決のために “CPU 単体で実行されるライブラリと同様の API
を持ちながら,対象問題のデータ規模が小さい場合には CPU のみで演算
を行い,データ規模が大きい場合には CPU と GPU の性能バランスにあ
わせて CPU と GPU で適切な問題分割・並列実行を行う機構を持つ並列
計算ライブラリ” を提案し,実装方法や実装上の問題についての検討を
行った.
• 提案に基づき行列積和計算を対象としたライブラリ “GPUPC GEMM Library” を実装し,テストプログラムやベンチマークプログラムを用いて
実装の手間と性能について評価を行った.
• 評価の結果,GPUPC GEMM Library が備えるチューニングスクリプト
およびスクリプトの出力結果にあわせて適切に問題分割を行う問題分割
機構によって,本ライブラリを利用するアプリケーションプログラマが
GPU に関する知識や実行対象計算機システムの CPU と GPU の性能バ
ランスを気にする必要なく GPU の持つ高い並列演算性能を常に容易に利
用できることを確認した.
2. 並列計算アルゴリズムを実装するための並列化プログラミング言語や並列化プ
ログラミング用のライブラリ (並列化プログラミング環境によるアプローチ)
• CPU を対象とした並列化プログラミング環境を GPU プログラミングに
も利用できるようにすることで,アプリケーションプログラマにとって
GPGPU 専用のプログラミング環境の習得などの手間を削減し,GPGPU
を容易に利用可能にすることを目的とした.
• 既存の CPU 向け並列化プログラミング環境を GPGPU プログラミング
にも利用可能とすることを提案し,典型的な GPU のハードウェア構成と
既存の CPU 向け並列化プログラミング環境との対応付けを検討した.さ
らに GPGPU 環境の 1 つである CUDA に対してより具体的な対応付けを
検討した.
• 検討に基づき CUDA 向けの OpenMP 処理系 “OMPCUDA” を実装し,テ
ストプログラムを用いて利用の手間と性能について評価を行った.
• 評価の結果,OMPCUDA は OpenMP の典型的な問題であるループの並
列化に対して,OpenMP を用いた簡単な並列化記述によって GPU 上の多
数の演算器を有効に利用することで高い性能が得られることを確認した.
以上の 2 つのアプローチにより,汎用プログラミング環境を用いて GPGPU を利
用可能とすることで,アプリケーションプログラマに対する手間を増加させること
なく GPGPU の高い並列演算性能を容易に利用可能とできることを示した.
本研究の今後の課題としては,アプリケーションプログラマにとっての手間の増
加と得られる性能とのトレードオフに関する課題と,本研究の成果を GPU 以外の
ハードウェア (GPU 以外の SIMD 型アクセラレータ) や OpenCL と比較することを
挙げた.
本研究の貢献は,GPGPU を多くのアプリケーションプログラマが容易に活用で
きるようにするアプローチを提案し,提案に基づいてライブラリや処理系の実装を
行い有効性を実証した点にある.この成果は,今後さらに普及が広がると考えられ
る GPU を搭載した計算機システムにおけるアプリケーションプログラマにとって
使いやすい利用環境のあり方を示すものとして意義がある.
目次
i
目次
1
2
序論
1
1.1
本研究の背景と目的
. . . . . . . . . . . . . . . . . . . . . . . . . . .
1
1.2
本研究のアプローチ
. . . . . . . . . . . . . . . . . . . . . . . . . . .
3
1.3
本論文の構成 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
6
GPU に関する技術動向と本研究の位置づけ
2.1
8
GPU のアーキテクチャとプログラミング環境 . . . . . . . . . . . . .
8
2.1.1
GPU と GPGPU . . . . . . . . . . . . . . . . . . . . . . . . .
8
2.1.2
GPGPU プログラミング環境
. . . . . . . . . . . . . . . . . . 10
2.2
SIMD 型アクセラレータとしての GPU . . . . . . . . . . . . . . . . . 15
2.3
プログラミング環境に関する研究の動向 . . . . . . . . . . . . . . . . 20
2.4
2.3.1
GPU 向けのプログラミング環境 . . . . . . . . . . . . . . . . . 20
2.3.2
CPU 向けのプログラミング環境 . . . . . . . . . . . . . . . . . 25
SIMD 型アクセラレータやプログラミング環境に関する研究と本研究
との関係 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
3
並列計算ライブラリによるアプローチ
31
3.1
CPU と GPU を用いて問題分割・並列実行を行うライブラリの提案 . 31
3.2
CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装 . 35
3.2.1
CPU と GPU を用いた並列処理の実装 . . . . . . . . . . . . . 35
3.2.2
CPU と GPU による適切な問題分割を行うための仕組み . . . 36
3.2.3
複数の CPU や複数の GPU を搭載した計算機システム向けの
実装 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40
3.3
GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実
行を行う行列計算ライブラリ の設計と実装 . . . . . . . . . . . . . . . 47
3.4
3.3.1
ライブラリが対象とする範囲 . . . . . . . . . . . . . . . . . . 47
3.3.2
ライブラリの設計と実装 . . . . . . . . . . . . . . . . . . . . . 49
GPUPC GEMM Library の評価 . . . . . . . . . . . . . . . . . . . . . 59
3.4.1
単純な行列積和計算を用いた性能確認
. . . . . . . . . . . . . 59
目次
4
ii
3.4.2
HPL ベンチマークを用いた性能確認 . . . . . . . . . . . . . . 70
3.4.3
利用の手間と得られる性能に関する評価 . . . . . . . . . . . . 75
並列化プログラミング環境によるアプローチ
4.1
77
既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログ
ラミングの提案 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 77
4.2
4.3
5
4.1.1
既存の CPU 向け並列化プログラミング環境と GPGPU . . . . 78
4.1.2
既存の CPU 向け並列化プログラミング環境と CUDA . . . . . 83
OMPCUDA : CUDA 向け OpenMP の提案と実装 . . . . . . . . . . . 98
4.2.1
全体の構成 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 98
4.2.2
プログラム変換機構の実装 . . . . . . . . . . . . . . . . . . . . 103
4.2.3
実行時ライブラリの実装 . . . . . . . . . . . . . . . . . . . . . 105
OMPCUDA の評価 . . . . . . . . . . . . . . . . . . . . . . . . . . . . 111
4.3.1
行列積を用いた性能確認 . . . . . . . . . . . . . . . . . . . . . 111
4.3.2
円周率の計算 (グレゴリ級数) を用いた性能確認 . . . . . . . . 115
4.3.3
実装の手間や記述の容易性に関する評価 . . . . . . . . . . . . 122
結論
125
5.1
研究成果の概要 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 125
5.2
今後の課題
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 132
謝辞
135
参考文献
136
A 付録 1: CUDA を用いた実装のソースコード
148
図目次
iii
図目次
1
既存の CPU 向けプログラミング環境と GPU . . . . . . . . . . . . . .
4
2
画像処理と並列計算
9
3
画像描画処理と汎用演算 . . . . . . . . . . . . . . . . . . . . . . . . . 11
4
単純な配列加算プログラムの例 (一部抜粋) . . . . . . . . . . . . . . . 13
5
CSX のハードウェア構成図 . . . . . . . . . . . . . . . . . . . . . . . 16
6
Cell のハードウェア構成図 . . . . . . . . . . . . . . . . . . . . . . . . 18
7
ストリーミング言語の概念 . . . . . . . . . . . . . . . . . . . . . . . . 21
8
BrookGPU を用いたプログラムの例 . . . . . . . . . . . . . . . . . . . 22
9
RapidMind を用いたプログラムの例 . . . . . . . . . . . . . . . . . . 23
10
SPRAT を用いたプログラムの例 . . . . . . . . . . . . . . . . . . . . 24
11
典型的な GPGPU プログラムの処理手順 . . . . . . . . . . . . . . . . 32
12
スレッドを用いた並列実行の失敗例 . . . . . . . . . . . . . . . . . . . 37
13
提案するライブラリの構造 . . . . . . . . . . . . . . . . . . . . . . . . 38
14
複数 CPU を用いた実装の例 1 . . . . . . . . . . . . . . . . . . . . . . 42
15
複数 CPU を用いた実装の例 2 . . . . . . . . . . . . . . . . . . . . . . 43
16
複数 CPU と複数 GPU を用いた実装の例 1 . . . . . . . . . . . . . . . 45
17
複数 CPU と複数 GPU を用いた実装の例 2 . . . . . . . . . . . . . . . 46
18
BLAS における GEMM の関数定義 . . . . . . . . . . . . . . . . . . . 48
19
ベクトル演算を利用した行列積の例 . . . . . . . . . . . . . . . . . . . 51
20
ベクトル演算が利用できない行列積の例 . . . . . . . . . . . . . . . . 52
21
問題分割方法 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53
22
ライブラリの設計 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
23
複数 CPU・複数 GPU 対応版 GPUPC GEMM Library の構造 . . . . 57
24
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 1) . 61
25
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 2) . 62
26
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 3) . 63
27
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境
. . . . . . . . . . . . . . . . . . . . . . . . . . .
1:DGEMM) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 65
図目次
28
iv
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境
2:DGEMM) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 66
29
各問題サイズに対する実行時間と CPU に対する実行時間比 (環境
3:DGEMM) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
30
2CPU+2GPU での性能評価 (SGEMM) . . . . . . . . . . . . . . . . . 69
31
HPL の性能パラメタ (括弧内は初期値) . . . . . . . . . . . . . . . . . 71
32
CPU による HPL の性能調査:問題サイズと性能 (環境 1) . . . . . . . 72
33
CPU による HPL の性能調査:ブロックサイズと性能 (環境 1) . . . . 72
34
GPUPC GEMM Library を用いた HPL の実行結果 (環境 1) . . . . . . 74
35
典型的な GPU のハードウェア構成 . . . . . . . . . . . . . . . . . . . 79
36
CUDA のハードウェアモデル . . . . . . . . . . . . . . . . . . . . . . 85
37
CUDA のメモリモデル . . . . . . . . . . . . . . . . . . . . . . . . . . 88
38
SIMD プログラミングと CUDA との対応付け . . . . . . . . . . . . . 90
39
スレッドライブラリを用いたマルチスレッドプログラミングと CUDA
との対応付け . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 92
40
OpenMP を用いた並列化プログラミングと CUDA との対応付け . . . 94
41
通信ライブラリを用いたマルチプロセスプログラミングと CUDA と
の対応付け
. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96
42
OpenMP と OMPCUDA の実行モデルとの対応付け . . . . . . . . . . 100
43
Omni と OMPCUDA の関係および OMPCUDA の構成 . . . . . . . . 101
44
プログラム変換機構の処理手順 . . . . . . . . . . . . . . . . . . . . . 104
45
OMPCUDA における for ループのスケジューリング例 . . . . . . . . 107
46
行列積のソースコード 1 (3 重ループ) . . . . . . . . . . . . . . . . . . 113
47
行列積のソースコード 2 (2 重ループ) . . . . . . . . . . . . . . . . . . 113
48
行列積の実行時間 1 (問題サイズ 1024) . . . . . . . . . . . . . . . . . 114
49
行列積の実行時間 2 (問題サイズ 1024) . . . . . . . . . . . . . . . . . 116
50
円周率計算のソースコード . . . . . . . . . . . . . . . . . . . . . . . . 116
51
円周率の求解の実行時間 1 (問題サイズ 0x10000000)
. . . . . . . . . 118
52
円周率の求解の実行時間 2 (問題サイズ 0x10000000)
. . . . . . . . . 120
53
円周率の求解の実行時間 3 (問題サイズ 0x10000000)
. . . . . . . . . 121
表目次
v
表目次
1
SIMD 型アクセラレータの基礎的なデータ . . . . . . . . . . . . . . . 15
2
評価環境 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 59
3
評価環境 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 111
4
行列積のプログラム行数と GPU に関する知識の必要性 . . . . . . . . 122
5
円周率求解のプログラム行数と GPU に関する知識の必要性
. . . . . 124
1
序論
1
1.1
本研究の背景と目的
気象,医療,宇宙など様々な分野において,高性能な計算機を用いた計算が必須
となっている [1, 2, 3].これらの分野では高速,高精度,大規模な計算が要求され
るため,より高性能な計算機が必要とされている [4, 5, 6, 7, 8].また近年では個人
ユースのパーソナルコンピュータ (PC) においても動画像処理など計算量の多い処
理を行う機会が増加し,高性能な計算機の要求が高まっている.
計算機の演算性能に大きな影響を与えるプロセッサ (CPU) の性能に注目すると,
従来はプロセスの微細化とクロック周波数の向上によりその性能を向上させてきた
ことがわかる.例えば 1993 年の Pentium プロセッサが 800nm プロセスルール・ク
ロック周波数 60MHz だったのに対して,2005 年の Pentium4 プロセッサ (Prescott
コア) は 90nm プロセスルール・クロック周波数 3.80GHz に達している [9].
しかしながら今日のプロセッサにおいては,微細化が進むとリーク電流が増加し
消費電力が増加してしまうことや,微細化が原子の大きさによる物理的限界に近づ
きつつあるため微細化そのものが難しくなっていること,またクロック周波数の向
上が発熱量や消費電力の増加につながることなどが問題となっている.その結果,
2008 年末の時点で利用されている CPU のプロセスルールは 2005 年のプロセスルー
ルの半分である 45nm にとどまっており,またクロック周波数についても,適切な
冷却機構の元で運用されるサーバ向け CPU が 5GHz 以上の周波数を達成している
[10] ものの,コンシューマ向けの多くの CPU では 4GHz 未満の周波数にとどまって
いるのが現状である.
今日における CPU の性能への関心は,これまでのシングルコア CPU によるシン
グルスレッドの性能から,複数のコアを 1 パッケージに収めたマルチコア CPU の性
能へと向けられている.2008 年末の時点では,2 つから 4 つのコアを搭載したマル
チコア CPU (デュアルコア CPU・クアッドコア CPU) が主流となっており,主要な
CPU ベンダーは 4 つ以上のコアを搭載した CPU の開発・リリースに注力している
[11, 12].
一方で,既存の CPU と比べてより高い並列度を持ち理論演算性能や電力あたり
性能が高い新しいハードウェアへの注目が高まっている.その中でも,主に PCI-
1.1 本研究の背景と目的
2
Express 接続のビデオカードとして提供されている画像処理用のハードウェア “GPU
(Graphics Processing Unit)” は,既存の CPU と比べて多数の演算を同時に実行可
能であり高い理論演算性能を持つため注目されている.特に,ハイエンドモデルの
GPU では同時に 200 以上の演算が可能であり,また最大理論演算性能は 1TFLOPS
に達している [13, 14].近年では GPU を用いた汎用演算 “GPGPU (General-Purpose
computation using GPUs)” [15, 16, 17, 18] によりプログラムの高速化を行った旨の
報告が相次いでいる [19, 20, 21, 22, 23].
今日の GPU は高速・高解像度な画面出力および動画再生支援機能などの要求に
ともない多くの PC に搭載されており,広く普及が進んでいるハードウェアである.
そのため GPGPU を利用可能な計算機システムの普及が進んでいる一方,GPGPU
プログラミングの難しさが GPGPU の普及における大きな問題となっている.現在
提供されている GPGPU 向けのプログラミング言語やライブラリ (以下本論文では,
プログラミング言語やライブラリをまとめてプログラミング環境と呼ぶ) は,GPU
のハードウェアアーキテクチャと強く関連づけられた言語仕様や,既存のプログラ
ミング手法とは異なる新たな実行モデルを習得しなければ利用できないため,アプ
リケーションプログラマにとっては利用に手間がかかり,大きな負担となっている.
現在の GPU は,ハードウェアアーキテクチャやプログラミング言語など新たな知
識や技術を習得し,手間のかかる実装を行うことではじめて高い性能を達成するこ
とが可能なハードウェアである.手間をかけずに GPU の性能を活用するのは難し
い一方で,かけた手間に対して性能が得られないことも少なくはない.アプリケー
ションプログラマが現実的にかけられる手間には限度があるうえに,特定のハード
ウェアでのみ有効な知識や技術の習得は活用できる範囲が限られるという理由で敬
遠される可能性もある.そのため GPU の性能を活用できるユーザは一部のパワー
ユーザに限られており,一般の多くのアプリケーションプログラマにとって GPU の
利用は難しいのが現状である.
そこで本研究では,既存の CPU 向けプログラミングに利用されている汎用プロ
グラミング環境を用いて GPGPU を利用できるようにすることで,アプリケーショ
ンプログラマが GPGPU を容易に活用可能とすることを目指す.
1.2 本研究のアプローチ
1.2
3
本研究のアプローチ
アプリケーションプログラマにとって GPGPU の利用が難しい原因として,GPGPU
を利用するためにハードウェアアーキテクチャと強く結びついた言語やライブラリ
を利用する必要があることが挙げられる.
既存の CPU 向けプログラミングにおいては,多くのアプリケーションプログラマ
は機械語やアセンブラ言語といった低級言語ではなく,C/C++や Java などの高級
言語を利用している.高級言語はハードウェアアーキテクチャとの結びつきが弱い
ため,アプリケーションプログラマは対象とする計算機システムの詳細なハードウェ
アアーキテクチャの知識がなくてもプログラムを記述し動かすことができる.また,
多くのコンパイラやインタプリタは複数の CPU アーキテクチャに対応しているた
め,アプリケーションプログラマは CPU の違いを気にせずプログラミングを行う
ことが可能であり,最適化コンパイラによって同一のソースコードから対象 CPU ご
とに最適化された実行ファイルを得ることもできる.
さらに,ソースコードを再利用するためやアルゴリズムを実装する手間を削減す
るため,そして最適化プログラミングの手間を削減するために,様々なライブラリ
1 .
が利用されている (図 1-°)
一方で現在 GPGPU 向けに提供されているプログラミング環境は,GPGPU 専用
の言語やライブラリ,もしくは新しい実行モデルのプログラミング環境である (図
2 2 章) .これらを用いて GPGPU プログラミングを行うには,GPU のハード
1-°,
ウェアアーキテクチャに関する知識や,新しいプログラミング言語の言語仕様や実
行モデルの理解が必要であるため,アプリケーションプログラマにとって手間がか
かり負担が大きいことが問題となっている.
これらの問題に対して本研究では,GPU が並列処理による高い演算性能を持つ
ハードウェアであることから,現在 CPU 向けの並列化プログラミングに利用され
ている汎用プログラミング環境が GPGPU プログラミングにも利用できれば,アプ
リケーションプログラマが GPGPU を容易に利用できると考えた.そこで現在 CPU
向けの並列化プログラミングに利用されている汎用プログラミング環境として “並
列化された計算カーネルを提供することで並列化プログラミング自体を隠蔽する並
列計算ライブラリ (並列計算ライブラリ)” と “並列計算アルゴリズムを実装するた
1.2 本研究のアプローチ
図 1: 既存の CPU 向けプログラミング環境と GPU
4
1.2 本研究のアプローチ
5
めの並列化プログラミング言語や並列化プログラミング用のライブラリ (並列化プ
ログラミング環境)” の 2 つを挙げ,これらを用いてアプリケーションプログラマが
GPGPU を容易に利用可能とする方法を提案する.
なお本研究で対象とする計算機システムは,シングルコアまたはマルチコアの CPU
が 1 個と GPU が 1 枚から数枚搭載された 1 台の計算機からなる計算機システムとす
る.複数台の計算機からなる計算機システムについては,基本的には各計算機の性
能が GPU により向上したものとみなした上で複数台の計算機向けの手法を用いる
ことで対応できると考えられるため,本研究では扱わない.
アプローチ 1 : 並列計算ライブラリ
アプリケーションプログラマに対して容易に GPU の並列演算性能を利用できる
ようにする方法として,GPU 向けに並列化された計算カーネルを提供する並列計算
ライブラリを作成し,GPU 向けの並列化プログラミングを行わなくても GPU の持
つ並列演算性能を利用できるようにするという方法が考えられる.この方法では並
列化プログラミング自体を隠蔽することができるため,アプリケーションプログラ
マは API さえ理解していれば GPU の持つ並列演算性能を利用することが可能とな
り,アルゴリズムの実装や GPGPU プログラミング習得の手間を大きく削減できる
と期待できる.
しかしながら,単に GPU 上での並列計算と CPU-GPU 間でのデータ転送や GPU
の制御処理をまとめただけのライブラリでは,対象問題のデータ規模が小さい場合
などいくつかの場合に高い性能が得られない可能性が生じてしまう.
そこで本アプローチでは,こうした性能が得られないという問題を解決し常に高
い性能を得ることができる並列計算ライブラリの提案と設計を行う.また提案した
アプローチに基づいて CPU と GPU を用いて問題分割・並列実行を行う数値計算ラ
イブラリ “GPUPC GEMM Library” を実装し,テストプログラムやベンチマークを
用いて利用の手間や性能の面から提案アプローチの評価を行う.
1.3 本論文の構成
6
アプローチ 2 : 並列化プログラミング環境
並列計算ライブラリにより並列化プログラミング自体を隠蔽するアプローチ 1 は,
対象プログラムが典型的なアルゴリズムの組み合わせなどライブラリ化に適した処
理により支配的な場合に特に有効である.しかしながら全てのアプリケーションが
これに該当するわけではなく,アプリケーションプログラマが自ら詳細なアルゴリ
ズムの実装を行う必要があることも少なくない.
一方で既存の GPGPU プログラミング環境は,GPU のアーキテクチャや新しいプ
ログラミング言語の言語仕様などを理解しなくては利用できないため,アプリケー
ションプログラマにとって容易に利用できるとは言い難い.しかしもし既存の CPU
向けプログラミング環境を用いて GPGPU プログラムを記述することができれば,
アプリケーションプログラマは GPU のアーキテクチャや新しいプログラミング言
語の言語仕様などを習得する手間をかけずに GPGPU を利用可能となることが期待
できる.
そこで本アプローチでは,既存の CPU 向けの並列化プログラミング環境を用いた
GPGPU プログラミングを提案する.また提案したアプローチに基づいて GPGPU
環境の 1 つである CUDA 向けの OpenMP 処理系 “OMPCUDA” を実装し,テスト
プログラムを用いて利用の手間や性能の面から提案アプローチの評価を行う.
1.3
本論文の構成
本論文は 5 つの章により構成される.
第 1 章は本章であり,本研究の背景やアプローチについて述べた.
第 2 章では GPU に関する技術動向や GPGPU 向けのプログラミング環境につい
ての研究を整理し,またしばしば GPU と性能やハードウェアアーキテクチャを比
較されるいくつかのハードウェアについての確認やプログラミング環境に関する研
究についての確認を行い,本研究の位置づけを明確にする.
第 3 章では,汎用プログラミング環境を用いて GPGPU を容易に利用可能とする
ための手法として,並列計算ライブラリによるアプローチを提案し,提案に基づく
ライブラリを実装して利用の手間や性能についての評価を行う.
1.3 本論文の構成
7
第 4 章では,汎用プログラミング環境を用いて GPGPU を容易に利用可能とする
ための手法として,並列化プログラミング環境によるアプローチを提案し,提案に
基づく処理系を実装して利用の手間や性能についての評価を行う.
第 5 章では,本研究の結言として研究成果と今後の課題についてまとめ,本研究
の意義を述べる.
8
GPU に関する技術動向と本研究の位置づけ
2
本章では,本研究が対象とする GPU のアーキテクチャおよび現在 GPGPU に用
いられているプログラミング言語やライブラリなどのプログラミング環境について
確認・整理する.さらに,GPU と共通点を持ちしばしば “SIMD 型アクセラレータ”
として GPU とともに扱われる他のハードウェアや,マルチコア CPU や SIMD 型ア
クセラレータを対象として開発されているプログラミング環境について確認し,本
研究の位置づけを明確にする.
2.1
2.1.1
GPU のアーキテクチャとプログラミング環境
GPU と GPGPU
GPU は画像処理用のハードウェアである.狭義にはグラフィックスカード上の
LSI やチップセットに統合されたグラフィックスチップが GPU であり,広義にはグ
ラフィックスカードそのもの,すなわち LSI のみではなく LSI に接続されたメモリ
(DRAM) やデコーダチップなどグラフィックスカード上に搭載されたモジュールな
どもまとめて GPU と呼ばれている.また,GPU の持つ演算性能を GPU 本来の目
的である画像処理に限らず様々な処理 (汎用演算:General-Puspose computation) に
も活用するのが GPGPU (General-Purpose computation using GPUs) である.
本来 GPU に求められていた画像処理とは,古くは多色・高速・高解像度な 2 次元
の画像描画処理であり,現在ではより複雑な 3 次元の画像描画処理へと変化してき
ている.これらの画像描画処理は頂点やピクセルを単位として多数同時に処理でき
る (図 2) ことから,GPU は CPU と比べて並列演算性能を重視した性能向上が行わ
れてきた [24].
3 次元物体の陰影を表現する際などには複雑で多彩なアルゴリズムの実装が要求
されるが,アルゴリズムをハードウェアレベルで実装する場合,新たな描画アルゴ
リズムに対応するにはハードウェアを変更しなくてはならない.そこで,GPU が行
う描画処理の内容をソフトウェアプログラムによって変更可能とする機構 “プログ
ラマブルシェーダ” が利用されるようになった.
以上の結果現在の GPU は,既存の CPU と比較すると制限が多いものの様々なア
2.1 GPU のアーキテクチャとプログラミング環境
図 2: 画像処理と並列計算
9
2.1 GPU のアーキテクチャとプログラミング環境
10
ルゴリズムを実装できるだけのプログラマビリティを持ち,またハードウェアレベ
ルでの高い並列性を持つため,並列性の高い問題に対しては CPU を大きく上回る
性能を発揮可能なハードウェアとなっている.そのため GPU は,画像処理以外に
も様々な演算に対して高い性能が得られる可能性を見いだされ,GPU を用いた汎用
演算 GPGPU が注目されるようになった.
現在の GPU は,本来の用途である高度な画像処理 [25, 26] だけではなく,各種の
シミュレーション [23, 19, 27, 28] や,LU 分解 [21, 22] や FFT[29, 30] などの様々な数
値計算問題 [31, 32, 33, 34, 35],動画像変換等のマルチメディア処理 [36] など,様々
な分野で高い性能を発揮している.さらに GPU ベンダも GPU の汎用演算性能を重
視した製品開発や発表などを行っており [13, 14],今後も多くの分野で GPGPU の
活用が進むことが考えられる.
2.1.2
GPGPU プログラミング環境
初期の GPGPU では,画像描画処理の手続きと演算とを対応付けて利用していた.
すなわち,CPU から GPU 上のメモリ (主にテクスチャ) へのデータセットを入力,
プログラマブルシェーダを用いた画像描画処理を演算,GPU から CPU へのデータ
の書き戻し (描画結果の取得) を出力とみなして処理を行っていた (図 3).
一方,GPU を用いて画像描画処理を行うプログラムを作成するには,GPU の動
作タイミング制御や CPU-GPU 間の通信などを行う CPU 上で実行されるプログラ
ムを記述するために DirectX[37] や OpenGL[38] といったグラフィックス API が,ま
た GPU 内部の処理ユニットが行う処理を記述するために GPU 向けのアセンブリ言
語や HLSL,GLSL,Cg[39] といった専用の高級言語 (シェーダ言語) が用いられて
きた.
初期の GPGPU におけるプログラム作成にはこれら画像描画処理向けのプログラ
ミング環境が利用された.グラフィックス API やシェーダ言語は標準化が進んでお
り対応 GPU も多く,画像描画処理との親和性が高い.そのため画像描画処理向け
のプログラミング環境を用いた GPGPU は,現在でも画像描画処理関係の GPGPU
プログラミングでは広く用いられている.しかし,画像描画処理向けのプログラミ
ング環境を用いて汎用的な演算を記述するには,対象問題を画像描画処理プログラ
ミングに対応させる独自のプログラミング手法を習得し利用する必要がある.
2.1 GPU のアーキテクチャとプログラミング環境
図 3: 画像描画処理と汎用演算
11
2.1 GPU のアーキテクチャとプログラミング環境
12
ここで GPGPU プログラミングの例として,画像描画処理を用いた単純な配列の
加算を考える.配列の加算を実現するために必要な処理とその手順は以下の通りで
ある.
1. CPU 側では,入力データとして用いるための配列を 2 つと,出力データを格
納するための配列を 1 つ用意する.
2. GPU 側では,入力データを格納するためのテクスチャを 2 つと,描画結果を
格納するための出力用バッファ (書き込み可能設定を施されたテクスチャ) を
1 つ用意する.
3. 入力データ配列に格納されているデータを CPU から GPU へ送信し,GPU 上
のテクスチャメモリへ配置する.
4. 描画処理の出力先をフレームバッファ (書き込まれた内容が画面表示に反映さ
れるバッファ) から 2 で用意した出力用バッファへと変更し,テクスチャデー
タの読み出しと加算処理が記述されたシェーダプログラムを用いて描画処理を
行う.
5. 出力用バッファの内容を GPU から CPU へ読み出し,出力データ配列に格納
する.
これら一連の処理に対応する OpenGL と GLSL を用いたプログラムの例 (ソース
コードの一部抜粋) を図 4 に示す.このように,GPGPU プログラムを作成するには
対象アプリケーションのアルゴリズムに加えて画像処理のためのプログラミング手
法や GPU アーキテクチャについての知識が必要であり,その上プログラムの記述
量も多く,アプリケーションプログラマにとって大きな負担となってきた.
そこで近年では,画像描画処理向けのプログラミングを必要とせずに GPGPU プ
ログラミングを行える新しい言語やライブラリの研究が進められている.例えば米
NVIDIA 社の CUDA[40] や米 AMD 社の CTM[41] および Stream[42] は,GPU ベン
ダが提供する GPGPU 向けのプログラミング環境である.これらのプログラミング
環境を用いることで画像描画処理向けのプログラミング環境と比べて直接的なプロ
グラミングが可能となるとともに,GPU のアーキテクチャに適した実装を行うこと
で高い性能を得ることが可能となる.
2.1 GPU のアーキテクチャとプログラミング環境
// GPU による処理 ( 描 画 内 容 の 記 述 )
uniform samplerRECT texUnit0 , t e x U n i t 1 ;
void main ( void ) {
vec2 TexA = vec2 ( 0 . 0 , 0 . 0 ) ;
vec2 TexB = vec2 ( 0 . 0 , 0 . 0 ) ;
TexA . x= g l F r a g C o o r d . x ;
TexA . y= g l F r a g C o o r d . y ;
TexB . x= g l F r a g C o o r d . x ;
TexB . y= g l F r a g C o o r d . y ;
g l F r a g C o l o r = texRECT ( texUnit0 , TexA) + texRECT ( texUnit1 , TexB ) ;
}
// CPU による処理 ( G P U の 制 御 な ど の 記 述 )
g l u t I n i t (& argc , argv ) ; g l u t I n i t W i n d o w S i z e ( 6 4 , 6 4 ) ; // OpenGL 初期化
glutCreateWindow ( ‘ ‘ GpgpuArrayAdd ’ ’ ) ; g l e w I n i t ( ) ;
glGenFramebuffersEXT ( 1 , &f b ) ;
// T e x t u r e の 生 成 な ど
glBindFramebufferEXT (GL FRAMEBUFFER EXT, f b ) ;
glGenTextures ( 4 , nTexID ) ; g l B i n d T e x t u r e ( opt1 , t e x i d ) ;
g l T e x P a r a m e t e r i ( opt1 , GL TEXTURE MIN FILTER, GL NEAREST ) ;
glTexParameteri ( . . . . . . ) ;
glTexImage2D ( opt1 , 0 , opt2 , w, h , 0 , GL RGBA, GL FLOAT, 0 ) ;
glMatrixMode (GL PROJECTION ) ;
g l L o a d I d e n t i t y ( ) ; gluOrtho2D ( 0 . 0 , nTexCX , 0 . 0 , nTexCY ) ;
glMatrixMode (GL MODELVIEW) ;
g l L o a d I d e n t i t y ( ) ; g l V i e w p o r t ( 0 , 0 , nTexCX , nTexCY ) ;
glUseProgramObjectARB ( programObject ) ;
g l B i n d T e x t u r e (TEX OPT1, nTexID [ 0 ] ) ; // T e x t u r e へ の デ ー タ セ ッ ト
glTexSubImage2D (TEX OPT1,
...
, GL FLOAT, fDataA ) ;
glTexEnvi (GL TEXTURE ENV, GL TEXTURE ENV MODE, GL REPLACE ) ;
glFramebufferTexture2DEXT (GL FRAMEBUFFER EXT, . . . , nTexID [ 2 ] , 0 ) ;
g l A c t i v e T e x t u r e (GL TEXTURE0 ) ;
g l B i n d T e x t u r e (TEX OPT1, nTexID [ 0 ] ) ; glUniform1iARB ( texUnit0 , 0 ) ;
g l A c t i v e T e x t u r e (GL TEXTURE1 ) ; glUniform1fARB ( . . . . . . ) ;
g l D r a w B u f f e r (GL COLOR ATTACHMENT0 EXT ) ; // 描 画 処 理
g l B e g i n (GL QUADS ) ; glTexCoord2f ( 0 . 0 , 0 . 0 ) ; g l V e r t e x 2 f ( 0 . 0 , 0 . 0 ) ;
glTexCoord2f (nTexCX , 0 . 0 ) ; g l V e r t e x 2 f (nTexCX , 0 . 0 ) ;
glTexCoord2f (nTexCX , nTexCY ) ; g l V e r t e x 2 f (nTexCX , nTexCY ) ;
glTexCoord2f ( 0 . 0 , nTexCY ) ; g l V e r t e x 2 f ( 0 . 0 , nTexCY ) ; glEnd ( ) ;
g l R e a d B u f f e r (GL COLOR ATTACHMENT0 EXT ) ; // 結 果 の 取 得
g l R e a d P i x e l s ( 0 , 0 , nTexCX , nTexCY ,GL RGBA, GL FLOAT, f D a t a R e s u l t ) ;
図 4: 単純な配列加算プログラムの例 (一部抜粋)
13
2.1 GPU のアーキテクチャとプログラミング環境
14
しかしながら,GPU のハードウェアアーキテクチャは製品によって異なる部分
も多い.現在 GPGPU に利用されている主な GPU として,NVIDIA 社の GeForce・
Quadro・Tesla シリーズと AMD 社の Radeon・FireStream シリーズが挙げられる.
これらの GPU はいずれも GPU 上に多数の演算器や複数種類のメモリを搭載するな
ど共通の特徴を持ってはいるものの,各演算器の性能やメモリの種類と性能などの
詳細なハードウェア構成は異なっている.さらに CUDA や CTM および Stream と
いったプログラミング環境は言語仕様や実行モデルが GPU のアーキテクチャと強く
関連しているため,これらのプログラミング環境を利用するユーザは GPU のアー
キテクチャについて理解する必要があり,また利用可能な GPU が限られているた
め実行環境に合わせてプログラミング環境を習得して利用せねばならない.以上か
ら,GPU ベンダの提供するプログラミング環境はアプリケーションプログラマに対
して GPGPU プログラミングの難しさや手間を解消できているとは言い難い.
GPU は多くの PC に搭載されており,GPGPU を利用可能な計算機システムは広
く普及していると言える.しかしながら GPGPU プログラムの作成が難しいため多
くの GPU は演算性能を活用されておらず,GPGPU が広く普及し有効に活用され
るには,GPGPU プログラムを容易に作成することが可能な仕組みが必要である.
2.2 SIMD 型アクセラレータとしての GPU
2.2
15
SIMD 型アクセラレータとしての GPU
GPU 以外にも,既存の CPU と比べてより高い並列度を持ち,理論演算性能や電力
あたり性能が高い新しいハードウェアの開発や普及が進みつつある.特に ClearSpeed
社の浮動小数点アクセラレータカード (以下 CSX) [43] や,SCEI・東芝・IBM が共
同開発した Cell Broadband Engine および Cell Broadband Engine の強化版である
IBM の PowerXCell 8i (以下 Cell) [44] は,しばしば GPU と対比される.これらの
ハードウェアはいずれも,既存の CPU と比べて単純なコアを複数搭載することで演
算性能を高めているため,SIMD (Single Instruction Multiple Data) 処理や MIMD
(Multiple Instruction Multiple Data) 処理などの並列処理に適しており,また対象ア
プリケーションの中でも特に並列度の高い部分を重点的に高速化するアクセラレー
タとして利用されている.そのため本論文では GPU を含めたこれらのハードウェ
アを “SIMD 型アクセラレータ” と呼び,本節では SIMD 型アクセラレータのハード
ウェアアーキテクチャやプログラミング環境について概観する.
なお,各 SIMD 型アクセラレータの動作周波数や理論演算性能などの基礎的な性
能データとアプリケーションプログラマに対して提供されているプログラミング環
境については,表 1 の通りである.
表 1: SIMD 型アクセラレータの基礎的なデータ
CPU (比較用)
GPU
CSX
Cell
製品モデル
Xeon X5482
GeForceGTX280
e720
GigaAccell 180
演算器 (コア) 数
4
240
192
1(PPU)+8(SPU)
クロック周波数
3.20GHz
602MHz(Core)
250MHz
2.8GHz
(PPU,SPU 共通)
1296MHz(SP)
搭載メモリ容量
ー
1GB
8GB max
4GB
メモリ帯域幅
12.8GB/s
141.7GB/s
96GB/s
25.6GB/s
最大消費電力
150W
236W
25W
150W
CPU との接続
ー
PCIe x16(Gen2)
PCIe x16(Gen1)
EIB †
プログラミング環境
ー
CUDA
Cn
C/C++
or シェーダ言語
with 専用 SDK
理論演算性能 (単精度)
51.2GFLOPS
933GFLOPS
96GFLOPS
180GFLOPS
出典
PlatformBrief[45]
TechnicalBrief[46]
ProductBrief[47]
製品カタログ [48]
† ホスト PC との接続は PCIe x16
2.2 SIMD 型アクセラレータとしての GPU
16
CSX
CSX は,ClearSpeed 社が浮動小数点アクセラレータカードとして開発している
ClearSpeed Advance アクセラレータカードであり,PCI-Express または PCI-X 接続
の拡張カードとして提供されているハードウェアである.東京工業大学が所有する
スーパーコンピュータ TSUBAME に搭載されているアクセラレータとして知られ
ている [5].(ただし実際に TSUBAME に搭載されているのは表中の e720 より 1 世
代前の製品である.)
CSX は,電力あたりの演算性能が高いことが特徴である.200 近い多数の演算器
を低速に動作させることで,低い消費電力と高い演算性能を達成している.
CSX の構成の 1 つである e720 のハードウェア構成を図 5 に示す [49, 50, 47].e720
はアクセラレータカード上にアクセラレータチップと大容量メモリ (DRAM) を搭
載しており,アクセラレータチップ上には 96 の浮動小数点演算ユニットが搭載され
たコアが 2 つ搭載されている.
図 5: CSX のハードウェア構成図
2.2 SIMD 型アクセラレータとしての GPU
17
CSX を利用する方法としては,ベンダによって提供されている並列計算ライブラ
リを利用する方法と,CSX 用のプログラミング環境を用いてプログラムを作成する
方法とが提供されている.
CSX ではベクトル計算や行列計算,FFT など,典型的な演算に関する並列計算ラ
イブラリがベンダによって提供されている.そのためこれらの問題を高速化したい
場合には,CSX のアーキテクチャや実行モデルなどを知らずとも,提供されている
ライブラリを利用することで容易に高速化を行うことができる.
一方,アプリケーションプログラマが CSX 上で動作するプログラムを作成した
い場合には,専用のプログラミング言語である Cn 言語 [51] を利用する必要がある.
Cn 言語は C/C++言語を CSX のメモリモデルにあわせて拡張した言語である.Cn
言語には poly と mono という変数宣言時に利用可能な予約語があり,これらを用い
ることで CSX 上でのメモリ配置を明示的に指定することができる.さらに,CSX
を制御するための API を利用可能にするライブラリが提供されており,これを用い
ることで CPU-CSX 間のデータ送受信等を行うことができる.Cn 言語を用いたプロ
グラミングにおいては,CPU 上で動作するホストプログラムと CSX 上で動作する
デバイスプログラムを個別のソースコードとして記述し,各々のソースコードから
個別の実行ファイルを生成する.実行時には CSX 上でデバイスプログラムを実行し
ておき,CPU 上のホストプログラムからデバイスプログラムに対して演算対象デー
タの送信や演算結果の取得等を行うという実行の流れとなる.
Cell
Cell は,SCEI・東芝・IBM が共同開発した,既存の CPU と同程度の機能を持つ制御
用コア PPE と演算専用のより単純なコア SPE を組み合わせたマイクロプロセッサで
ある.PLAYSTATION3 のプロセッサとしてや,米 Los Alamos National Laboratory
が所有するスーパーコンピュータ Roadrunner が備えるアクセラレータカードに搭載
されているプロセッサとして [52] 知られている.また,SPE のみを搭載したメディ
ア処理用のアクセラレータカード SpursEngine としても利用されている [53].
Cell のハードウェア構成を図 6 に示す.Cell は LSI 上に 1 つの PPE と 8 つの SPE
(PLAYSTATION3 では 1 つが無効化されており 7 つの SPE が利用可能となってい
る),さらに DRAM を搭載している.PPE (PowerPC Processor Element) は,Power
2.2 SIMD 型アクセラレータとしての GPU
18
アーキテクチャを基にした 2 スレッド同時実行可能なインオーダ型のプロセッサ PPU
(PowerPC Processor Unit) を核とする,SPE の制御や外部デバイスへの入出力制
御等を受け持つ汎用プロセッサである.SPE (Synergistic Processor Element) は演
算専用のシンプルなプロセッサであり,核となる演算用ユニット SPU (Synergistic
Processor Unit),SPU ごとのローカルメモリ LS (Local Store),メインメモリや他
の SPE との通信を行う MFC (Memory Flow Controller) から構成されている.PPE
と SPE は EIB (Element Interconnect Bus) と呼ばれる高速なリングバスで接続さ
れている.こうしたハードウェア構成から,Cell は異なる種類のコアを混載した “
非対称型マルチコアプロセッサ” の一種であると言える.PPE と SPE をあわせて
200GFLOPS 程度の単精度浮動小数点演算性能を持つ.
図 6: Cell のハードウェア構成図
Cell に搭載された PPE は既存の CPU に近いハードウェアであるため,Linux な
どの OS を動作させることが可能であり,また PPE のみを用いるプログラムであれ
ば,既存の PowerPC アーキテクチャCPU 向けプログラムと同様に作成し実行する
ことができる.しかしながら Cell の持つ高い演算性能を得るには,SPE を効果的に
活用できるようにプログラムを作成する必要がある.
2.2 SIMD 型アクセラレータとしての GPU
19
SPE を活用したプログラムを作成するには,C/C++言語と各コアの制御等を行
う専用のライブラリ (SDK) を用いる.CSX と同様に,PPE 上で動作するプログラ
ムと SPE 上で動作するプログラムを個別のソースとして記述し,各々のプログラム
から個別の実行ファイルを生成する.実行時には PPE プログラムから SPE プログ
ラムを起動して利用する.
PPE と複数の SPE との間のデータ転送を考慮したプログラミングの難しさや手間
を削減し,また PPE 向けのプログラムと SPE 向けのプログラムを個別に記述する手
間を削減するために,Cell 向けのコンパイラやライブラリについての研究がいくつか
行われている.IBM の XL C/C++ for Multicore Acceleration for Linux[54] は,マル
チコア CPU や Cell に対応したコンパイラであり,OpenMP を用いたシングルソー
スによる Cell プログラム開発も可能となっている.西 Barcelona Supercomputing
Center の Cell Superscalar (CellSs)[55] も,OpenMP とは異なるが指示子の挿入によ
るシングルソースでの Cell プログラム開発を可能としている.また電気通信大学で
は POSIX スレッドを用いてシングルソースによる Cell プログラム開発を可能とす
るプログラム変換ツールを提案している [56].
2.3 プログラミング環境に関する研究の動向
2.3
20
プログラミング環境に関する研究の動向
GPU を用いることにより高い演算性能が得られる一方で,アプリケーションプロ
グラマにとって GPGPU プログラミングが難しく手間がかかることは広く認識され
ており,これまでに GPGPU プログラミングを容易にするためのプログラミング環
境に関する研究がいくつか行われてきた.またマルチコア CPU が普及し,今後さら
に多数のコアを搭載した CPU の普及が見込まれていることから,高い並列性を持
つプログラムの容易な記述に向けた新しい並列化プログラミング環境に関する研究
も行われている.本節ではこれらのプログラミング環境について確認する.
2.3.1
GPU 向けのプログラミング環境
GPGPU プログラミングが難しい大きな要因として,ハードウェアアーキテクチャ
への依存性が高い専用の言語やライブラリを用いる必要があることが挙げられる.
ハードウェアアーキテクチャや言語仕様について学習する手間を削減し GPGPU を
容易に利用できるようにするには,ハードウェアアーキテクチャへの依存性が低く
汎用性・抽象度の高いプログラミング環境が必要である.そこで近年では,ハード
ウェアアーキテクチャに依存しない新たなプログラミング環境に関する研究がいく
つか行われている.これらの研究の中から本項では,ストリームプログラミング言
語,OpenCL,コンピュータビジョンアプリケーション用のプログラミング環境の 3
つについて確認する.
ストリームプログラミング言語
ストリームプログラミング言語とは,“「ストリーム (stream) と呼ばれる入力デー
タ」に対して「カーネル (kernel) と呼ばれる演算操作」を作用するものとみなすス
トリーミングモデル” (図 7) に基づく処理 (ストリーム処理) を記述するためのプロ
グラミング言語である.近年,GPU に適しており GPGPU による高速化が期待で
きる問題としてストリーム処理が注目されており,GPU 向けストリームプログラミ
ング言語の研究が行われている.以下にストリームプログラミング言語の例をいく
つか挙げる.
米 Stanford University の BrookGPU [57] は,既存の C 言語を元に拡張を加えた
言語仕様といくつかのライブラリ関数を提供するオープンソースのストリーミング
2.3 プログラミング環境に関する研究の動向
21
図 7: ストリーミング言語の概念
言語である.BrookGPU を用いたプログラムの例を図 8 に示す.この例では,GPU
上で実行される並列計算部 (カーネル) が関数として独立に記述されていることや,
カーネルの実行前後で streamRead および streamWrite という関数を用いて明示的
に入出力の指定が行われていることが確認できる.図中のカーネルでは 2 つの変数
を加算してもう 1 つの変数への代入を行っているが,各変数は配列であり,配列の
各要素に対する演算が GPU 上の多数の演算器によって独立に並列処理される.
BrookGPU はカーネルを実行するバックエンドとして DirectX9,OpenGL,CPU,
CTM に対応している.AMD 社が BrookGPU を元にして自社の GPU 向けのストリー
ミング言語 Brook+[58] を開発しているが,これは BrookGPU の CTM をバックエ
ンドとした実装をベースにしていると考えられる.
加 RAPIDMIND 社の RapidMind[59] は,加 University of Waterloo で開発された
オープンソースのメタプログラミング言語 Sh[60] を元にしたストリーミング言語で
ある.RapidMind を用いたプログラムの例を図 9 に示す.RapidMind も BrookGPU
と同様にカーネルとカーネルへの入出力を明示的に指定していることが確認できる
一方で,BrookGPU によるカーネルの記述が既存の C/C++言語における関数の記
述に似た形式で行われていたのに対して,RapidMind によるカーネルの記述はより
独特な記述によって行われていることがわかる.
RapidMind の特徴として,実行環境として CPU や GPU だけではなく Cell にも
対応している点が挙げられる.そのため単一の言語を用いて CPU・GPU・Cell 向け
のプログラムを記述可能であり,アプリケーションプログラマにとっては実行環境
ごとにプログラミング言語を習得し直すという大きな手間が削減できると言える.
東北大学の SPRAT[61] は,実行時環境に特徴があるストリーミング言語である.
本研究のアプローチ 1 (3 章) で述べているように,GPGPU においては対象問題の
2.3 プログラミング環境に関する研究の動向
// カ ー ネ ル
k e r n e l void k f u n c ( f l o a t x<>, f l o a t y<>, out f l o a t z<>){
z = x + y;
}
int main ( ) {
f l o a t a<100>;
f l o a t b<100>;
f l o a t c <100>;
// 入 力 ス ト リ ー ム の 指 定
streamRead ( a , data1 ) ;
streamRead ( b , data2 ) ;
// カ ー ネ ル の 実 行
kfunc ( a , b ) ;
// 出 力 ス ト リ ー ム の 指 定
streamWrite ( c , r e s u l t ) ;
return 0 ;
}
図 8: BrookGPU を用いたプログラムの例
22
2.3 プログラミング環境に関する研究の動向
23
int main ( ) {
// カ ー ネ ル
Program k f u n c=BEGIN{
In<Value3f >x , y ;
Out<Value3f >z ;
z = x + y;
}END;
// 入 出 力 ス ト リ ー ム の 指 定
Array <1, Value3f >a ( 5 1 2 ) ;
Array <1, Value3f >b ( 5 1 2 ) ;
Array <1, Value3f >c ( 5 1 2 ) ;
// カ ー ネ ル の 実 行
c = kfunc ( a , b ) ;
return 0 ;
}
図 9: RapidMind を用いたプログラムの例
計算量や並列度と,CPU と GPU の性能バランスによって,対象問題を CPU で実
行した方が高い性能が得られる場合と GPU で実行した方が高い性能が得られる場
合とがある.SPRAT の実行時環境はカーネルを CPU と GPU のどちらで実行した
方がより高い性能が得られるかを性能モデルや実測値から判断し,より高い性能が
得られるハードウェアを選択して実行するという機構を有している.SPRAT のプ
ログラム記述方法は BrookGPU に近いものとなっている (図 10).
OpenCL
OpenCL Working Group が策定を行っている OpenCL[62] は,C 言語をベースと
した並列処理向けのプログラミング環境である.OpenCL は GPU だけではなくや
マルチコア CPU,Cell,DSP (Digital Signal Processor) など様々なハードウェアに
おける並列処理を統一的に記述可能とすることを目指している.
OpenCL は新しいプログラミング環境であり本論文執筆時点では対応するハード
ウェアがまだ存在していないが,主な GPU ベンダである NVIDIA 社と AMD 社が
それぞれ CUDA と Stream による OpenCL への対応を表明している.そのためアプ
2.3 プログラミング環境に関する研究の動向
// カ ー ネ ル
k e r n e l k f u n c ( i n stream<f l o a t > x , i n stream<f l o a t > y ,
out stream<f l o a t > z ) {
z = x + y;
}
int main ( ) {
stream<f l o a t > s a ( 1 0 0 ) , sb ( 1 0 0 ) , s c ( 1 0 0 ) ;
float a [100] , b [100] , c [ 1 0 0 ] ;
// 入 力 ス ト リ ー ム の 指 定
init array ( a , b);
streamRead ( sa , a ) ;
streamRead ( sb , b ) ;
// カ ー ネ ル の 実 行
k f u n c ( sa , sb , s c ) ;
// 出 力 ス ト リ ー ム の 指 定
streamWrite ( sc , c ) ;
return 0 ;
}
図 10: SPRAT を用いたプログラムの例
24
2.3 プログラミング環境に関する研究の動向
25
リケーションプログラマは OpenCL を用いることにより様々な GPU 向けのプログ
ラムを C 言語に近い単一のプログラム記述によって行うことが可能となり,習得や
利用の手間と難しさが削減されることが期待できる.
コンピュータビジョンアプリケーション用のプログラミング環境
GPU の用途の 1 つとして,コンピュータビジョンアプリケーションにおける新
たな表現手法の実装や高速化 [63] が挙げられる.この分野のアプリケーションは
GPU 本来の処理である画像描画に関する処理を多く含むが,処理内容が高度化して
いるため,汎用演算と同様に習得や実装の手間や難しさが問題となっている.そこ
で,コンピュータビジョンアプリケーションの開発を支援するシステムの研究開発
が行われている.研究開発されたシステムの例としては,北陸先端技術大学院大学
の EasyGPU[64] や,加 University of Toronto の OpenVIDIA[65],仏 University of
Lyon の GPUCV[66] などが挙げられる.いずれのシステムも,フィルタ処理などコ
ンピュータビジョンアプリケーションで利用される処理を容易に記述可能とするこ
とで,アプリケーションプログラマに対する GPU プログラミングの習得や利用の
手間と難しさの削減を可能としている.
2.3.2
CPU 向けのプログラミング環境
近年ではマルチコア CPU の普及やマルチコア CPU に搭載されるコア数の増加
(メニーコア化) が進んでいる.そのためマルチコア CPU 上で高い性能を得られる
プログラムの作成方法や,マルチコア CPU に適したプログラムを容易に作成する
ためのプログラミング環境に関する研究が盛んに行われている.
マルチコア CPU 向けの並列化プログラミング環境に関する研究の例は多く存在
するが,特に,計算機を提供するベンダーが策定や提供に影響力を持つ言語 (IBM
の X10[67],Cray の Chapel[68],Sun の Fortress[69]) や広く普及している既存のプ
ログラミング言語に対する拡張仕様など (C 言語に対する Unified Parallel C[70] や,
Fortran に対する High Performance Fortran[71] や Co-Array Fortran[72]) は他の言語
と比べると多くの利用者を獲得し今後の並列化プログラミングにおける主流となる
可能性が高く,また並列化プログラミングのトレンドに影響を及ぼす可能性がある.
例えば,これらのマルチコア CPU 向け並列化プログラミング環境のいくつかは,
スレッドとメモリとの対応付けをアプリケーションプログラマが明示的に記述する
2.3 プログラミング環境に関する研究の動向
26
Partitioned Global Address Space (PGAS) モデルを採用している.PGAS モデルを
採用したプログラミング環境では,変数や配列などのデータに対して,そのデータ
をスレッド (プロセス) ごとに独立して持つものとして扱うべきか,スレッド間で共
有して持つものとして扱うかを,コンパイラに対する指示子や専用の変数宣言を用
いて指定する.これらの指定により,アプリケーションプログラマはデータの分散
配置や通信を容易に指示することが可能となり,またコンパイラや実行時環境によ
る高度な最適化も可能となることが期待されている.
さらに,メモリの分散配置を記述するプログラミング環境としては,共有メモリ
型並列計算機向けのプログラミング環境である OpenMP に対してメモリの分散配置
に関する記述が行えるように拡張を行った OpenMPD[73] なども挙げられる.
一方,対象問題の持つ並列性を容易に記述するための並列化プログラミング環境
についての研究も行われている.
スケルトン並列プログラミングは,並列スケルトンと呼ばれる並列処理における
頻出計算パターンを抽象化したライブラリ関数の組み合わせによる並列化プログラ
ミング手法である.スケルトン並列プログラミングの利点としては,アプリケーショ
ンプログラマに対して低レベルの並列化実装を隠蔽することが可能であり,並列計
算の知識を持たなくても高性能な並列処理プログラムを作成できることなどが挙げ
られている [74].スケルトン並列プログラミング環境の例としては,東京大学の助っ
人 (SkeTo) [75] などが挙げられる.
配列の各要素に対する処理や繰り返し処理を記述しやすい言語仕様を持つ並列化
プログラミング環境に関する研究も行われている.近年の研究例としては,東芝社
の配列切り出し演算子を備えた配列処理向け言語 [76] 等が挙げられる.これらのプ
ログラミング環境の利点としては,ループ記述を行うことなく繰り返し処理を表現
できるため多重ループ処理の可読性が高いことや,最適化に用いる情報を抽出しや
すく抽象度の高い言語仕様としているため最適化が行いやすいことなどが挙げられ
ている.
2.4 SIMD 型アクセラレータやプログラミング環境に関する研究と本研究との関
係 27
2.4
SIMD 型アクセラレータやプログラミング環境に関する研究と
本研究との関係
本研究ではアプリケーションプログラマにとって GPGPU を容易に利用できるよ
うにするため “並列計算ライブラリ” と “並列化プログラミング環境” の 2 つのアプ
ローチを提案している.
本研究のアプローチ 1 (3 章) では,CPU と GPU による適切な問題分割・並列実
行を行うライブラリを提案し,最適な性能を得るための性能パラメタや実装につい
て論じている.
CSX は拡張バスを通して CPU と接続して利用されるアクセラレータカードであ
ること,カード上にメインメモリとは別のメモリを搭載していることなどが GPU
と共通している.CSX 上で動作する数値計算ライブラリが提供されているが,CSX
に搭載されている演算器は GPU よりさらに低速なため,対象問題のデータ規模が
小さい場合などに単純に CSX 用のライブラリを利用しただけでは性能が低下してし
まう可能性が高い.そのため,対象問題のデータ規模にあわせて CPU のみでの実行
と CPU と SIMD 型アクセラレータによる適切な問題分割・並列実行を切り替える
機構を持つライブラリという本研究で提案するアプローチは,CSX でも有効に活用
できると考えられる.
なお,CSX に対して ClearSpeed 社が提供しているライブラリの中には,本アプ
ローチのようにライブラリ内部で CPU と CSX で問題分割を行うライブラリも含ま
れている.本アプローチは GPGPU において適切な問題分割・並列実行を行うライ
ブラリの有効性を示すとともにライブラリを作成するための方法を示している.そ
のため,GPU と CSX それぞれにおけるライブラリの実装方法や最適化方法の比較
を行い,CPU と SIMD 型アクセラレータにより適切な問題分割・並列実行を行うラ
イブラリの作成方法や最適化方法の研究が進むことで,今後新たな SIMD 型アクセ
ラレータが開発された際に同様のライブラリを作る場合に成果が活用可能となると
考えられる.
Cell は,Cell 自体が汎用プロセッサとアクセラレータを含むハードウェアである
ため,CSX と比べると GPU とは異なる部分が多いハードウェアアーキテクチャお
よび実行モデルであるが,PPU と SPU での問題分割等に本アプローチで行った問
2.4 SIMD 型アクセラレータやプログラミング環境に関する研究と本研究との関
係 28
題分割・並列実行の実装方法や性能パラメタが利用できることが期待できる.
本研究のアプローチ 2 (4 章) では,既存の CPU 向け並列化プログラミング環境を
用いた GPGPU 向けのプログラミング環境を提案している.
Cell については,本アプローチと同様に既存の並列化プログラミング環境を用いて
プログラミングを行うためのコンパイラなどの研究が進んでいることを述べた.こ
れは現在の SIMD 型アクセラレータ向けプログラミングがアプリケーションプログ
ラマにとって難しく手間がかかること,既存の並列化プログラミング手法を用いた
SIMD 型アクセラレータ向けプログラミングの需要・要求が高いことを示している.
OpenMP を用いた Cell プログラムの開発を可能としている XL C/C++ for Multicore Acceleration for Linux の実装については,SPE は DMA によって Cell 上の大
容量メモリを任意のタイミングで送受信できるため実行時に動的なデータ転送を行
い共有メモリの管理を行っている.一方で OMPCUDA の実装では CPU-GPU 間で
データ送受信を行うことが可能なタイミングが限定されていることから,コンパイ
ル時に並列実行部で必要となるデータを確認して並列実行の前後に CPU-GPU 間で
送受信しており,実装が異なっている.
本アプローチによる OMPCUDA の実装は,CPU と Cell に加えて GPU において
も共通の並列化プログラミング手法 (OpenMP) を用いた並列化プログラミングを
可能とするものである.様々な環境において共通のプログラム記述を用いられるこ
とは,アプリケーションプログラマにとって習得の手間が削減できるため有意義で
ある.
ストリームプログラミング言語はいずれも GPU のアーキテクチャをストリーム
処理という概念で抽象化しているため,アプリケーションプログラマはストリーム
プログラミング言語を利用することでハードウェアアーキテクチャに関する知識が
なくても GPU 向けの並列処理プログラムを作成することができる.また言語仕様
については,多くのストリームプログラミング言語が C/C++言語を元に拡張を行っ
たものであるため,C/C++言語に慣れ親しんだアプリケーションプログラマが比較
的容易に習得・利用できると述べられている.
しかしながらストリームプログラミング言語の言語仕様や実行モデルは,C/C++
言語と似てはいるものの同一ではないため,アプリケーションプログラマにとって
は習得に手間がかかる.また共通化された言語仕様等があるわけではないため,い
2.4 SIMD 型アクセラレータやプログラミング環境に関する研究と本研究との関
係 29
ずれかの言語を習得すれば他の言語も利用できるわけではない.新しいプログラミ
ング言語は,ユーザが少ないためマニュアルやノウハウの蓄積が難しく,マニュア
ルやノウハウの蓄積が少ないとユーザが増えにくい可能性があり,ユーザ獲得にお
ける悪循環となる可能性がある.
一方で本研究は,アプリケーションプログラマにとっての習得の手間や難しさを
重視し,既に普及している CPU 向けのプログラミング環境を用いた GPGPU プロ
グラミングに注目していることから,ストリームプログラミング言語とは立場が異
なっている.
OpenCL は,OpenCL を策定している Working Group に多くの企業,特にそれぞれ
が独自の GPGPU プログラミング環境を提供していた主要な GPU ベンダ (NVIDIA
社と AMD 社) が対応を表明していることなどから,今後の GPGPU プログラミング
の主流となることが期待されている.また OpenCL は GPU のみならず様々なハード
ウェアにおける並列処理を記述できるため,アプリケーションプログラマは OpenCL
さえ習得すれば様々なハードウェア向けのプログラムが作成可能となることが期待
できる.
一方で OpenCL は様々なハードウェアにおいて利用できるようにするため,特徴
的な実行モデルやメモリモデルを定義している.これらのモデルは既存の CPU 向け
プログラミング環境と比べて複雑であるため,多くのアプリケーションプログラマ
にとって習得や利用の手間と難しさが削減されるとは言い難い.そのため,OpenCL
が実際に多くのシステムで利用可能になった後も,多くのアプリケーションプログ
ラマが容易に利用可能なプログラミング環境への要求がなくなることは考えにくい.
むしろ OpenCL が普及した場合には,OpenCL による様々なハードウェアへの対応
とアプリケーションプログラマに対する習得や実装の容易さを両立させるために,既
存の CPU 向け並列化プログラミング環境を用いて記述されたプログラムを OpenCL
向けのプログラムに変換する機構が有用となることが考えられる.
コンピュータビジョンアプリケーション用のプログラミング環境など特定用途向
けのプログラミング環境は,GPU のハードウェアアーキテクチャに関する知識の習
得を不要としたり,対象とする特定のアプリケーションを容易に作成しやすくする
など,それぞれ独自の視点でアプリケーションプログラマにとっての手間の削減を
行っている.
2.4 SIMD 型アクセラレータやプログラミング環境に関する研究と本研究との関
係 30
しかしながらこれらのライブラリやプログラミング環境は新たなプログラミング
モデルや新たな言語仕様を作成するものであり,アプリケーションプログラマにとっ
て新しい知識や技術を習得する手間の増加を問題視している本研究とは立場が異なっ
ている.
マルチコア CPU の普及により CPU 向けの新たな並列化プログラミング環境に関
する研究が盛んとなっているが,本研究は既存の CPU 向け並列化プログラミング環
境を利用することでアプリケーションプログラマに対する習得の手間の削減を目指
す研究であるため,これらの新たな並列化プログラミング言語とは直接関係がない.
しかしながら GPGPU プログラミングにおいては多数の演算器を活用することが
重要であることから,多数のコアを搭載した CPU を活用するために提案された新
たな並列化プログラミング環境は,既存の CPU 向けプログラミング環境と比べて
GPGPU プログラミングに適していると考えられる.また PGAS モデルのプログラ
ミング環境などにおけるメモリの分散配置の記述は,GPGPU プログラムにおける
メインメモリと GPU 上のメモリとの分散配置の記述や,GPU 上の複数種類のメモ
リに対するデータの分散配置の記述に利用することで,容易に高性能な GPGPU プ
ログラムを記述できるようになることが期待できる.
一方で,これまでにもアセンブラを用いて手動最適化されたプログラムと高級言
語で記述されコンパイラにより最適化されたプログラムに対して盛んに議論が行わ
れてきたように,プログラミングの難しさと得られる性能についてはトレードオフ
となる部分もある.本研究ではアプリケーションプログラマにとっての手間や難し
さを削減することを重視し,既存の CPU 向け並列化プログラミング環境を用いた
GPGPU プログラミングを提案して研究を行った.しかし本研究の目的やアプロー
チとは立場が異なるものの,CPU 向けの新たな並列化プログラミング環境を用いた
GPGPU プログラミングについて検討することや,GPGPU 向けの新たなプログラ
ミング環境を提案することは,アプリケーションプログラマが GPU の性能をより
容易に活用できるようにするうえでは重要であると言える.
31
並列計算ライブラリによるアプローチ
3
本章では,GPU を用いて計算を行う並列計算ライブラリを提供することでアプリ
ケーションプログラマに対して並列化プログラミングそのものを隠蔽するアプロー
チを提案する.はじめに本提案の着眼点である CPU と GPU を用いて問題分割・並
列実行を行うライブラリの概要を述べ,次にライブラリの実装方法について述べる.
さらに,提案を元に作成したライブラリ “GPUPC GEMM Library” の設計と実装に
ついて述べ,テストプログラムやベンチマークプログラムを用いて評価を行う.
3.1
CPU と GPU を用いて問題分割・並列実行を行うライブラリの
提案
本節では,“CPU 単体で実行されるライブラリと同様の API を持ちながら CPU と
GPU による適切な問題分割・並列実行を行う機構を持つ” ライブラリを提案する.
2.1 節で述べたように,GPGPU プログラミングを行うためには GPU のアーキテ
クチャや GPGPU プログラミング環境に関する知識と理解が必要であり,アプリケー
ションプログラマにとって大きな手間となっている.
一方で,プログラムの再利用を容易にするとともに習得が難しく手間のかかる最
適化プログラミングを隠蔽可能な計算ライブラリが広く利用されている.特にアプ
リケーションプログラマにとっての計算ライブラリは,ライブラリインターフェイ
ス (アプリケーションプログラミングインターフェイス:API) さえ理解していれば
対象アプリケーションで用いるアルゴリズムに関する理解がなくてもライブラリの
提供する機能を利用することで正しく動作するプログラムを作成可能であることや,
様々な環境向けに最適化された同一の API を持つライブラリがあれば実行環境の違
いについて気にすることなく同じ機能と高い性能を得られることが,アプリケーショ
ンの実装における手間を大きく削減するのに役立っている.
そこで,GPGPU プログラミングの手間を削減し,アプリケーションプログラマ
が GPU を容易に利用できるようにする方法として,CPU 向けの既存の計算ライブ
ラリと同様の API を持つ GPU 向けの計算ライブラリを提供することを考える.こ
れによりアプリケーションプログラマはリンクするライブラリを切り替えるのみで
3.1 CPU と GPU を用いて問題分割・並列実行を行うライブラリの提案
32
GPU の持つ高い演算性能を利用可能となることが期待できる.
典型的な GPGPU プログラムにおいて GPU を使用する際には,初めに GPU の
初期化や GPU 上で実行されるプログラムの準備を行い,次に CPU から GPU への
データ転送を行い,さらに CPU から GPU に対して演算開始を指示し,最後に GPU
の演算終了を待って GPU から CPU へ演算結果を転送するという手順で処理を行う
必要がある (図 11).
図 11: 典型的な GPGPU プログラムの処理手順
しかしながら,単純にこれらの処理をライブラリとしてまとめて既存の CPU 向
けのライブラリと同様に利用する場合,次の 2 つの課題を解決しなくては高い性能
が得られないという問題が生じてしまう.
3.1 CPU と GPU を用いて問題分割・並列実行を行うライブラリの提案
33
問題 1. GPU 上での実行に適さない問題設定に関する課題
GPU は既存の CPU と比べて多数の演算器を搭載しているために並列性が高い問
題を高速に実行できる一方,GPU に搭載されている各演算器単体と CPU との性能
を比較すると,CPU の方がクロック周波数が高く演算性能も高い.そのため,対象
問題の並列性があまり高くない場合には GPU より CPU の方が短い実行時間で対象
問題を解くことができる.
また,GPU を用いて演算を行うには CPU を用いて GPU を制御する必要があり,
CPU-GPU 間のデータ転送を行う必要もある.そのため,対象問題の並列性が高く
ても演算対象のデータ規模が小さいなどの理由で対象問題の絶対的な処理時間が短
い場合には,GPU を制御するオーバヘッドや CPU-GPU 間でのデータ送受信によ
るオーバヘッドが実行時間全体に占める割合が大きくなり,GPU は CPU と比べて
あまり高い性能を得ることができないことや CPU より低い性能となることがある.
そのため,実行環境の CPU と GPU の性能バランスや演算対象のデータ規模に応
じて性能向上が期待できる場合にのみ GPU を利用する機構を持つライブラリが有
用であることが考えられる.
問題 2. CPU-GPU 間での負荷分散に関する課題
CPU と GPU は独立した計算ハードウェアであり,適切なプログラム記述を行え
ば CPU と GPU で同時に演算を行うことができる.そのため対象問題が CPU でも
GPU でも高速に処理できる場合は,対象問題を分割し CPU と GPU で並列に実行
すれば,さらに高い性能を得られることが期待できる.また対象問題の計算量が十
分に大きく実行時間が長い場合には,CPU と GPU の性能に差がある場合でも対象
問題を適切に分割し並列実行することで CPU のみや GPU のみよりも高い性能を得
られることが期待できる.
しかしながら,単に CPU-GPU 間のデータ送受信や GPU での演算をまとめたラ
イブラリが提供されている場合,ライブラリを利用するアプリケーションプログラ
マ自身が CPU と GPU で問題分割・並列実行するプログラムを作成する必要がある.
そのようなプログラムを作成するにはマルチスレッドプログラミングなどアプリケー
ションプログラマにとって手間のかかるプログラミングを行う必要が生じ,API に
3.1 CPU と GPU を用いて問題分割・並列実行を行うライブラリの提案
34
より隠蔽されているため利用が容易であるというライブラリの利点が損なわれてし
まう.
そのため,対象問題を適切な割合で分割し CPU と GPU で並列実行する機構を持
つライブラリが有用であることが考えられる.
そこで本アプローチでは,“CPU 単体で実行されるライブラリと同様の API を持
ちながら,対象問題のデータ規模が小さい場合には CPU のみで演算を行い,データ
規模が大きい場合には CPU と GPU の性能バランスにあわせて CPU と GPU で適
切な問題分割・並列実行を行う機構を持つ並列計算ライブラリ” を提案する.アプ
リケーションプログラマにとってこの提案は,GPGPU 環境を容易に利用できるこ
とと,常に高い性能を得られることの両方が達成できる提案である.
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
3.2
35
CPU と GPU を用いて問題分割・並列実行を行うライブラリの
実装
本節では,前節で提案したライブラリの実装についての検討を行う.
本節におけるライブラリの実装では,グラフィックス API とシェーダ言語,具体
的には “DirectX 9 (以下 DirectX) と HLSL” もしくは “OpenGL と GLSL” を用いる
こととする.グラフィックス API とシェーダ言語を用いてプログラムを作成する理
由は,作成したプログラムが多くの GPU で利用可能であることと,本アプローチ
に基づく提案と実装を行った時点では CUDA や CTM など GPGPU 向けの低レイヤ
なプログラミング環境が存在していなかったことによるものである.
また本ライブラリは,GPU を搭載した計算機システムの最も基本的な構成であ
る,1 個つのシングルコア CPU を搭載した計算機に 1 枚の GPU を搭載した 1 台の
計算機からなる計算機システムを基本的な対象計算機システムとする.しかしなが
ら,今日ではマルチコア CPU を搭載した計算機システムや複数の GPU を搭載可能
な計算機システムの普及が進みつつあることから,複数の CPU ないしマルチコア
CPU や複数の GPU を搭載した計算機システムについても発展的な対象計算機シス
テムとする.
以下本節では,提案したライブラリに必要な,CPU と GPU を用いた並列処理の
実装方法と,CPU と GPU による適切な問題分割を行うための仕組みについて述べ
る.さらに発展的な対象計算機システムである複数の CPU や複数の GPU を搭載し
た計算機システム向けの実装について述べる.
3.2.1
CPU と GPU を用いた並列処理の実装
CPU と GPU を用いて並列処理を行うための基本的な考え方は,GPU が描画 (演
算) を行っている間に CPU でも演算を行うというものである.
DirectX や OpenGL を用いて GPU に対する描画開始指示や演算データの送受信指
示を行うには,各グラフィックス API が提供する API 関数を利用して対応する処理
を記述する必要がある.これらの処理の多くは非同期に実行される関数によって記
述することが可能であり,DirectX・OpenGL ともに GPU に対する描画開始処理を
行う関数は非同期関数である.そのため描画開始処理に続いて描画終了処理を待た
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
36
ずに CPU による演算を記述すれば CPU と GPU による並列処理を行う事ができる.
またプログラム記述に関しては,CPU による演算と GPU による描画 (演算) を別の
スレッドとして記述すれば,CPU による演算に関する記述と GPU による演算に関
する記述が明確に分離された可読性の高いプログラムが作成できると考えられる.
しかしながら,スレッドによる記述を用いて CPU と GPU による並列処理を記述
する際に,以下のような問題が発生した.
CPU が GPU から演算結果を取得する際には,CPU は GPU の描画終了を待つ必
要がある.しかし,OpenGL を利用した GPU プログラムにおいて CPU が GPU の
描画結果を取得する際に実行する必要がある API 関数の 1 つは,GPU の描画が終
了する前に CPU によって呼び出された場合に GPU の描画が終了するまで CPU へ
制御を戻さないばかりか,GPU の描画が終了するのを待つ間は常に CPU の利用率
を 100%にしてしまうことが判明した.そのため,CPU による演算と GPU に関す
る演算を別のスレッドとして記述した場合に,CPU による演算を行っているスレッ
ドと GPU が演算を終えるのを待っているスレッドの 2 スレッドが同時に CPU を利
用しようとしてしまうため,CPU による演算の性能が低下するという問題が発生し
た (図 12).
このような問題を避ける方法は,マルチスレッドプログラムを作成するのではな
く,CPU による演算が終了してから GPU の演算終了を待つよう明示的に記述され
たシングルスレッドプログラムを作成することである.
以上の検討に基づき,本章では図 11 に対して CPU が行うべき処理がない部分に
CPU による演算を加えた図 13 に示す構造のライブラリを実装することにした.演
算結果受信から “反復計算が必要な場合など” の矢印が 2 本出ているのは,対象問題
によっては再度演算を行うことや再度問題分割し直してから演算を行うことも考え
られるためである.
3.2.2
CPU と GPU による適切な問題分割を行うための仕組み
対象問題のデータ規模がどの程度大きければ問題分割・並列実行の効果によって
良い性能が得られるかや,CPU と GPU に対する最適な問題分割割合はどの程度か
といった性能パラメタは,対象問題のアルゴリズムだけではなく実行環境の CPU と
GPU の性能バランスにも大きく依存する.そのため本アプローチに基づいて作成し
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 12: スレッドを用いた並列実行の失敗例
37
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 13: 提案するライブラリの構造
38
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
39
たライブラリは,対象環境毎に異なる CPU と GPU の性能バランスに合わせた適切
な問題分割・並列実行を行わなくては良い性能を得ることができない.
このような性能パラメタの確認 (性能チューニング) は,アプリケーションプロ
グラマにとって大きな手間となる可能性が高い.特に,アプリケーションプログラ
マが GPU のアーキテクチャなどライブラリにより隠蔽されるはずであった知識を
習得しなくては性能チューニングが行えないようでは,ライブラリによってアプリ
ケーションプログラマに対して実行環境を隠蔽するというメリットが失われてしま
う.そのため,GPU のアーキテクチャなどに関する知識がなくても性能パラメタを
求めることのできる機構が望まれる.
例えば CPU 向けにベクトルや行列に関する演算を提供するライブラリ ATLAS[77]
では,ライブラリをインストールする際にチューニングを行う機構 (自動チューニ
ング機構 [78]) を備えている.ATLAS の備えるチューニング機構は,CPU アーキテ
クチャや利用するコンパイラ等いくつかの簡単なパラメタを指定すると,キャッシュ
サイズなどの演算性能に影響を与えるハードウェア情報を自動的に収集し,また単
純に収集できない情報についてはベンチマークを行い特定したりする機能を持って
いる.こうして得られたハードウェア情報を反映したライブラリがインストールさ
れるため,アプリケーションプログラマは利用しているハードウェア (CPU やメモ
リ) に関する深い知識がなくても常に最適な性能を得ることができる.
本アプローチにおいては,対象問題のデータ規模が小さい場合には CPU のみで
演算を行うこと,データ規模が大きい場合には CPU と GPU の性能バランスにあわ
せて CPU と GPU で適切な問題分割・並列実行を行うこと,の 2 点が重要である.
そのため,ライブラリを利用する計算機システムに搭載された CPU と GPU の性能
バランスではどのようなデータ規模の問題を CPU のみで実行し,またどのような
データ規模の問題をどのような割合で CPU と GPU に分割すれば高い性能が得られ
るのかを判断する機構と,判断結果に基づいて実行する機構を作成することで,ア
プリケーションプログラマがチューニングを行う手間が削減できると考えられる.
そこで,様々な問題サイズの対象問題に対して様々な問題分割割合で性能を測定
し CPU のみで実行した方が高い性能が得られるデータ規模や適切な問題分割割合
を求める “チューニングスクリプト” と,チューニングスクリプトによって求められ
たパラメタを用いて CPU のみでの実行・GPU のみでの実行・CPU と GPU による
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
40
並列実行から最も高い性能が得られるものを選択する “問題分割機構” によって適切
な問題分割を行うこととする.これによりアプリケーションプログラマは,ライブ
ラリのインストール時にチューニングスクリプトを実行しておくことで,ライブラ
リ利用時にはチューニングスクリプトによって得られたパラメタに基づき常に高い
演算性能を得ることが可能となる.
実際にどのようなチューニングスクリプトを作成するべきかは対象問題による部
分が大きいため,3.3 節にて改めてチューニングの内容を述べる.
3.2.3
複数の CPU や複数の GPU を搭載した計算機システム向けの実装
現在では多くの計算機環境で複数のコアを搭載した CPU や複数の CPU を搭載し
た計算機システムが利用されていることは既に述べた通りであるが,複数の GPU
を搭載した計算機システムの構築も可能である.GPU は主に PCI-Express で CPU
(マザーボード) と接続して利用されており,マザーボード上に GPU に対応した
PCI-Express バスが複数本搭載されていれば複数の GPU を利用することができる.
(PCI-Express x1 などレーン数の少ない PCI-Express バスではほとんどの GPU を利
用することができない.) そこで,ここでは複数の CPU (マルチコア CPU) や複数
の GPU を搭載した計算機システムへの対応についても検討を行うことにする.
GeForce や Radeon には SLI[79] や CrossFire[80] といった複数の GPU を用いて描
画性能を向上させる機構も存在する.これらの機構を用いるとソフトウェアからは
あたかも複数の GPU が統合されて 1 台の高性能な GPU が搭載されているかのよう
に見えるようになり,複数の GPU が搭載されていることを考慮していないアプリ
ケーションでも複数の GPU の性能を足しあわせた性能で動作 (描画) させることが
可能となる.しかしながら,これらの機能を用いても本アプローチにおける性能評
価では全く性能が向上しなかったため,ここでは扱わないものとする.
複数の CPU が搭載された計算機環境で GPU を利用する方法としては,いくつか
の実装が考えられる.
例えば,マルチスレッドプログラムを作成し,1 つのスレッドは 1CPU+1GPU の
時と同様に GPU の制御と CPU による演算を行い,他のスレッドでは演算のみを行
うという実装が考えられる (図 14).
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
41
また別の実装例としては,CPU による計算を複数の CPU に対応した外部の計算
ライブラリに行わせるという実装が考えられる.この場合,問題分割の際に CPU が
複数あることを踏まえた割合で分割を行い,複数 CPU による演算自体は外部の計
算ライブラリに行わせるというのは,複数の CPU を活用しつつ GPU も利用できる
比較的容易な実装である (図 15).例えば 1CPU+1GPU では CPU 1 : GPU 1 に等
分割していたものを,2CPU+1GPU では CPU 2 : GPU 1 の割合に分割すればある
程度高い性能が得られると期待できる.
一方グラフィックス API を用いて複数の GPU を利用する方法については以下の
通りである.
DirectX では,各種 API を利用する際に各 GPU に対応するクラスインスタンス
を指定する.GPU 数分のクラスインスタンスを生成し,適切にパラメタ設定をして
おくことで,複数の GPU を利用することができる.そのため,API の呼び出しを
GPU の数だけ増やし,問題分割時の割合等を複数 GPU にあわせて変更すれば,複
数 GPU に対応することができる.
一方 OpenGL では,1 プロセスあたり 1 つの GPU しか利用することができない.
1 つのプログラムで複数の GPU を扱うにはマルチプロセスプログラムを作成する
必要があり,問題分割・並列実行するためにはプロセス間でのデータ共有が必要で
ある.
しかしながら,例えば 2CPU+2GPU の環境において,GPU を制御するためのプ
ロセスを 2 つ,CPU で演算を行うためのプロセスを 2 つの合計 4 プロセスを用いて
並列処理を行ったとする.この場合,図 16 に示すように CPU が演算を終える前に
GPU への演算結果要求が行われてしまい,GPU を待つプロセスが CPU に負荷をか
けることで CPU の演算が遅くなり,全体として実行時間が延びてしまう可能性が
高い.
この問題に対しては次に述べるような実装を行うことで解決可能であることを確
認した.
GPU に関する処理は GPU 数分の子プロセスを生成してそれぞれの子プロセスに
行わせ,CPU による演算は親プロセス上で CPU 数 (コア数) と同じだけのスレッド
を生成しマルチスレッド実行する.この際,プロセス間通信を用いるなどして実行
順序の制御を行い CPU による演算と CPU から GPU への演算結果要求が同時に起
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 14: 複数 CPU を用いた実装の例 1
42
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 15: 複数 CPU を用いた実装の例 2
43
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
44
こらないようにする.プロセス間のデータ共有に共有メモリを利用し,共有メモリ
のデータ更新を通知するために unix socket を用いた場合の処理手順を図 17 に示す.
プロセス間のデータ共有については,GPU に関する処理を行う子プロセスと CPU
によるマルチスレッド演算を行う親プロセスとでデータのやりとりができれば良い
ため,共有メモリを利用せずにプロセス間通信で代用しても良い.
次節で述べる複数 CPU および複数 GPU 向けの実装では,以上の検討結果に基づ
く実装を行う.
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 16: 複数 CPU と複数 GPU を用いた実装の例 1
45
3.2 CPU と GPU を用いて問題分割・並列実行を行うライブラリの実装
図 17: 複数 CPU と複数 GPU を用いた実装の例 2
46
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
47
3.3
GPUPC GEMM Library : CPU と GPU を用いて問題分
割・並列実行を行う行列計算ライブラリ の設計と実装
本節では,本アプローチに基づき CPU と GPU を用いて問題分割・並列実行を行
う行列計算ライブラリ “GPUPC GEMM Library” の提案と実装について述べる.
3.3.1
ライブラリが対象とする範囲
“GPUPC GEMM Library” は行列積和計算を対象とした並列計算ライブラリで
ある.
行列積和計算は,行列 A,B,C およびスカラー α,β に対して C = α ∗ A ∗ B + β ∗ C と
いう演算を行い行列 C を更新する計算であり,多くのアプリケーションで利用され
ている基本的な計算の 1 つである.行列やベクトルに関する関数インターフェイスを
まとめたライブラリ BLAS (Basic Linear Algebra Subprograms) [81, 82] の GEMM
関数 (図 18) として知られており,科学技術計算アプリケーションをはじめとした多
くのプログラムで利用されている.世界中の計算機の性能を順位付けする TOP500
[83] で用いられている HPL (High-Performance Linpack) ベンチマーク [84] に用い
られている計算としても知られている.
CPU 向けの高速な行列積和計算の実装としては,GPUPC GEMM Library でも
利用されている ATLAS や,GotoBLAS[85] が広く用いられている.
GPGPU においても行列積和計算 (行列積) はしばしば取り上げられている.プロ
グラマブルシェーダが登場する前の GPU においては描画機能を用いた数値計算の
例として [20],またプログラマブルシェーダが普及し GPGPU への注目が高まるに
つれてプログラマブルシェーダを用いた数値計算の高速化の例や GPU の性能評価
の題材として数多く取り上げられてきた [86, 87, 88] .行列積和計算はデータ量に対
して演算量が多く,並列性も高いため,GPU による高速化が期待できる問題である
と言える.
行列積和計算は反復計算等のない単純な問題であるものの,問題のデータ規模が
大きくなるにともない実行時間が増加しやすいため高速化の要求が大きく,並列性
が高いため GPU を用いることで比較的単純な実装でも高速化の効果が得やすく,さ
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
48
¶
³
void cblas ♦gemm
const enum CBLAS ORDER Order
const enum CBLAS TRANSPOSE TransA
const enum CBLAS TRANSPOSE TransB
const int M
const int N
const int K
const SCALAR alpha
const TYPE *A
const int lda
const TYPE *B
const int ldb
const SCALAR beta
TYPE *C
const int ldc
ただし,♦ には TYPE と SCALAR の型を規定する1文字が,TYPE および
SCALAR には ♦ によって定められたデータ型が使われる.これらの対応は下
記のとおりである.
文字
TYPE
SCALAR 意味
s
float
float
d
double double
倍精度浮動小数に対する演算
c
void
void*
単精度複素数に対する演算
g
void
void*
倍精度複素数に対する演算
単精度浮動小数に対する演算
µ
´
図 18: BLAS における GEMM の関数定義
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
49
らに次項で述べるように問題分割が容易であるため,本アプローチを用いたライブ
ラリの対象問題とした.
なお GPUPC GEMM Library は CPU や GPU 単体での性能を追求するのが目的
ではないため,CPU 上での行列積和計算は既存のライブラリ ATLAS を用いて実行
することとし,GPU 上での行列積和計算については後述するようなある程度の高速
化手法を適用したグラフィックスプログラミングを用いて実装している.
3.3.2
ライブラリの設計と実装
本項ではライブラリの設計と実装について,以下のことを述べる.
1. GPU を用いた行列積和計算の実装方法
2. CPU と GPU による問題分割・並列実行の実装方法
3. チューニングスクリプト
4. 複数 CPU や複数 GPU を搭載した計算機システム向けの実装
5. 倍精度浮動小数点演算への対応
6. メモリ容量に基づく問題サイズの制限
7. 行列データの転置や ORDER といった BLAS のパラメタへの対応
なお,実装には OpenGL と GLSL を用い,実行環境は Linux とした.これは評価
に用いる HPL ベンチマークの実行環境として Linux が適していることおよび Linux
向けのグラフィックスプログラミングには OpenGL と GLSL が適していることによ
る選択である.
GPU を用いた行列積和計算の実装方法
GPUPC GEMM Library における GPU を用いた行列積和計算については,Fatahalian らによる行列積の実装 [86] を用いた.
この実装は行列 C の縦横サイズに対応した大きさの描画先テクスチャを用意し,
ピクセル毎にシェーダプログラムを用いて行列積和計算を行うものである.図 19 に
示すように長さ 4 のベクトルをまとめて処理する高速化手法を取り入れた実装では
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
50
あるものの,図 20 のように対象行列の転置状態によっては手法が有効に機能せず高
い性能が得られない.そのためシェーダによるベクトル演算が行いにくい問題につ
いては,転置してから GPU へ転送し,計算結果を取得後に転置を戻すという実装
を行った.また行列の縦横サイズが 4 の倍数でない場合はパディングも行っている.
なおこれらの処理は計算時間に影響を及ぼさない程度の十分に短い時間で行うこと
が可能であり,性能に有意な影響を及ぼすことがないことが確認できている.
CPU と GPU による問題分割・並列実行の実装方法
行列積和計算はデータの参照パターンが単純なため,問題分割も容易に行う事が
できる.GPUPC GEMM Library では,CPU-GPU 間でのデータ転送量が増えない
ようにすることと,CPU と GPU での問題担当割合を容易に変更できることを考慮
し,図 21 に示すような方法で問題分割を行うことにした.
この問題分割方法では分割割合 “m” を変更することで CPU と GPU の問題担当
割合を容易に変更することができるため,CPU と GPU の性能バランスに合わせて
問題分割割合を容易に調整することができる.
行列積和計算は反復計算等を必要としない単純な問題であるため,3.2 節を踏まえ
て図 22 に示すような設計とした.
ライブラリ関数を実行する際のライブラリ内における処理の順序は以下の通りで
ある.
1. 初回の実行時のみ GPU の初期化とシェーダプログラムの読み込みを行う.
2. 引数として与えられた問題サイズを元に,CPU のみで計算を行うか CPU と
GPU を用いて並列計算を行うかの判定を行う.CPU のみで計算を行う場合は
3 へ,並列計算を行う場合は 4 へ.
3. ATLAS の行列積和関数を実行して値を返す (関数終了).
4. 問題分割割合を決めたうえで GPU に対するデータ転送と描画指示を行う.
5. GPU が描画処理を行っている間に ATLAS を用いて CPU による計算を行う.
6. GPU の計算結果を取得し,CPU と GPU の計算結果を統合して返す (関数
終了).
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
51
図 19: ベクトル演算を利用した行列積の例
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
52
図 20: ベクトル演算が利用できない行列積の例
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
53
図 21: 問題分割方法
ここで問題となるのは,CPU のみで計算を行うか,CPU と GPU を用いて問題分
割・並列実行を行うかの判定基準である.既に述べたように,対象問題のデータ規
模が小さい場合には CPU 単体で実行した方が高い性能が得られる可能性がある.そ
こで GPUPC GEMM Library では,問題分割の際には関数の引数として与えられた
問題サイズを確認し,問題サイズが閾値より小さい場合には全てを CPU に割り当
て,それ以外の場合に問題分割・並列実行を行うこととした.
チューニングスクリプト
CPU のみで計算を行うか CPU と GPU で問題分割・並列実行するかの閾値につい
ては,CPU と GPU の性能バランスに依存することが考えられる.そこで GPUPC
GEMM Library では,閾値となる問題サイズや CPU と GPU での問題分割割合を外
部ファイルで指定し問題分割機構のふるまいを指定できるようにした.また,閾値
と適切な問題分割割合を求めるためのチューニングスクリプトを作成した.
ここで作成したチューニングスクリプトは,以下のような手順で適切な閾値と問
題分割割合を求めるものである.
1. 適当な問題サイズ (初期値では 1024) の正方行列に対して,CPU と GPU によ
る問題分割割合を 10%ずつ変更しながら行列積和計算を行い実行時間を測定
する.
2. 1 で最も高い性能を得られた問題分割割合の前後において,更に細かく分割割
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
54
図 22: ライブラリの設計
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
55
合を指定し直して実行時間を測定する.(初期値では-20%から+20%まで 5%刻
みで測定.)
3. 2 で最も高い性能を得られた問題分割割合を最適な問題分割割合と見なす.
4. 問題サイズを変更しながら (初期値では 256 から 3072 まで 256 刻み),3 で求
めた問題分割割合を用いた場合と CPU のみでの実行時間を比較する.
5. CPU のみより高い性能を得られる問題サイズの下限を閾値と見なす.
この方法では問題サイズが閾値を超えたものは全て同じ問題分割割合となってしま
う.しかしながら,本章の実験環境を含むいくつかの実験環境を用いて性能評価を
行ったところ,閾値以上の問題サイズにおける最適な問題分割割合はほとんどがプ
ラスマイナス 10%以内に収まっており常に良い性能が得られたため,このような方
法を採用した.今後様々な実験環境で性能確認を行い,チューニング方法を改良す
る余地はある.
なお,実行時間が 0.01 秒未満の問題については,仮に並列実行による高速化が得
られるという出力が得られた場合でも絶対的な実行時間が短すぎて問題分割・並列
実行の効果が期待できないと考えられるため,CPU のみで実行するべきであると判
断している.
複数 CPU や複数 GPU を搭載した計算機システム向けの実装
前項で述べたように,複数 CPU や複数 GPU 向けの実装にはいくつかの方法が考
えられる.ここではマルチスレッド対応の CPU 向け並列計算ライブラリと,共有メ
モリ (shm, mmap) および unix socket を用いた GPU の制御による複数 CPU や複数
GPU 向けの実装を行った.
複数 CPU (マルチコア CPU) への対応はマルチスレッドに対応した ATLAS に行
わせることにした.これは,ATLAS のマルチスレッド実行への対応は古くから行
われており,手動で問題分割を行うよりも良い性能が得られる可能性が高いためで
ある.
複数 GPU への対応については,fork を用いたマルチプロセスプログラミングに
よって複数 GPU の制御を行うこととした.プロセス間で行列データを共有する必
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
56
要があるため,shm と mmap を用いた共有メモリを利用することとした.さらに,
unix socket を用いたプロセス間の通信も行っている.プロセス間の通信は,問題分
割終了時に共有メモリの更新完了および描画開始を指示する際に利用している.ま
た,CPU の計算が終わる前に GPU の結果取得処理が始まり CPU がブロックされ
て CPU の計算時間が伸びてしまうのを避けるため,計算結果取得のタイミングを
指示するのにも利用している.
以上を元に作成した複数 CPU・複数 GPU に対応した GPUPC GEMM Library の
構造を図 23 に示す.
倍精度浮動小数点演算への対応
2008 年末の時点では最新の一部のモデルを除いた多くの GPU は倍精度浮動小数
点演算に対応しておらず,倍精度浮動小数点演算に対応している GPU もその性能
は単精度浮動小数点演算と比べると著しく低い.またグラフィックス API やシェー
ダ言語も倍精度浮動小数点演算に対応していない.その一方で数値計算アプリケー
ションなど行列積和関数を利用するアプリケーションには高い演算精度を求めるも
のが少なくはない.
そこで本研究では,単精度浮動小数点向けの行列積和関数 SGEMM だけではなく,
倍精度浮動小数点向けの行列積和関数 DGEMM も作成した.この DGEMM は API
と CPU が担当する部分のみ倍精度で計算し,GPU が担当する部分は単精度に精度
を落として実行するという,形式的な DGEMM である.そのため演算精度に問題が
あるものの,既存の DGEMM を用いたアプリケーションに対して形式的な適用実験
を行うことが可能となっている.
演算精度を改善し演算精度確認をパスするための方法としては,複数の単精度演
算を行うことで倍精度演算と同等の演算精度の演算を行う方法が挙げられる.これ
は本アプローチの提案とは直接関係のない問題であるため,ここでは扱わない.演
算精度に問題がある性能評価でも,本アプローチの中心である GPGPU 環境を容易
に利用できることと常に高い性能を得られることを否定することにはならず,意味
があると考えられる.
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
57
図 23: 複数 CPU・複数 GPU 対応版 GPUPC GEMM Library の構造
3.3 GPUPC GEMM Library : CPU と GPU を用いて問題分割・並列実行を行う
行列計算ライブラリ の設計と実装
58
メモリ容量に基づく問題サイズの制限
GPU に対して GPU の搭載メモリ容量を超える処理を行わせることは不可能であ
り,また GPU はグラフィックス API の仕様により一辺の長さが 4096 を超える大き
さのテクスチャを利用することができない.また一辺の長さが 4096 に達していない
場合でも,4000 程度の大きさになると正しい実行結果が得られないことがあること
を確認した.そのため,全体の問題サイズが大きな場合でも GPU が担当する問題
サイズ (正確にはテクスチャの一辺の長さ) の上限が 4000 未満となるような調整機
構を入れている.
行列データの転置や ORDER といった BLAS のパラメタへの対応
CPU-GPU 間のデータ転送時に行列の転置を行う必要がある場合など,対象問題
のデータ配置によっては CPU-GPU 間の転送前後でデータを並び替えるための一時
的なメモリが必要となる.対象問題の問題サイズや GPU の担当割合が大きな場合
に一度に必要な全てのデータを並び替えようとするとメインメモリに大きな一時領
域が必要となるため,分割して並び替え・送受信できるような機構を実装した.
データの並び替えの際の分割サイズを適当に変えて実験した結果,分割サイズが
著しく大きな場合や小さな場合にのみ CPU-GPU 間のデータ送受信やデータ再配置
にかかる時間が長くなりプログラム全体の大きな性能低下に繋がることが確認でき
た.次項の性能評価ではいずれも問題がない程度の分割サイズを設定している.
さらに BLAS の行列積和関数 API に正しく対応するため,行列の ORDER (Row-
Major/ColMajor,行列の並びが縦方向であるか横方向であるかを意味する) や転置
設定などについても適切な実装を行った.GPUPC GEMM Library は GEMM の各
種パラメタに全て対応した cblas sgemm 関数および cblas dgemm 関数相当の関数,
gpupc sgemm 関数および gpupc dgemm 関数を提供するライブラリである.
3.4 GPUPC GEMM Library の評価
3.4
59
GPUPC GEMM Library の評価
本節では GPUPC GEMM Library について,アプリケーションプログラマが容易
に利用できるか (ライブラリ利用の手間に関する評価) および CPU 単体や GPU 単
体と比べて高い性能を得られるか (ライブラリの性能に関する評価) についての評価
を行う.
評価は以下の 3 点について行う.
1. 単純な行列積和計算を用いた性能確認
2. HPL を用いた性能確認
3. 利用の手間に関する評価
評価環境は表 2 に示す通りである.
表 2: 評価環境 1
環境 1
CPU
環境 2
Pentium4 3.0GHz
環境 3
Athlon64X2 4600+
2.4GHz
メインメモリ
1.0GB
GPU
GeForce7800GTX GeForce7600GT GeForce7950GT
ビデオメモリ容量
256MB
GPU 接続バス
PCI-Express x16 (Gen 1)
OS
CentOS 5.0 (kernel 2.6.18)
コンパイラ
GCC 4.1.2
3.4.1
4.0GB
256MB
512MB
単純な行列積和計算を用いた性能確認
GPUPC GEMM Library は,問題サイズ (行列の一辺の長さ) が小さすぎる場合
に CPU のみで計算を行い CPU と GPU による問題分割・並列実行によって高い性
能が得られる場合にのみ並列実行するという機能を持つ (ただし CPU のみで計算を
行う問題サイズの閾値や適切な問題分割割合はチューニングスクリプトで事前に求
3.4 GPUPC GEMM Library の評価
60
めておく必要がある) ため,問題サイズに関係なく “CPU のみによる実行”,“GPU
のみによる実行”,“CPU と GPU による問題分割・並列実行” の中から最も高速な
ものを選択し実行することができる.
そこで第 1 の評価として,いくつかの問題サイズの行列積和計算に対して,CPU
と GPU の問題分割割合にいくつかの値を設定して CPU と GPU による問題分割・並
列実行の実行時間を測定する.測定結果を CPU のみによる実行や GPU のみによる
実行の実行時間と比較し,CPU と GPU による問題分割・並列実行により CPU のみ
や GPU のみよりも高い性能が得られること,また環境によっては問題サイズが小さ
すぎる場合に CPU のみの方が性能が高いことを確認し,GPUPC GEMM Library の
機能,すなわち問題サイズが小さすぎる場合に CPU のみで計算を行い CPU と GPU
による問題分割・並列実行によって高い性能が得られる場合にのみ並列実行する機
能が有用であることを示す.
以下,SGEMM を用いた性能確認,DGEMM を用いた性能確認,複数の CPU と
複数の GPU を搭載した計算機システムでの性能確認,の順で評価を行う.
SGEMM を用いた性能確認
ここでは SGEMM を用いた性能確認を行い,GPUPC GEMM Library の有用性
を確認する.
図 24 から図 26 は各実行環境に対して,CPU のみによる実行 (CPU)・GPU のみ
による実行 (GPU)・CPU と GPU を用いた並列実行 (PARALLEL) の各実行時間
(a) と,GPU のみによる実行および並列実行についての CPU に対する実行時間比
(b),さらに並列実行において最適な実行時間となった問題分割割合 (c) を示すグラ
フである.並列実行の実行時間は CPU と GPU の問題分割割合を CPU 5% : GPU
95%から CPU 95% : GPU 5%まで 5%刻みで変化させた際の最も高速な場合をとっ
ている.各実行時間には GPU を初期化する時間は含まれていないが,CPU-GPU 間
の通信時間は含まれている.
グラフからわかるように,実行時間が 0.01 秒未満と著しく短いもの (横軸の問題
サイズに*をつけたもの) を除外して見てみると,環境 1 と環境 3 は問題サイズ 512
において CPU のみや GPU のによりも並列実行の実行時間が最も短いのに対して,
環境 2 では GPU の性能が低いため並列実行の実行時間が最も短くなるのは問題サ
3.4 GPUPC GEMM Library の評価
図 24: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 1)
61
3.4 GPUPC GEMM Library の評価
図 25: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 2)
62
3.4 GPUPC GEMM Library の評価
図 26: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 3)
63
3.4 GPUPC GEMM Library の評価
64
イズ 768 からである.またいずれの環境においても問題サイズがある程度大きい場
合には並列実行の実行時間が最も短くなっている.各問題サイズにおいて最も実行
時間が短くなった際の問題分割割合をみると,それぞれ 10%以内の範囲に収まって
いることがわかる.
DGEMM を用いた性能確認
DGEMM についても SGEMM と同様の性能確認を行った.
CPU のみによる実行 (CPU)・GPU のみによる実行 (GPU)・CPU と GPU を用い
た並列実行 (PARALLEL) の各実行時間と,GPU のみによる実行および並列実行に
ついての CPU に対する実行時間比,さらに並列実行において最適な実行時間となっ
た問題分割割合を示すグラフを図 27 から図 29 に示す.
グラフからわかるように,CPU と GPU で問題分割・並列実行するよりも CPU の
みで実行した方が高い性能となる閾値や問題分割・並列実行における適切な問題分
割割合などの具体的な値は異なるものの,SGEMM と同様の傾向が見て取れる.い
ずれの環境においても SGEMM より多くの問題を GPU が担当したときに高い性能
が得られているのは,CPU の演算が DGEMM となり実行時間が長くなった一方で
GPU の演算は SGEMM のままであるため,相対的に GPU の性能が高くなり,より
多くの問題を GPU に割り当てた方が高い性能が得られたことによるものであると
考えられる.
複数の CPU と複数の GPU を搭載した計算機システムでの性能確認
環境 2 に対して,搭載されている GPU と同じ GPU をもう 1 台搭載して 2CPU
(デュアルコア CPU×1) + 2GPU の環境を作り,複数の CPU と複数の GPU を用い
た場合の性能についても性能確認を行った.以下,元の環境 2 を “1CPU+1GPU 環
境”,GPU を追加した環境を “2CPU+2GPU 環境” と呼ぶことにする.
今回の実験環境 (2CPU+2GPU 環境) では CPU に搭載された 2 つのコアは同じ性
能を持ち,また 2 台の GPU もそれぞれ同じ性能を持つ.そのため,2CPU+2GPU
の問題分割では 1CPU+1GPU 環境における問題分割を利用し,CPU A% : GPU
B%の問題分割割合だったものを CPU0 (A/2)% : CPU1 (A/2)% : GPU0 (B/2)%
3.4 GPUPC GEMM Library の評価
65
図 27: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 1:DGEMM)
3.4 GPUPC GEMM Library の評価
66
図 28: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 2:DGEMM)
3.4 GPUPC GEMM Library の評価
67
図 29: 各問題サイズに対する実行時間と CPU に対する実行時間比 (環境 3:DGEMM)
3.4 GPUPC GEMM Library の評価
68
: GPU1 (B/2)%という割り当てにすることである程度高い性能が得られると期待で
きる.
“SGEMM を用いた性能確認” からわかるように 1CPU+1GPU 環境における最適
な問題分割割合が CPU 50% : GPU 50%であったことから,2CPU+2GPU 環境では
2CPU (ATLAS によるマルチスレッド処理) に 50%を割り当て,残りの 50%を 2GPU
で均等に分割して実行時間を測定した.図 30 は,CPU のみによる実行 (CPU)・
GPU のみによる実行 (GPU)・1CPU+1GPU 環境での並列実行 (1CPU+1GPU)・
2CPU+2GPU 環境での並列実行 (2CPU+2GPU) の 4 環境についての実行時間と,
それぞれ CPU のみによる実行に対する実行時間比を示したグラフである.グラフ
からわかるように,2CPU+2GPU 環境では 1CPU+1GPU 環境と比較してさらに実
行時間を短縮することができている.
まとめ
以上のように,CPU と GPU による問題分割・並列実行は CPU のみや GPU のみ
と比べて高い性能を得られる可能性がある一方で,問題サイズが小さすぎる場合に
は CPU のみで計算を行う方が問題分割・並列実行するよりも高い性能が得られ,ま
た問題サイズが大きい場合には CPU の GPU の性能バランスに対応した一定の割合
で問題分割・並列実行を行うことで高い性能を得られることが確認できた.
GPUPC GEMM Library では並列実行により実行時間が短くなる問題サイズの閾
値や最適な問題分割割合をチューニングスクリプトを用いて調査し,また調査した
結果を用いて常に高い演算性能を発揮することができる.アプリケーションプログ
ラマは本ライブラリを用いない場合,自ら手間のかかる CPU と GPU による並列処
理を実装しなくてはならないうえに,対象問題の問題サイズによって CPU のみで
の実行,GPU のみでの実行,CPU と GPU による問題分割・並列実行の中から適切
な実行方法を選択しなくてはならない.GPUPC GEMM Library はこうしたアプリ
ケーションプログラマにとっての手間を削減することができるため有用であると言
える.
3.4 GPUPC GEMM Library の評価
図 30: 2CPU+2GPU での性能評価 (SGEMM)
69
3.4 GPUPC GEMM Library の評価
3.4.2
70
HPL ベンチマークを用いた性能確認
第 2 の評価として,環境 1 に対して HPL ベンチマークを用いた性能確認を行った.
本項では,HPL ベンチマークは単一 CPU 上で実行する際にも性能チューニングを
行わなくては良い性能が得られないことから,はじめに CPU による HPL の実行と
解析および性能チューニングを行い,その結果を踏まえて GPUPC GEMM Library
を用いた HPL ベンチマークを行うこととする.
CPU による HPL の実行と解析および性能チューニング
HPL ベンチマークは,計算機の性能指標として用いられているベンチマークの 1
つであり,世界中の計算機の性能を競う TOP500 に用いられているベンチマークと
して広く知られている.並列計算機の性能評価によく用いられるベンチマークであ
るが,1 ノードの PC でも問題なく動作する.
HPL の実行時間の多くは行列積和計算によって占められており,その計算には
ATLAS などの数値計算ライブラリを利用するように設定することができる.ATLAS
を利用する場合には,cblas dgemm 関数によって演算が行われる.
HPL は図 31 に示す 16 の性能パラメタによるチューニングを行うことができる
[89].これらのパラメタのうち,1 ノードでの実行において性能を大きく左右するの
は問題サイズとブロックサイズの 2 つのパラメタである.
問題サイズについては,基本的には問題サイズが大きな方が高い性能が得られる.
しかしながら,使用可能な物理メモリサイズを超える大きさになると性能が著しく
低下する.つまり,この値は実行環境の物理メモリ搭載量によって左右される.ブ
ロックサイズについては,CPU のキャッシュサイズに応じた値を指定することで良
い性能を得ることができる.ATLAS のインストールログの値を参考にすると良い
とされており,本実験環境におけるインストールログからは 72 の倍数が適切である
ことが確認できた.
そこで,以下の 2 つの実験を行った.
第 1 の実験として,ブロックサイズを 72 としたうえで問題サイズを 1000 ずつ変更
しながら HPL を実行した.その結果,問題サイズ 11000 までは性能が向上するが,
問題サイズ 12000 になると性能が急激に低下するという結果が得られた (図 32).
3.4 GPUPC GEMM Library の評価
71
第 2 の実験として,問題サイズを 11000 に固定しブロックサイズを 2 ずつ変更し
ながら HPL を実行したところ,72 の倍数のときに良い性能が得られることが確認
できた (図 33).
以上から,実験環境 1 においては,問題サイズ 11000,ブロックサイズ 72 におい
て,最大性能 FLOPS 値 4.04GFLOPS を得ることができた.
− 問 題 サ イ ズ (29 ,30 ,34 ,35)
− ブ ロ ッ ク サ イ ズ (1 ,2 ,3 ,4)
− プ ロ セ ス グ リ ッ ド の サ イ ズ ( 2 x2 , 1 x4 , 4 x1 )
− 解 の チ ェ ッ ク に お け る 残 差 の 境 界 線 (16.0)
− Panel F a c t o r i z a t i o n の ア ル ゴ リ ズ ム ( l e f t , Crout , Right )
− 再 帰 的 Panel F a c t o r i z a t i o n の ア ル ゴ リ ズ ム ( l e f t , Crout , Right )
− 再 帰 的 F a c t o r i z a t i o n に お け る subpanel 数 (2)
− 再 帰 的 F a c t o r i z a t i o n に お け る subpanel 幅 の 最 小 値 (2)
− Panel B r o a d c a s t の ト ポ ロ ジ ( 1 r g )
− Look−ahead の 深 さ ( 1 )
− Update に お け る 通 信 ト ポ ロ ジ ( mix )
− long に お け る U の 平 衡 化 処 理 の 有 無 ( 有 )
− mix に お け る 行 数 の 境 界 値 ( 6 4 )
− L1 パ ネ ル の 保 持 の 仕 方 ( t r a n s p o s e d )
− U パ ネ ル の 保 持 の 仕 方 ( transposed )
− メ モ リ の alignment (8)
図 31: HPL の性能パラメタ (括弧内は初期値)
GPUPC GEMM Library を用いた HPL ベンチマーク
GPUPC GEMM Library を用いて HPL ベンチマークを実行する前に,CPU 向け
の HPL ベンチマーク結果を参考にして GPUPC GEMM Library を用いた HPL ベン
チマークの問題設定を検討する.
GPUPC GEMM Library では CPU から GPU へのデータ転送において一定のメイ
ンメモリが必要となることから,HPL の問題サイズを CPU による HPL ベンチマー
クで高い性能が得られる範囲における最大の問題サイズではなく,ある程度小さい
値で行う必要がある.
3.4 GPUPC GEMM Library の評価
図 32: CPU による HPL の性能調査:問題サイズと性能 (環境 1)
図 33: CPU による HPL の性能調査:ブロックサイズと性能 (環境 1)
72
3.4 GPUPC GEMM Library の評価
73
また第 1 の評価の結果から,問題分割・並列実行によって高い性能を発揮するには
DGEMM の問題サイズがある程度大きい必要があることが判明している.そのため,
仮に HPL 内で実行される DGEMM の問題サイズが全て小さい場合は,分割実行に
より良い性能を得ることが困難であると言える.そこで,HPL における DGEMM
の実行について確認した.その結果,次のようなパターンとなっていることが確認
できた.なお,文中の問題サイズ MNK は図 21 に対応している.
1. HPL 内では DGEMM を繰り返し実行している.
2. DGEMM の問題サイズ M は,HPL の問題サイズから次第に小さくなっていく.
3. DGEMM の問題サイズ N と K は,次項 (4) の場合を除いてブロックサイズ未
満の小さな値である.
4. “一定の周期” で,問題サイズ N が問題サイズ M+1,問題サイズ K がブロック
サイズ,という “比較的大きな DGEMM” が実行される.
5. ブロックサイズが大きいほど,“一定の周期” は長い周期になり,HPL 全体に
おいて “比較的大きな DGEMM” が実行される回数も減少する.
実行パターンから,GPUPC GEMM Library は “比較的大きな DGEMM” のみを適
切に問題分割・並列実行することで高い性能が得られることが期待できる.
既に述べたように,CPU 単体での HPL ベンチマークにおいてはブロックサイズ
が 72 の倍数の時に良い性能が得られる.並列実行では問題サイズが大きなときに良
い性能が得られることから,これらの数の倍数の中から適当な値を選択することで
高い性能が得られると考えられる.
以上の検討結果から,問題サイズは 8000 に固定し,ブロックサイズは 72 の倍数
をいくつか試すことで良いベンチマーク結果が得られると考えられる.なお,問題
サイズ 8000,ブロックサイズ 72 における CPU のみを用いた HPL ベンチマークの
性能は 3.90GFLOPS であった.
検討結果に基づき環境 1 にて HPL ベンチマークを行った結果を図 34 に示す.横
軸にはブロックサイズ,縦軸には性能 FLOPS 値をとっている.
グラフからわかるように,本環境ではブロックサイズが 576 のときに最も高い性
能が得られており,その性能 FLOPS 値は 5.86GFLOPS であった.CPU による HPL
3.4 GPUPC GEMM Library の評価
74
図 34: GPUPC GEMM Library を用いた HPL の実行結果 (環境 1)
の最大性能 FLOPS 値が 4.04GFLOPS であったことから,提案方式による速度向上
率は 45.0%となる.
以上の結果から,GPUPC GEMM Library を用いることで高い性能を得られるこ
とが示された.
ただし,演算精度には問題が残った.HPL は演算の途中と終了時に演算精度の確
認を行う機能を備えている.GPUPC GEMM Library を用いて HPL を実行した場
合,終了時の演算精度確認をパスすることができなかった.GPU による演算が単精
度であるために計算誤差が大きくなってしまったことが理由であると考えられる.既
に述べたように本アプローチでは演算精度の改善を行わない方針であり,性能評価
の結果から本アプローチにより高い演算性能を得られることが確認できたと見なす.
なお,HPL 内の DGEMM 演算を全て GPU のみで実行することも可能である.し
かしながら,問題サイズが小さいときに高い性能が得られないため,全体として低
い FLOPS 値が得られることが明らかである.実際に測定を行った結果,1GFLOPS
にも満たない低い性能が得られた.
3.4 GPUPC GEMM Library の評価
3.4.3
75
利用の手間と得られる性能に関する評価
最後に,GPUPC GEMM Library の利用の手間と得られる性能に関する評価を
行う.
GPUPC GEMM Library は既存の BLAS と同様の API をアプリケーションプロ
グラマに提供する.そのためアプリケーションプログラマは,対象となる BLAS 関
数 (cblas sgemm,cblas dgemm) を利用しているプログラムに対して,関数名の変更
(およびリンクするライブラリの追加・変更) のみで GPUPC GEMM Library を適
用することができる.
GPUPC GEMM Library が高い性能を得るためには,実行環境に依存する性能パ
ラメタとして,CPU のみで計算するか CPU と GPU で問題分割・並列実行を行う
かの閾値と,CPU と GPU での問題分割割合を適切に選択する必要がある.そこで,
チューニングスクリプトを作成し,ライブラリインストール時にこれを用いること
で適切な閾値と問題分割割合を自動的に求めて利用できるようにした.
以上により,HPL を用いた性能評価においてもプログラムの変更は関数名の変
更のみに抑えられた.GPUPC GEMM Library を正しくリンクするために HPL の
Makefile を数カ所編集する必要はあったが,アプリケーションプログラマにとって
大きな手間とはなっていないと考えられ,手間をかけずに高い性能を得られたと言
える.
一方で GPUPC GEMM Library を用いた HPL の性能チューニングにおいては,
通常の HPL のチューニングに加えて,問題サイズをやや小さくすることとブロック
サイズを大きめにするという,GPUPC GEMM Library を利用することを意識した
HPL のチューニングが必要となった.しかしこれらのチューニングについては “ラ
イブラリがメインメモリを多めに確保する” や “問題サイズが大きい方が高い性能が
得られる” といった GPU のアーキテクチャなど GPGPU 特有の情報が表面化しない
最適化パラメタに置き換えることができるため,大きな手間とはならないものと考
えられる.
以上のように,GPUPC GEMM Library はアプリケーションプログラマが大きな
手間をかけずに GPU の持つ高い性能を有効に活用できるようにすることができた
と言える.
最後に参考値として,GPUPC GEMM Library にどの程度の行数のプログラム記
3.4 GPUPC GEMM Library の評価
76
述を行っているか,本アプローチに基づくライブラリが存在しない場合にはどの程
度の実装の手間がかかるのかを確認する.
• 問題分割・並列実行に関する記述 (CPU 上で動作するプログラム) : 4000 行程
度.ただし SGEMM と DGEMM で似たような記述を繰り返している部分が多
いため,実質 2000 行程度.
• シェーダプログラム (GPU 上で動作するプログラム) : 100 行程度.ただし行
列の ORDER と転置のパラメタに対応するため類似したプログラムが複数存
在する.
• OpenGL やシェーダの初期化などに関する記述 (CPU 上で動作するプログラ
ム) : 1000 行程度.
• 複数 CPU や複数 GPU 向けの記述 (CPU 上で動作するプログラム) : 3000 行
程度.
GPUPC GEMM Library は合計 6000 行程度 (複数 CPU や複数 GPU 向けの実装で
は合計 10000 行程度) で書かれたプログラムである.このうち問題分割・並列実行
に関する記述が本アプローチの中心となる部分であり,アプリケーションプログラ
マにとっては,この行数分の手間が削減されていると言える.
77
並列化プログラミング環境によるアプローチ
4
本章では,既存の CPU 向け並列化プログラミング環境を用いて GPGPU プログ
ラムを作成できるようにすることでアプリケーションプログラマに対して GPGPU
プログラムに関する知識や技術を習得する手間を削減するアプローチを提案する.
はじめに本提案の着眼点である既存の CPU 向け並列化プログラミング環境を用い
た GPGPU プログラミングの概要を述べ,次に既存の CPU 向け並列化プログラミ
ング環境と GPGPU および CUDA との対応付けについて述べる.さらに提案を元
に作成した処理系 “OMPCUDA” の設計と実装について述べ,テストプログラムを
用いて評価を行う.
4.1
既存の CPU 向け並列化プログラミング環境を用いた GPGPU
プログラミングの提案
GPU は内部の演算器にハードウェアレベルでの高い並列性を備えた並列処理によ
る高い演算性能を持つハードウェアである.そのため GPU は並列性の高いプログ
ラムに対する性能向上が期待されている.しかしながら GPU プログラミングには
GPU プログラミング独自の並列化プログラミング環境を用いる必要があるため,ま
た GPU のアーキテクチャについての知識が必要なため,アプリケーションプログ
ラマにとって GPU プログラミングは難しく手間がかかるものとなっている.
一方で CPU を対象とした並列化プログラミングに関する研究はこれまでに数多く
行われてきた.現在では単純なループの並列化など一部のプログラムについては自
動並列化コンパイラによる並列化でも高い性能を得ることが可能となっているもの
の,一般的な多くのプログラムではアプリケーションプログラマによる並列化記述
が必要である.そのため様々な並列化プログラミングのためのプログラミング環境
が提案されており,いくつかの並列化プログラミング環境は多くのアプリケーショ
ンプログラマに利用されている.したがって,GPGPU プログラミングにもこれら
の並列化プログラミング環境が利用できれば,アプリケーションプログラマにとっ
て GPU のアーキテクチャに関する理解や GPGPU プログラミング独自の並列化手
法,並列化プログラミング言語の習得といった手間が削減され,GPGPU を容易に
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
78
利用可能になると考えられる.
そこで,既存の CPU 向け並列化プログラミング環境を用いた GPU プログラミン
グを提案する.以下本節では,既存の CPU 向け並列化プログラミング環境のいくつ
かについて,現在の一般的な GPU との対応付けを考える.さらに GPU アーキテク
チャの 1 つである CUDA を対象として,既存の CPU 向け並列化プログラミング環
境と GPU プログラミングとのより具体的な対応付けの検討を行う.
4.1.1
既存の CPU 向け並列化プログラミング環境と GPGPU
本項では既存の CPU 向け並列化プログラミング環境を用いた GPU プログラミン
グについての検討を行う.具体的には,現在普及している GPU のアーキテクチャを
元に典型的な GPU のハードウェア構成を想定し,既存の CPU 向け並列化プログラ
ミング環境との対応付けを考える.
2008 年の時点で普及している GPU,GeForce シリーズ [90, 40] と Radeon シリー
ズ [91] のアーキテクチャを元に典型的な GPU のハードウェア構成を想定し,想定
したハードウェア構成と既存の CPU 向け並列化プログラミング環境との対応付け
を検討する.
現在の GPU に搭載されている各演算器は同時期の CPU コアと比べると単純な構
造で演算性能も低いものの,多数の演算器を搭載することで GPU 全体での演算性
能を高めている.また,GPU 上には CPU(マザーボード上) のメインメモリとは独
立に比較的大容量 (最大で数 GB) かつ GPU 内部の各演算器から読み書き可能なメ
モリ (DRAM) が搭載されている.
さらに GPU 上の演算器は数個ごとに演算器群を構成しており,GPU 上には同一
演算器群の演算器のみが読み書き可能な高速・小容量のオンチップメモリも搭載さ
れている.このように演算器とメモリに階層性を持つ Device(GPU) が PCI-Express
などのバスによって Host(CPU やメインメモリが搭載されたマザーボード) に接続
されている.GPU は CPU によって演算開始などの指示を受ける必要があるものの,
CPU と同時に演算を行うことができる.
以上を元に想定した GPU のハードウェア構成を図 35 に示す.
vvGPGPU における典型的な GPU の活用方法は,対象アプリケーションの中か
ら並列性が高いタスクを抽出して GPU に実行させることである.この場合におけ
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
79
図 35: 典型的な GPU のハードウェア構成
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
80
る CPU-GPU 間での通信と演算の流れは,CPU がメインメモリ上のデータ (変数・
配列) を GPU 上のメモリへ転送し,GPU が (もしくは CPU と GPU がそれぞれ) 演
算を行い,CPU から GPU への指示によって GPU 上のメモリからメインメモリへ
演算結果などのデータが転送されるというものである.
こうした一連の処理を行うには GPU の実行制御やメインメモリと GPU 上のメモ
リの間での通信が必要である.通信や制御を既存の CPU 向け並列化プログラミン
グ環境を用いて記述することができれば,GPU プログラミングが容易に行えるよう
になると考えられる.
さらに GPU の持つ高い並列実行性能を活用するには,GPU 内部の並列性を利用
する必要がある.ただし GPU にどのようなメモリが搭載されているかや搭載され
ているメモリが CPU 側からどのようにアクセスできるかは対象とする GPU のアー
キテクチャやドライバなどに依存する.
GPU 上の演算器やメモリを用いた並列処理を既存の CPU 向け並列化プログラミ
ング環境を用いて記述することができれば,GPGPU プログラミングが容易に行え
るようになると考えられる.
一方で CPU 向けの並列化プログラミングについては,CPU 内の SIMD 演算器,
SMP (共有メモリ型並列計算機,Symmetric Multiple Processor/Shared Memory
Multiprocessor),マルチコア CPU,PC クラスタなど既に様々な環境に向けて数多
くの研究が行われている.またアプリケーションプログラマが明示的に並列性を記述
する際に用いられている手法やライブラリとしては,SIMD 関数,pthread (POSIX
Threads) などのスレッドライブラリ,OpenMP,MPI をはじめとした通信ライブラ
リなどが広く利用されている.そこで,GPGPU における並列処理の記述に対する
これらの並列化プログラミング環境の適用可能性を考えることにする.
SIMD プログラミング
複数のデータに対して同時に同じ演算を行う SIMD 演算は,マルチメディア処理
をはじめとした様々な処理の高速化に有効である.SIMD 化についてはコンパイラ
による自動 SIMD 化によってもある程度の性能が得られることが知られている [92]
が,これを利用するにはコンパイラの SIMD 化変換パターンに適したコードを書く
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
81
必要があることから扱いやすいプログラミング環境であるとは言い難く [93],イン
ラインアセンブラや SIMD 関数を用いたプログラミングが行われている [94, 95].
SIMD 演算は細粒度のデータ並列処理に適している.そこで,GPU 内部の各演算
器を SIMD 演算ユニットと見なしてデータ並列演算と対応付けることで,GPU 上
の演算器による並列処理を SIMD 関数などを用いて記述できるようになると考えら
れる.
スレッドライブラリを用いたマルチスレッドプログラミング
近年普及が進んでいるマルチコア CPU を含めた共有メモリ型並列計算機では,ス
レッドを用いた並列化が広く行われている.特に共通化されたスレッドライブラリ
pthread は多くの計算機環境 (OS) に対応しているため広く普及している.
スレッドプログラミングでは複数のスレッドが共有メモリを利用して並列処理を
行うことから,GPU 上の演算器間の並列性や演算器群間の並列性の記述との適用性
が高いと考えられる.
一方で,CPU から GPU に対する演算の指示をスレッドプログラミングの手法で
記述することも考えられる.スレッドプログラミングでは一般的に関数単位でのス
レッド割り当てを行う.そこで,スレッドプログラミングにおけるスレッド化対象の
関数を GPGPU プログラムにおいては GPU に実行させる,といったプログラミン
グモデルの対応付けが考えられる.ただし対応付けを行うには,CPU と GPU は独
立したメモリ空間を持つため,スレッド内部で利用するデータを CPU-GPU 間で送
受信する必要がある.そのためにはコンパイラによる静的なデータ参照の解析を行
うか,可能であるならば SDSM[96, 97] のようにメモリアクセスのたびに CPU-GPU
間でデータを送受信する機構を提供する必要があると考えられる.
OpenMP を用いた並列化プログラミング
pthread などのスレッドライブラリを用いた並列化をより容易に記述する方法と
して,OpenMP[98] を用いた並列化が利用されている.OpenMP による並列化プロ
グラミングは逐次プログラムに指示子を追加することによって行われ,特にループ
の並列化など共有メモリを用いた典型的な並列処理を容易に記述することができる.
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
82
OpenMP の典型的な対象問題である共有メモリを用いたループの並列化を GPGPU
と対応付ける場合,GPU 上には階層的な共有メモリが存在するため,演算器間で
の並列処理を OpenMP と対応付けて記述することや,演算器群間での並列処理を
OpenMP と対応付けて記述することが考えられる.またマルチスレッドプログラミ
ングと同様に,実行前や実行時に並列処理部で利用するデータを特定し CPU-GPU
間で送受信することができれば,逐次実行部を CPU で実行し並列実行部を GPU で
実行するような OpenMP と GPU プログラミングとの対応付けが可能になると考え
られる.
通信ライブラリを用いたマルチプロセスプログラミング
分散メモリ型並列計算機や PC クラスタなどの共有メモリを持たない環境におい
て,また共有メモリ型並列計算機においてもきめ細かい通信制御によって高い性能
を得るために,通信ライブラリを用いたマルチプロセスプログラミングによる並列
化が行われている.特に MPI[99, 100] は様々な実行環境向けの実装が行われており
広く普及している.
通信ライブラリを用いた並列化は SIMD 演算やマルチスレッドプログラミングと
比べてやや粒度の大きな並列化に用いられることが多いため,GPGPU においては
GPU 上の演算器群間における並列性の記述に利用することで GPGPU とマルチプ
ロセスプログラミングの適切な対応付けが行えると考えられる.一方で GPU 上に
は比較的大容量の共有メモリが存在している.既存の共有メモリ型並列計算機にお
いては,共有メモリが利用可能であっても MPI を用いて細かい通信制御を行うこと
で並列化オーバヘッドが削減でき (OpenMP と比べて) 高い性能が得られることが知
られており,GPGPU においても CPU と同様に共有メモリと通信ライブラリを用い
た並列化記述を利用する価値があると考えられる.
さらに,CPU-GPU 間でのデータ送受信に通信関数を利用することも考えられる.
CPU と GPU はそれぞれ独立したメモリを持つため,GPU を計算ノードと見なした
うえで分散メモリ型並列計算機向けの通信ライブラリと同様のインターフェイスを
用いて CPU-GPU 間のデータ通信を記述し,CPU と GPU 上の演算器群での通信を
行いながら処理を行うプログラムが作成できる可能性がある.しかしながら,GPU
は CPU と並列に演算を行う事ができるものの,演算の開始や CPU-GPU 間でデー
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
83
タの送受信を行うは CPU による制御が必要なため,既存の CPU 向けプログラムと
同様の記述や動作が行えない可能性もある.
以上のように,GPGPU の持つ並列性は既存の CPU 向け並列化プログラミング
環境を利用して記述できることが期待できる.
さらに,CPU-GPU 間での通信を MPI で記述し,GPU 上の演算器群間での並列
処理を OpenMP で記述し,演算器群内の演算器間での並列処理を SIMD 関数で記述
するなど,既存の CPU 向け並列化プログラミング環境を複数組み合わせて利用す
ることも考えられる.これにより GPU の持つ並列性を適切かつ容易に記述できる
可能性がある一方,複数の並列化プログラミング環境を組み合わせたプログラミン
グはアプリケーションプログラマにとっての実装の手間を増加させてしまうこと考
えられる.
4.1.2
既存の CPU 向け並列化プログラミング環境と CUDA
前項では典型的な GPU を想定し既存の CPU 向け並列化プログラミング環境との
対応付けを検討した.一方で演算器やメモリなどのハードウェア構成とは有効に対
応付けられると期待できる CPU 向けの並列化プログラミング環境であっても,提
供されている GPU プログラミング環境で利用可能な API 等の都合により現実的に
は実装することができない可能性や,高い性能が得られない可能性がある.
そこで本項では,GPGPU 環境の 1 つである CUDA を対象として,既存の CPU
向け並列化プログラミング環境と GPGPU とのより具体的な対応付けを検討する.
実行対象として CUDA を選択した理由は,CUDA ではシェーダ言語を用いたグラ
フィックスプログラミングと比べて GPU に対するプリミティブな操作が可能である
こと,シェーダ言語を用いたグラフィックスプログラミングでは 1 度の描画パス中
におけるテクスチャデータの更新ができない (GPU 上の比較的大容量な共有メモリ
に対して書き込んだ値は,同じ描画パスで読み込むことができない) ためにプログ
ラム変換の手間が増加すると考えられること,そして CUDA を用いたプログラムと
C 言語を用いたプログラムとの記述の差はグラフィックス API とシェーダ言語を用
いたプログラムと C 言語を用いたプログラムとの記述の差と比べて小さく処理系を
実装する際の手間をある程度抑えられると考えたことによるものである.
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
84
CUDA
CUDA は GPU をデータ並列計算機として活用するためのハードウェアとソフト
ウェアのアーキテクチャであり,アプリケーションプログラマに対して C/C++を
拡張した言語仕様のプログラミング言語による GPGPU プログラム開発環境を提供
している.CPU 上で実行される実行ファイルについては CUDA の提供するライブ
ラリをリンクする必要がある以外は既存の CPU 向けプログラムと同様に (gcc など
を用いて) 作成することが可能であり,GPU 上で実行される実行ファイルは専用の
コンパイラ (nvcc) を用いて生成する必要がある.
ここでは CUDA と既存の CPU 向け並列化プログラミング環境との対応付けの検
討に向けて,CUDA の実行モデルと演算器やメモリの配置および標準的な C/C++
とのプログラム記述の違いを確認する.
CUDA における GPU のハードウェアモデルを図 36 に示す.GPU は Streaming
Multiprocessor(以下 SM) と呼ばれる演算ユニット (演算器群) を複数個 (GPU によっ
て異なるが,現在は GPU1 台あたり 1 から 30 個) 搭載しており,さらに SM 内には
Scalar Processor(以下 SP) と呼ばれる演算器を 8 個搭載している.
これに対して並列実行の単位としては Grid,Block,Thread がある.
Grid は CPU が GPU に演算を実行させる際の単位である.GPU への演算の指定
は関数単位で行う必要があるため,GPU に対する 1 関数呼び出しを 1Grid と考えれ
ば良い.
Grid は複数の Block(以下 CUDA Block と呼ぶ) から構成され,さらに CUDA Block
は複数の Thread(以下 CUDA Thread と呼ぶ) から構成される.CPU から GPU に
処理を行わせる際には,1Grid の実行において使用する CUDA Block の数と CUDA
Block あたりの CUDA Thread の数 (各 CUDA Block で異なる数とすることは不可能)
を指定する.これにより CU DABlock 数 × CU DAT hread 数 個のタスクが生成され,
CUDA Block 単位で SM に割り当てられる.各 CUDA Block 内の CUDA Thread は
同一 SM 内の SP によって並列実行される.なお,CUDA Block 数や CUDA Thread
数は Grid 内で変更することはできない.Grid 実行時には CUDA Block ごとおよび
CUDA Thread ごとに一意に割り当てられた ID を取得することができるため,この
ID を利用してデータ並列処理を行うのが CUDA における並列プログラムの基本と
なる.
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
85
図 36: CUDA のハードウェアモデル
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
86
物理的な SM や SP の数以上の CUDA Block や CUDA Thread が割り当てられた
場合は時分割実行される.CUDA におけるタスクスイッチのコストは小さいため,
SM には SP 数を上回る CUDA Thread 数を割り当て,時間のかかるメモリアクセス
が起きた際にタスクスイッチが行われメモリアクセスのレイテンシが隠蔽されるよ
うに実装するのが良いとされている.適切な 1CUDA Block あたりの CUDA Thread
数の目安としては 256 程度が良いとされているが,対象プログラムに含まれる命令
の数やメモリアクセスの種類と頻度等により最適な値は上下する.
GPU 内の各 SM は独立に処理を行う事ができる一方,同一 SM 内の SP は同時に
同種の演算しか行う事ができない.そのため同一 SM 内の SP が異なる分岐パスを
辿るようなプログラムを記述した場合は,正しい実行結果を返すことは可能である
もの,条件が成立しない命令についてはマスク処理を行うため性能が低下する.
一方,CUDA における GPU を用いた計算モデルは以下の処理を繰り返すモデル
である.
1. CPU がメインメモリ上のデータを GPU 上のメモリへと転送する
2. CPU から GPU に対して関数 (Grid) 実行を指示し,GPU が演算を開始する
3. GPU の演算が終了した後に,CPU から GPU への指示によって GPU 上のメ
モリからメインメモリへ演算結果などのデータが転送される
メインメモリと GPU 上のメモリの間におけるデータの送受信については,CPU 上
のプログラムから GPU 上のメモリのアドレスを直接参照することはできず,メモ
リの確保や転送を行う API 関数を介して行う必要がある.また GPU 上には複数種
類の異なる特徴を持つメモリが存在し,全てのメモリを CPU から操作できるわけ
ではない.
GPU 上のメモリは図 37 のように分類され,各メモリはそれぞれ以下のような特
徴を持っている.
1. GlobalMemory:全 CUDA Block および全 CUDA Thread から共有メモリとし
て読み書き可能.(高レイテンシ・低速・大容量)
2. ConstantMemory:全 CUDA Block および全 CUDA Thread から読み取り専用
のメモリとして扱うことができる.(高レイテンシ・キャッシュされる・GPU
全体で 64KB)
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
87
3. TextureMemory:全 CUDA Block および全 CUDA Thread から読み取り専用
のメモリとして扱うことができる.(高レイテンシ・キャッシュされる・大容量)
4. SharedMemory:各 CUDA Block が独立に持ち同一 CUDA Block 内の CUDA
Thread からは共有メモリとして読み書き可能.
(オンチップ・低レイテンシ・
高速・SM ごとに 16KB)
5. 各 CUDA Thread が独立に持つ Register(
.低レイテンシ・高速・SM ごとに 8192
本または 16384 本)
6. 各 CUDA Thread が独立に持つ LocalMemory.
(GlobalMemory と同等)
GlobalMemory,ConstantMemory,TextureMemory については,専用のメモリ操作
関数を用いることで CPU から Grid を実行する前後に読み書きすることができるが,
その他のメモリについては CPU からアクセスすることはできない.
CUDA におけるプログラム記述では変数宣言時に接頭語を付加することでその変数
がどのメモリとして扱われるかを指定する. device をつけることで GlobalMemoy,
constant で ConstantMemory, shared で SharedMemory として扱われる.TextureMemory は専用の関数と構造体を用いて利用する.接頭語をつけずに関数内で
宣言された変数は Register として扱われ,Register の数を超えた分は自動的に Lo-
calMemory として扱われる.
変数と同様に,関数についても接頭語を利用して振る舞いを指定する.
global をつけた関数 (Global 関数) は CPU から呼び出されて GPU 上で実行さ
れる関数として, device をつけた関数 (Device 関数) は GPU 上で実行される関数
( global 関数もしくは device 関数 ) から呼び出されて GPU 上で実行される関数
として扱われる.これらの関数は GPU 上で実行可能なバイナリのみが生成される.
host をつけた関数 (Host 関数) は CPU 上で実行される関数から呼び出されて
CPU 上で実行される関数として扱われ,接頭語のない関数もこれと同じ扱いとなる.
host と device を同時につけた場合は, device をつけた関数と同様に GPU 上
で実行可能なバイナリが生成されるとともに, host をつけた関数と同様に CPU
上でも実行可能となる.
CPU から行う Global 関数の呼び出しは,関数の終了を待たずに制御が戻る非同
期呼び出しである.そのためマルチスレッド化など手間のかかるプログラム記述を
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
88
図 37: CUDA のメモリモデル
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
89
行うことなく CPU と GPU による並列処理を記述することができる.CPU 上で専
用の関数を実行することで,Global 関数の終了を確認する (待つ) ことができる.
GPU 上で実行される関数については,C/C++言語と比べて再帰呼び出しや static
変数が使えないといった制限がある.また CUDA 特有の処理として,同一 CUDA
Block 内の全 CUDA Thread で同期をとる関数や,GPU 全体でのアトミック実行を
保証する atomic 関数が提供されている.
このように,CUDA を用いてプログラムを作成するには,GPU のアーキテクチャ
や実行モデル,プログラムの記述方法を把握し,手間のかかるプログラミングを行
わなくてはならずアプリケーションプログラマにとっては手間が大きい.特に GPU
を最大限に活用して高い性能を得るためには,GPU 上に搭載されている多数の演算
器と様々なメモリを活用する必要があるため,アプリケーションプログラマにとっ
てのプログラミングの手間は非常に大きなものとなる.
なお本研究では複数の GPU を搭載した環境向けの実装を行っていないため詳細
については触れないことにするが,CUDA は複数の GPU にも対応している.
以下,CUDA と既存の CPU 向け並列化プログラミング環境との対応付けを検討
する.
SIMD プログラミング
SIMD 処理は多数のデータに同じ演算を行うものである (図 38-1) ことから,同時
に同じ種類の演算しか行うことができない同一 SM 内の SP による CUDA Thread レ
ベルの並列処理にも,CUDA Block レベルの並列処理にも対応付けることができる
と考えられる.
特に SIMD 化は細粒度の並列化に適していることから,SIMD 演算を多数の CUDA
Thread による SharedMemory を用いた並列計算へと対応付けることで,高速な SharedMemory を有効に活用した高速処理による高い性能が期待できる (図 38-2).
一方で,GlobalMemory を共有メモリと見なして CUDA Block レベルの並列性を
記述し,SIMD 関数へのデータセットを CPU から GPU へのデータ転送,SIMD 関
数の実行を GPU 上での演算とみなし,GPU 全体で SIMD 演算を行うことも考えら
れる (図 38-3).この対応付けでは,アプリケーションプログラマに対して CUDA プ
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
90
図 38: SIMD プログラミングと CUDA との対応付け
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
91
ログラミングそのものを隠蔽することが可能となり,習得や実装の手間が大きく削
減できる可能性がある.
スレッドライブラリを用いたマルチスレッドプログラミング
CPU 向けの pthread による並列プログラミングでは,各スレッドの行う処理を関
数単位でそれぞれ記述し,スレッドごとに任意のタイミングでの実行制御を行う (図
39-1).一方で CUDA において pthread のスレッドのように独立して処理を行うこと
ができる実行単位としては,CUDA Block レベルでの並列処理が考えられる.しか
しながら CUDA では全 CUDA Block・全 CUDA Thread が同時に演算を開始し,ま
た CPU が GPU の演算終了を待つ場合には全 CUDA Block・全 CUDA Thread の演
算終了を待つという実行モデルとなっている.そのため,pthread のように任意の
タイミングで個別のスレッドを生成・破棄することができず,実行モデルを合わせ
ることができない (図 39-2).
別の対応付けとしては,CUDA では CPU から GPU に対する処理の呼び出しを関
数単位で行うことから,GPU 全体の処理を 1 スレッドとして記述し GPU の数をス
レッドプログラミングにおけるスレッド数に対応付けることによるマルチスレッド
プログラムと CUDA との対応付けが考えられる.しかしながらこの対応付けでは,
CPU と各 GPU では共通のメモリ空間を持つことができないため,スレッド間で共
有メモリを利用するスレッドプログラミングの基本的な動作を対応付けることがで
きない (図 39-3).
以上から,実行モデルやメモリモデルの対応付けが難しいため pthread などのス
レッドライブラリを用いたマルチスレッドプログラミングの手法は CUDA プログラ
ミングに適しているとは言い難い.
OpenMP を用いた並列化プログラミング
CPU 向けの OpenMP を用いた並列化プログラミングでは,複数のスレッドが共有
メモリを用いた並列処理を行う (図 40-1).OpenMP の典型的な並列化対象問題であ
るループの並列化と CUDA の対応付けを考えた場合,CUDA では GlobalMemory を
GPU 上の全 CUDA Block・全 CUDA Thread が,また SharedMemory を各 CUDA
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
92
図 39: スレッドライブラリを用いたマルチスレッドプログラミングと CUDA との対
応付け
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
93
Block 内の全 CUDA Thread が共有しているため,GlobalMemory を共有メモリと見
なした GPU 全体での大規模な並列化,もしくは SharedMemory を共有メモリと見
なした局所的な並列化が行えると考えられる (図 40-2).
また CUDA Block 単位では同時に異なる種類の演算を行うことができるため,sec-
tions 並列の各 section を CUDA Block に対応付けることも考えられる.さらに階層
的な並列性を持つ OpenMP プログラムについても,上位の階層を CUDA Block に,
下位の階層を CUDA Thread に対応付けることで適切な対応付けが行えると考えら
れる.
OpenMP を用いた並列化では,アプリケーションプログラマが指示子を用いて明
示的に指定した部分のみが並列実行され,その他の部分は逐次実行される.そのた
め逐次実行部と並列実行部の境界が明確である.一方 CUDA でも GPU による並列
処理は global 関数および device 関数として CPU 上で実行される関数とは明確
に区別して記述される.プログラム全体の中から並列化による高速化を行いやすい
部分のみを選択的に並列実行するという考え方は CUDA と OpenMP で共通してい
るため,並列実行部を GPU 上で,逐次実行部を CPU 上で実行するという対応付け
は,アプリケーションプログラマにも理解しやすく記述しやすいと考えられる.
一方で,既存の OpenMP では逐次実行部と並列実行部とで同じメモリ空間を共有
するためデータを送受信する必要はないが,CUDA では CPU と GPU は互いに独立
したメモリを持つため,逐次実行部と並列実行部とで使用するデータを送受信する
必要がある.ただし,OpenMP の実行モデルでは逐次実行部と並列実行部が同時に
実行されることはないため,逐次処理部分と並列処理部分の境界で必要なデータを
全て送受信すれば正しい実行結果が得られると考えられる (図 40-3).複雑なポイン
タ参照を含むプログラムの場合は必要なデータを全て送受信すること自体が容易で
はないが,これは既存の OpenMP でも間接ポインタ参照を含むプログラムの場合に
データの依存関係の問題で並列高速化が行えないのと同様の問題であり,CUDA と
対応付ける場合にのみ問題となるわけではない.
CPU を搭載した計算機システムにおいて並列実行部をより高速に実行するには,
アプローチ 1 で行ったように並列実行部を CPU と GPU で分割し並列実行すること
が有効であると考えられる.しかし,CPU-GPU 間での適切なデータの送受信が必
要になるため,実装が難しくなることや逆に性能が低下してしまうことが予想され
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
94
図 40: OpenMP を用いた並列化プログラミングと CUDA との対応付け
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
95
る.また CPU と GPU による並列実行部の分割並列実行は難しいとしても,SPRAT
のように並列実行部を CPU で実行するか GPU で実行するかを選択する機構を実装
すれば,対象問題のデータ規模が小さい場合にも高速に実行できると考えられる.
通信ライブラリを用いたマルチプロセスプログラミング
MPI は複数のプロセスが並列処理を行う際にプロセス間の通信を行うために利用
されている (図 41-1).そのため CUDA において GPU 上の並列処理に MPI を利用
するには,同時に異なる種類の演算を行う事ができない CUDA Thread 間の並列処
理ではなく,CUDA Block 間の並列処理,もしくは CPU と GPU での並列処理に対
応付けるべきであると考えられる.
MPI を GPU 上の CUDA Block 間での通信に割り当てるうえでは,CUDA Block
間の同期とメモリ割り当てが課題となる.
MPI の最も基本的な処理としてプロセス間の同期通信やバリア処理が考えられる
が,CUDA には CUDA Block 間での同期をとる機構が提供されていない.しかし,
atomic 関数があるため CUDA Block 間で同期をとることは可能であり,同期通信や
バリア処理を行うことは不可能ではない.
メモリ割り当てについては,MPI ではプロセス毎のローカル変数やノード毎のロー
カルメモリを通信しながら並列処理を行う.これに対して CUDA では,CUDA Block
毎にプライベートなメモリとして SharedMemory があるものの,その容量は CUDA
Block あたり 16KB と小さいため CPU 向けの MPI におけるプロセス毎のローカル変
数のように使うと実行可能な問題の規模に厳しい制限がかかることになる.そのた
め,容量を超えて GlobalMemory に配置されることを前提で Register にデータを配
置するか,GlobalMemory を分割して利用するなどの方法によって MPI に対応した
動作が可能となると考えられる.しかしながらこの場合は,アプリケーションプログ
ラマにとっては CUDA Thread レベルの並列化や SharedMemory と GobalMemory
の使い分けなどを意識して記述する必要が生じるため,習得や実装の手間が増加し
てしまうことが問題となる.
さらに,CUDA では物理的な CUDA Block 数を超える並列度の並列処理でも十分
に高い性能を得ることができる.そのため GPU 上に比較的大容量の共有メモリを
備えているものの,CPU 向けの MPI の用に各 CUDA Block が共有メモリをそれぞ
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
96
図 41: 通信ライブラリを用いたマルチプロセスプログラミングと CUDA との対応
付け
4.1 既存の CPU 向け並列化プログラミング環境を用いた GPGPU プログラミング
の提案
97
れ占有し,また通信用に共有メモリを確保してしまっては,CUDA Block 単位で利
用可能なメモリの容量がが小さくなり小規模な問題しか解けなくなってしまう (図
41-2).
そのため CPU 向けの MPI のように CUDA Block 間でデータの送受信を行うより
は,各 CUDA Block が CUDA Block 同士で通信関数を用いて通知を行いつつ共有
メモリを用いて並列処理を行う方が,メモリを有効活用できると考えられる.しか
しこれでは一般的な MPI のモデルとは異なるものとなってしまう.
一方,CPU と GPU での通信を MPI の通信関数のように記述し,CPU と GPU
による並列計算を行うことも考えられる.しかしながら CUDA の実行モデルでは,
CPU から GPU へデータを送信し,GPU 上で並列処理を行い,GPU から CPU へ
のデータ書き戻しを行うという一連の動作を実行単位としている.そのため,CPU
向けの MPI では独立した複数のプロセスが任意のタイミングで互いにデータの送受
信を行いながら並列処理を行うのに対して,CUDA では関数 (Grid) 実行の前後にし
か CPU-GPU 間のデータ送受信が行えないため,CPU 向けの MPI と CUDA を適切
に対応付けることは困難である (図 41-3).
まとめ
以上から,SIMD 化プログラミングは並列処理の粒度から主に CUDA Thread レ
ベルでの並列処理の記述に,MPI は同時に実行可能な処理やデータ通信タイミング
の制約から CUDA Block レベルでの並列処理の記述に,OpenMP は CUDA Thread
レベル・CUDA Block レベル・CPU と GPU での並列処理の記述のいずれにも対応
付けることができると考えられる.さらに,これらの各プログラミング環境を組み
合わせて利用することも考えられる.複数の CPU 向け並列化プログラミング環境を
組み合わせて用する場合は複数のプログラミング環境を使いこなす必要があるため
プログラミングが難しくなる可能性があるものの,既にそれぞれの手法を習得して
いるアプリケーションプログラマにとっては利用しやすい可能性がある.また,対
象アプリケーションに階層的な並列性があるなどアルゴリズムとの親和性が高い場
合には,複数の CPU 向け並列化プログラミング環境を組み合わせて利用すること
も有効であると考えられる.
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
4.2
98
OMPCUDA : CUDA 向け OpenMP の提案と実装
本節では前節に基づく具体的な実装として,CUDA 向けの OpenMP 処理系 “OM-
PCUDA” を提案し,設計と実装を行う.
アプリケーションプログラマに対して,GPU(CUDA) のアーキテクチャを隠蔽し容
易にプログラミング可能とするには CPU-GPU 間の通信や GPU の制御を隠蔽する必
要があり,また GPU 内部の演算器が持つ並列性を利用した性能向上を得るには GPU
内の並列性を記述する必要がある.これに対して前節での検討の結果,OpenMP を
用いることで CPU-GPU 間の通信や GPU の制御と GPU 内の並列性の両方を記述
できると考えられる.そこで,CUDA 向けの OpenMP 処理系 “OMPCUDA” を提案
する.以下本項では OMPCUDA の具体的な実装について述べる.
OpenMP を用いた典型的な並列プログラムは,C 向け OpenMP における “for” 指
示子および Fortran 向け OpenMP における “DO” 指示子を用いたループ並列プログ
ラムである.これは,OpenMP 向けのベンチマークプログラムとして広く用いられ
ている SPEComp2001[101] において半数以上のベンチマークプログラムで利用され
ている指示子が,“for” 指示子および “DO” 指示子,並列実行部で利用される各変
数をスレッド間で共有するか否かを指定する “shared” 指示子および “private” 指示
子,そして並列実行部を実行する際に並列実行の最後で全スレッドの持つ変数の総
和を求めるなどの処理に利用される “reduction” 指示子のみであることから明らか
である.
そこで OMPCUDA は,OpenMP を用いた典型的な並列プログラムであるループ
並列プログラムに対して,GPU の特徴である高い並列性を有効に活用し効果的に並
列化・高速実行できるようにすることを主眼に置いて実装した.
以下 OMPCUDA の実装について,OMPCUDA 全体の構成,OMPCUDA を構成
するプログラム変換機構の構成,実行時ライブラリの構成の順に述べる.
4.2.1
全体の構成
本項では OpenMP と CUDA の並列実行モデルおよびメモリモデルのより具体的
な対応付けを検討する.
前節で述べたように,既存の OpenMP は指示子によって指定された並列実行部
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
99
のみを複数のスレッドで並列実行し,それ以外の部分は逐次実行する.逐次実行部
と並列実行部では,主記憶上に確保した共有メモリをスレッド間で共有する.そこ
で OMPCUDA では,並列実行部のみを GPU で実行し,他の部分は CPU で実行す
ることとする.つまり,既存の OpenMP がスレッド単位で並列実行を行うのに対
して,OMPCUDA では CUDA Thread 単位で並列実行を行うこととなる.この際,
GlobalMemory を共有メモリと見なし,多数の CUDA Thread を用いて並列計算を
行う.CUDA を用いて高い性能を得るには SharedMemory を活用することが重要と
されているものの,OpenMP に適した高い並列性を持つ対象問題であれば並列実行
によりある程度高い性能を得られ,OMPCUDA の有用性が確認できるものと考え
られる.
以上に基づく OpenMP と OMPCUDA の実行モデルとメモリモデルの対応付けを
図 42 に示す.
OMPCUDA の実装は,既存の OpenMP 処理系 Omni OpenMP Compiler version
1.6[102] (以下 Omni) をベースに行った.これにより OpenMP 指示子の解釈など CPU
向けの OpenMP と共通の処理の再実装を避けており,プログラム変換機構および新
しい実行時ライブラリを実装することで OpenMP プログラムの並列実行部を CUDA
対応 GPU 上で実行可能としている.
Omni と OMPCUDA の関係および OMPCUDA の構成を図 43 に示す.
Omni が OpenMP 指示子の挿入されたソースコードから並列化された実行ファイ
ルを生成するための手順は以下の通りである.
1. OpenMP 指示子の挿入されたソースコードを入力として受け取り,各言語に
対応した Frontend によって OpenMP 指示子の入った中間コードへと変換する.
2. OpenMP 指示子の挿入された中間コードに対して,OpenMP モジュールを用
いて OpenMP 指示子の解釈を行い,Omni の実行時ライブラリ呼び出しを含
む中間コードを生成する.この際,OpenMP における並列実行部の指定はブ
ロック単位で行われるのに対して,Omni の中間コードにおける並列実行部は
関数として分離させられ,並列実行部関数をスレッドに割り当てる Omni の実
行時ライブラリ関数によって呼び出されるように書き換えられる.
3. 中間コードを C 言語プログラムに変換 (デコンパイル) し,バックエンドコンパ
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
図 42: OpenMP と OMPCUDA の実行モデルとの対応付け
100
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
図 43: Omni と OMPCUDA の関係および OMPCUDA の構成
101
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
102
イラを用いてコンパイルし,Omni の実行時ライブラリとリンクして実行ファ
イルを生成する.
このように,Omni によって分離させられた並列実行関数は,実行時ライブラリ
の並列実行開始関数によってスレッドに割り当てられて並列実行されることとなる.
一方で CUDA における GPU 上での並列処理も関数単位であり,CPU からの指示に
従い GPU 上の多数の演算器で同時に同じプログラムを実行する.ただし,演算の
前に CPU から GPU へ必要なデータを送信し,また演算の後には GPU から CPU へ
結果を送信する必要がある.
そこで OMPCUDA では,“Omni の並列実行開始関数呼び出し” を “CPU から GPU
へのデータ送信,GPU への演算実行開始指示,GPU から CPU へのデータ書き戻
し” の一連の処理に置き換えるプログラム変換機構を実装した.このプログラム変
換機構は,プログラムを調査し CPU-GPU 間で送受信する必要があるデータを自動
的に送受信する機能を持つ.ただし,ポインタを含む構造体など単純に送受信でき
ないデータを利用しているプログラムには対応していない.
OMPCUDA では,処理の対象を OpenMP 指示子の挿入されたソースコードでは
なく,Omni によって指示子の解釈が行われ実行時ライブラリの呼び出しに変換さ
れた中間コードとした.Omni の中間コードは Xcode と呼ばれる専用の中間表現に
よって記述されており,Omni に含まれる Exc Java tool kit によって解析・書き換
え・C 言語コードとの相互変換を行うことができる.OpenMP 指示子の解析や実行
時ライブラリへの変換を行う OpenMP モジュールも Exc Java tool kit の一部として
実装されている.OMPCUDA のプログラム変換機能もその機能の多くを Exc Java
tool kit の追加モジュールとして実装しているが,CPU 向けのコードと GPU 向けの
コードを別々にコンパイルするための処理や CPU-GPU 間のデータ転送に向けたプ
ログラム解析のために,元々の Omni に組み込まれている各種モジュール (Java の
クラス) に対する機能追加や変更も行っている.
CUDA 用実行時ライブラリは,Omni の実行時ライブラリが持つ機能を CUDA 向
けに再実装したものである.
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
4.2.2
103
プログラム変換機構の実装
OMPCUDA のプログラム変換機構が行う,実行時ライブラリの呼び出しを含む
Omni の中間表現を CUDA に対応したプログラムへと変換する手順を以下に示す.
この手順は図 44 と対応している.なお,Omni の中間コードは C 言語で記述された
プログラムと相互変換が可能であることから,図 44 では Omni の出力する中間コー
ドを C 言語で記述されたプログラムに置き換えたうえで,主要な部分以外を簡略化
して記述している.
1. 中間表現で書かれたプログラム全体から実行時ライブラリの並列実行開始関
1 .
数が呼び出されている部分を探し出す (図 44-°)
2. 並列実行部の内部で利用されている変数を確認し,関数内ローカルでない変
数,すなわち CPU-GPU 間で送受信を行う必要がある変数を特定する.また
Omni の並列実行開始関数は並列実行部で利用する呼び出し元のローカル変数
も引数として受け取る仕様のため,引数を確認して送受信を行う必要がある
2 .
ローカル変数を特定しておく (図 44-°)
3 .
3. 並列実行部を別ファイルに書き出し,元のソースコードから削除する (図 44-°)
並列実行部に関数呼び出しが存在する場合は,その関数内で利用している変数
についても同様に確認し,まとめて書き出す.ただし,並列実行部で呼ばれて
いる関数は逐次実行部からも呼び出される可能性があるため,元のソースコー
ドにも残したままとする.
以下,別ファイルに書き出したソースコードを GPU コード,残されたソース
コードを CPU コードと呼ぶことにする.GPU コードは並列実行部の数だけ
存在することとなる.
4. CPU コードについては既に述べた通り,Omni の並列実行開始関数呼び出し
を CPU-GPU 間のデータ送受信および GPU への演算実行開始指示に書き換え
る.これをバックエンドコンパイラでコンパイルし,CUDA の実行時ライブ
4 .
ラリとリンクして CPU 用の実行ファイルを生成する (図 44-°)
5. GPU コードには,CUDA の記法に従い関数や変数に指示子を付加する.さら
に,関数の引数を調整し,CPU-GPU 間で変数の送受信が行えるようにしたう
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
図 44: プログラム変換機構の処理手順
104
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
105
えで,CUDA コンパイラ (nvcc) を利用して CUDA 用の実行ファイルを生成す
5 .
る (図 44-°)
現在の実装では実行時に並列実行部の数だけ CUDA 用の実行ファイルが必要だ
が,これは CPU 用の実行ファイルと結合するなどの手段で不要とすることができる
と考えられる.また,現在の実装では並列実行部で参照するデータは全て送受信の
対象としている.4.3 節の評価で示すように全てのデータを送受信することが直接致
命的な性能低下にはならないと考えられるが,GPU 上で変更されることのないデー
タは CPU へ書き戻さないようにするなど送受信する容量を削減することで性能が
さらに向上すると考えられる.いずれも今後 OMPCUDA をより実用的なツールと
していくうえでは解決する意味がある課題であるため,今後の発展課題とする.
4.2.3
実行時ライブラリの実装
Omni の実行時ライブラリは,スレッドの生成および割り当てやループのスケジュー
リング,スレッド間の同期処理,リダクション演算などの機能を提供している.
OMPCUDA の実行時ライブラリは,Omni において逐次実行部で行っている処
理は CPU で行い,並列実行部で行っている処理は GPU で行う,という方針で実装
した.
単純な for ループの並列化に最低限必要な関数として,GPU 上で実行される for
ループのスケジューリングを行う関数を実装した.さらに,for ループの並列化と
ともに利用されることの多いリダクション演算に必要な,GPU 上で実行されるリ
ダクション関数を実装した.Omni では CPU 上で実行されるスレッド割り当ておよ
び並列実行開始関数も提供しているが,これについてはプログラム変換機構による
CUDA 実行時ライブラリ関数の呼び出しへの書き換えが役割を果たしているため,
実行時ライブラリでは特に処理を行わない.
for ループのスケジューリング
Omni における for ループの並列化は,実行時ライブラリが提供する,各スレッド
が自らのスレッド ID を元に新たな部分ループを作成するための関数 (スケジューリ
ング関数) を用いて行われている.CUDA の実行時ライブラリにも一意の ID を得る
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
106
機能が備わっているため,OMPCUDA はこれを用いて Omni と同様に部分ループを
作成するための関数を提供することとした.
CUDA における並列実行は既存の CPU におけるスレッド実行と異なり,CUDA
Block と CUDA Thread の 2 階層によって構成されている.GPU は CPU からの並
列実行開始指示を受けると,多数の CUDA Thread が同時に演算を開始する.同一
CUDA Block 内の CUDA Thread は同時に異なる演算を行うことができず,また,
各 CUDA Block を構成する CUDA Thread の数は全 CUDA Block で同一である.し
かし各 CUDA Thread は固有の ID を持つため,この ID を用いて共有メモリ上の異
なるデータに対して同時に演算を行うことができる.
そのため CUDA における並列処理については,1CUDA Block 内の複数 CUDA
Thread を用いた並列処理,複数 CUDA Block を用いるが各 CUDA Block 内では
1CUDA Thread のみを利用する並列処理,複数 CUDA Block・複数 CUDA Thread
を用いた並列処理,以上の 3 種類の並列処理が考えられる.複数 CUDA Block・複
数 CUDA Thread を用いた並列処理が最も多くの演算を同時実行できるものの,同
一 CUDA Block 内の各 CUDA Thread は同時に異なる演算を行えないため,対象問
題によっては複数の CUDA Thread を用いても性能向上が得られない可能性がある.
これに対して,単純な for ループの並列化では各スレッドが同時に同じ演算を行
うことが多い.そのため for ループの並列化を CUDA に割り当てるうえでは,複数
の CUDA Thread による並列処理でも性能向上が可能であり,上記 3 種類の並列処
理のいずれにも対応付けることができると考えられる.
Omni はループ並列化におけるスケジューリング方法を複数提供しておりアプリ
ケーションプログラマが選択することができる.OMPCUDA では最も単純なスケ
ジューリングである,ループのイタレーションを等分割したスタティックスケジュー
リングのみを提供し,他のスケジューリング方法については検討を行うのみとする.
現在提供している OMPCUDA における for ループのスケジューリング (割り当て)
例を図 45 に示す.
CUDA 向けにおける最適な CUDA Block 使用数・CUDA Thread 使用数は,対
象プログラムの並列性や対象プログラム内の命令の構成,対象 GPU の性能 (主に
搭載している SM の数) により左右される.現在は CUDA Thread 使用数のデフォ
ルト値として (CUDA Thread 使用数については 1CUDA Block あたり 256 程度の
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
図 45: OMPCUDA における for ループのスケジューリング例
107
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
108
CUDA Thread を利用するべきであるという最適化指標が示されているため) 256 を,
CUDA Block 使用数については for ループの並列度を CUDA Thread で割った値 (た
だし CUDA の仕様に定められている利用可能な CUDA Block 数の上限を超えない
ように調整する) としている.
なお Omni の実行時ライブラリは環境変数や実行時の関数呼び出しにより利用す
るスレッドの数を変更することが可能となっている.OMPCUDA も最適な CUDA
Block 使用数・CUDA Thread 使用数は対象問題に依存することから,実行時に関数
や環境変数を用いて CUDA Block 使用数・CUDA Thread 使用数を変更できるよう
にした.
ただし,一般的に既存の OpenMP においてスレッド数として指定する意味がある
のは実行環境に存在する CPU(コア) 数程度の値であるのに対して,CUDA において
最も高い性能が得られる CUDA Block 数・CUDA Thread 数は数百から数千である.
そのためアプリケーションプログラマが自ら CUDA Block 数・CUDA Thread 数を指
定する場合は,CUDA における適切な並列度の指定に関する知識がなくては適切な
値を指定できない.これはアプリケーションプログラマに対して実行環境に関する知
識を習得する手間を削減するという本アプローチの趣旨に反している.OMPCUDA
が自動的に常に適切な CUDA Block 数・CUDA Thread 数を求められるようにする
ためにも,今後より多くの GPU 環境や対象プログラムに対して適用実験を行う必
要がある.
なお,Omni が提供している for ループのスケジューリング方法の例としては,以下
のものが挙げられる.いずれも並列実行部において各スレッドが実行するスケジュー
リング関数として実装されている.
1. 指定されたチャンクサイズを単位としたスタティックなラウンドロビンスケ
ジューリング
2. 指定サイズのチャンクサイズを単位としたダイナミックスケジューリング
3. 指定されたチャンクサイズを最初の割り当て単位とした Guided Self Scheduling
OMPCUDA でもこれらの各スケジューリングアルゴリズムを実装することは可
能であると考えられる.しかしダイナミックなスケジューリングを行う場合には,
チャンクの再割り当てを行う際に多重割り当て等が起きないよう CUDA Block 内の
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
109
CUDA Thread 同士または CUDA Block 間の CUDA Thread 同士の待ち合わせや排
他制御が必要となる可能性がある.OMPCUDA では GPU 全体で合計数千の CUDA
Thread を同時に実行することが予想されるため,待ち合わせにより性能が低下する
可能性のあるダイナミックスケジューリングよりもスタティックスケジューリング
の方が適していると考え,今回の実装を選択した.
リダクション演算
“for” 指示子や “DO” 指示子といったループ並列化指示子とともに多くの OpenMP
プログラムで利用されている指示子に “reduction” 指示子がある.“reduction” 指示
子は並列実行部を実行する際に並列実行の最後で全スレッドの持つ変数を足し込ん
だり,全スレッドの持つ同名の変数の中で最も大きな値のみを並列実行部が終了し
た後も残したりするために利用される指示子である.Omni では “reduction” 指示
子を実行時ライブラリのリダクション関数として実装している.OMPCUDA では
“reduction” 指示子を用いた処理の中でも最も典型的な処理である “全スレッドの持
つ同名な変数の総和を求める処理” を実行時ライブラリ関数として実装した.以下
この “全スレッドの持つ同名な変数の総和を求める処理” を単にリダクション演算と
呼ぶことにする.
GPU や CUDA を用いたリダクション演算については,既にいくつかの実装 [103,
104] が知られている.OMPCUDA では Owens らの手法 [105] をベースに SharedMemory を用いた並列リダクション関数を実装して利用することにした.ただし Owens
らの手法は CUDA Block 内のリダクション演算のみを扱っている.CUDA Block 内
のリダクション演算は SharedMemory を用いることで高速に行うことができる一方,
問題全体,すなわち CUDA Block 間でのリダクション演算については,atomic 演算
を用いた CUDA Block 間での排他制御や CUDA Block 間での待ち合わせを行いな
がら GlobalMemory に対して処理を行う必要があるため実行時間が長くなる可能性
がある.むしろ CUDA Block 単位でリダクション演算を行った結果を CPU に返し,
CPU 上で最終的なリダクション演算を行った方が良い性能が得られることが考えら
れる.
OMPCUDA では CUDA Block 毎にリダクション演算を行った後,各 CUDA Block
内の 1CUDA Thread が atomic 演算によって最終的なリダクションを行うという実
装を行った.そのため利用する CUDA Block 数が増えると CUDA Block 間のリダク
4.2 OMPCUDA : CUDA 向け OpenMP の提案と実装
110
ション時間が増大し,性能に悪影響を及ぼすと考えられる.この影響については次
節の性能評価で確認する.
OMPCUDA の実行モデルでは,OpenMP プログラムの共有メモリに対応する
CUDA の共有メモリとしては GlobalMemory のみを利用しているが,リダクショ
ン演算では SharedMemory を利用している.このように実行時ライブラリ関数の中
で SharedMemory を用いることで,アプリケーションプログラマには SharedMem-
ory を意識させずに SharedMemory を活用した高速化が行えると考えられる.例え
ば OMPCUDA の発展的な実装の案として,ループ並列部の内部にさらなる並列性が
見られる場合はループの並列化を GlobalMemory を用いた CUDA Block レベルでの
並列処理に対応付けたうえでループ内部の並列性を SharedMemory を用いた CUDA
Thread レベルでの並列処理に対応付けることなどが考えられる.
4.3 OMPCUDA の評価
4.3
111
OMPCUDA の評価
本節では OMPCUDA について,並列実行の効果が得られるかの性能確認と並列
プログラムが容易に作成できるかの評価を行う.
実験対象プログラムとしては,OpenMP による並列化に適した理想的な並列性を
持つプログラムが OMPCUDA によって容易に並列高速化できることを確認するた
め,並列化が容易な問題である行列積と円周率の求解 (グレゴリ級数) を用いる.各
評価においては,CPU を用いた場合や,OMPCUDA を用いずに直接 CUDA を用い
た場合との性能や記述の容易性の比較を行う.また円周率の求解ではリダクション
演算を利用しているため,リダクション演算の実装についての評価も行う.
評価環境は表 3 に示す通りである.
表 3: 評価環境 2
CPU
Xeon E5345 2.33GHz (4 コア)
メインメモリ
4.0GB (32bitOS につき 3.2GB 使用可)
GPU
GeForce GTX 280
(コアクロック 602MHz, SP クロック 1296MHz)
ビデオメモリ
1.0GB
GPU 接続バス
PCI-Express x16 (Gen 2)
OS
CentOS 5.0 (kernel 2.6.18)
コンパイラ
GCC 3.4.6
Omni OpenMP Compiler version 1.6
nvcc 2.0 v0.2.1221
以下,行列積を用いた性能確認,円周率の求解を用いた性能確認,実装の手間や
記述の容易性に関する評価という順番で OMPCUDA の評価について述べる.
4.3.1
行列積を用いた性能確認
アプローチ 1 で述べた通り,行列積はデータ量に対して計算量が多く並列性が高
い問題であり,GPU を用いて高速実行できる問題としても知られている.本アプ
4.3 OMPCUDA の評価
112
ローチでは最大性能を得ることよりも単純な実装で容易に性能を得られることを重
視しているため,単純なループ処理による実装を用いて性能の比較を行った.
本評価における行列積は全て単精度浮動小数の転置なし正方行列に対する行列積
とし,行列の一辺の長さを問題サイズと呼ぶことにする.
評価では以下の実装についての性能比較を行った.
1. OMPCUDA-loop3 : OMPCUDA を用いた,単純な 3 重ループによる行列積の
実装 (図 46)
2. OMPCUDA-loop2 : OMPCUDA を用いた,loop3 における外側の 2 ループを
併合して 2 重ループとした実装 (図 47)
3. SimpleCUDA : SharedMemory は用いずに各 CUDA Thread が行列の各要素を
担当する,CUDA を用いた実装 (ソースコード概要を付録 1 に載せる)
4. UseSharedCUDA : CUDA のサンプルとして提供されている SharedMemory を
用いた実装 (CUDA SDK 2.0 付属のサンプル MatrixMul を利用)
5. OmniCPU-loop3 : Omni を用いたループ並列化 (図 46 を Omni でコンパイル
したもの,CPU 上で実行,1 スレッドから 8 スレッド)
6. OmniCPU-loop2 : Omni を用いたループ並列化 (図 47 を Omni でコンパイル
したもの,CPU 上で実行,1 スレッドから 8 スレッド)
7. AtlasCPU-nothread, AtlasCPU-pthread : ATLAS を用いたもの (非スレッド
対応版の AtlasCPU-nothread とスレッド対応版の AtlasCPU-pthread,いずれ
も CPU 上で実行)
図 48 は,問題サイズ 1024 の行列積に対して,CUDA Thread 数を OMPCUDA の
デフォルト値である 256 とした際の各実装の実行時間を示したグラフである.なお
CUDA を用いた場合 (CUDA-loop3, CUDA-loop2, SimpleCUDA, UseSharedCUDA)
の実行時間には CUDA を初期化するための時間は含まれておらず,CPU-GPU 間で
のデータ通信時間は含まれている.CUDA の初期化には平均 900msec 程度,OM-
PCUDA の初期化 (CUDA の初期化を含む) の初期化には 1600msec 程度の時間が必
要であることが確認できている.
4.3 OMPCUDA の評価
#define N 1024
f l o a t a [N∗N] , b [N∗N] , c [N∗N ] ;
#pragma omp p a r a l l e l for p r i v a t e ( j , k )
f or ( i =0; i <N; i ++){
f o r ( j =0; j <N; j ++){
f l o a t tmp = 0 . 0 f ;
fo r ( k=0; k<N; k++){
tmp += a [ i ∗N+k ] ∗ b [ k∗N+j ] ;
}
c [ i ∗N+j ] = tmp ;
}
}
図 46: 行列積のソースコード 1 (3 重ループ)
#define N 1024
f l o a t a [N∗N] , b [N∗N] , c [N∗N ] ;
#pragma omp p a r a l l e l for p r i v a t e ( j )
f or ( i =0; i <N∗N; i ++){
f l o a t tmp = 0 . 0 f ;
f o r ( j =0; j <N; j ++){
tmp += a [ ( i /N) ∗N+j ] ∗ b [ j ∗N+( i%N ) ] ;
}
c [ i ] = tmp ;
}
図 47: 行列積のソースコード 2 (2 重ループ)
113
4.3 OMPCUDA の評価
図 48: 行列積の実行時間 1 (問題サイズ 1024)
114
4.3 OMPCUDA の評価
115
結果を見ると,OMPCUDA は OMPCUDA-loop3 と OMPCUDA-loop2 で大きく
性能が異なっている.これは 3 重ループ (OMPCUDA-loop3) の場合には並列度が外側
ループのループ回数である 1024 であり,CUDA Thread 数が 256 のため CUDA Block
数が 1024/256=4 という低い並列度で実行されたのに対して,loop2 では並列度が
1024*1024,CUDA Thread 数が 256 のため CUDA Block 数は 1024*1024/256=4096
となり,高い並列度で実行されたことにより性能が向上したものと考えられる.ま
た OmniCPU の実行時間を見ると,OmniCPU では CPU のコア数を超える数のス
レッドを利用しても性能が向上しないのに対して,CUDA では物理的な演算器の数
が適切な並列度に直接対応していないことが確認できる.
さらに CUDA-loop2 について,問題サイズを 1024 に保った状態で CUDA Thread
数と CUDA Block 数をいくつか変化させた際の実行時間を図 49 に示す.結果を見
ると,CUDA Thread 数は 256 または 512 のときに実行時間が短く,CUDA Block
数は多いほど良い性能が得られている.CUDA Block 単位での共有メモリである
SharedMemory を用いていないため,並列度が性能を大きく左右するパラメタとなっ
ていることがわかる.
以上の結果から,OMPCUDA は GPU の持つ高い並列性を活用したプログラムの
高速化を行えたと言える.
4.3.2
円周率の計算 (グレゴリ級数) を用いた性能確認
グレゴリ級数を用いた円周率の計算は,計算に必要なデータ量が少なく最後にリ
ダクション演算が必要な以外は理想的な並列性を持つ,並列化による高速化が容易
な問題である.評価に用いたプログラムのソースコードを図 50 に示す.OMPCUDA
のデフォルト設定では CUDA Thread 数を 256,CUDA Block 数を可能な限り大き
くとることにしてあるため,この for ループは 1024*1024=1048576 個という非常に
多くの CUDA Block によって並列処理されることとなる.そのためリダクション演
算の実行時間が全体の実行時間に影響を及ぼす可能性があると考えられる.
評価では以下の実装についての性能比較を行った.
1. OMPCUDA : OMPCUDA を用いた実装 (図 50)
2. SimpleCUDA : OMPCUDA を用いず CUDA を直接利用した実装
4.3 OMPCUDA の評価
図 49: 行列積の実行時間 2 (問題サイズ 1024)
f l o a t answer = 0 . 0 f ;
int i , n = 0 x10000000 ; // 256∗1024∗1024=268435456=0 x10000000
#pragma omp p a r a l l e l for r e d u c t i o n (+: answer )
f or ( i = 0 ; i < n ; i ++){
answer += ( 4 . 0 / ( 4 ∗ i + 1 ) − 4 . 0 / ( 4 ∗ i + 3 ) ) ;
}
図 50: 円周率計算のソースコード
116
4.3 OMPCUDA の評価
117
3. OmniCPU : Omni を用いたループ並列化 (図 50 を Omni でコンパイルしたも
の,CPU 上で実行,1 スレッドから 8 スレッド)
4. CUDA-CPUreduction : SimpleCUDA に対して,リダクション演算の一部 (CUDA
Block 間のリダクション演算) を CPU 側に移動した実装
5. CUDA-GLOBALreduction : SimpleCUDA に対して,全てのリダクション演
算を atomic 演算で行うようにした実装
評価 2 では評価 1 と異なり for ループ内部の計算において各 CUDA Thread が共通
に参照するデータはないため,SharedMemory を用いた実装との比較は意味をなさ
ない.一方,前節で述べたようにリダクション演算が性能に影響を与える可能性が
ある.特にデフォルトの CUDA Block 数・CUDA Thread 数では for ループのイタ
レーション数が多いほど CUDA Block 数が多くなりリダクション演算が実行時間に
与える影響が大きくなると考えられる.そこで,SimpleCUDA のプログラムを書き
換え,CUDA Block 間のリダクション演算を CPU 側に移動したプログラム (CUDA-
CPUreduction) と全てのリダクション演算を単純に atomic な加算命令で構成したプ
ログラム (CUDA-GLOBALreduction) を作成し,性能を比較することにした.
各実装の実行時間を図 51 に示す.前項の行列積と同様,CUDA を用いた実装に
ついては初期化の時間を含んでいない.
グレゴリ級数は理想的な並列性を持つため,Omni ではスレッド数を 2,4 と増や
すことで実行時間が 1/2,1/4 と短縮されており,同時実行可能なスレッド数を超え
ると性能が頭打ちになっている.一方 OMPCUDA では,CPU と比べてコアクロッ
クが低いにも関わらず実行時間が短くなっており,多数の演算器による並列処理の
効果が得られていることが見て取れる.OMPCUDA と SimpleCUDA を比較すると,
この実験では OMPCUDA の生成するプログラムと SimpleCUDA の生成するプログ
ラムは for ループの書き換えと OMPCUDA の初期化以外はほぼ同等のプログラム
であり,実行時間の差として現れるのはループの書き換えによる時間のみである.
OMPCUDA のスケジューリングは単純なスタティックスケジューリングであり複雑
な計算は行っていないため,実行時間に有意な差は見られなかった.
一方でリダクションの方法を変更した CUDA-CPUreduction では実行時間が 40%近
く短くなり,CUDA-GLOBALreduction は 100 倍以上長い実行時間となった.CUDA-
4.3 OMPCUDA の評価
図 51: 円周率の求解の実行時間 1 (問題サイズ 0x10000000)
118
4.3 OMPCUDA の評価
119
CPUreduction の実行時間内訳を確認したところ,CPU 上でのリダクション演算は
数ミリ秒で終了していることがわかった.OMPCUDA と比べて GPU から CPU へ転
送されるデータ量が増加してはいるものの,増加した容量はたかだか CUDA Block
数 (1024*1024) * float 変数の容量 (32bit) = 1MB であり,CPU-GPU 間の転送速度
が実測値 1GB/sec を超える今回の実験環境では実行時間に大きな影響を及ぼすと
は考えにくい.そのため,CUDA-CPUreduction は GPU 上の CUDA Block 間での
リダクションにかかる時間を大きく削減できたため実行時間が短く,また CUDA-
GLOBALreduction では逆に GPU 上の CUDA Block 間でのリダクション時間が大
きくなったためにこのような結果が得られたと考えられる.
ここで,OMPCUDA と CUDA-CPUreduction について CUDA Block 数と CUDA
Thread 数を変更した場合の性能を図 52 に示す.OMPCUDA,CUDA-CPUreduction
ともに CUDA Block 数・CUDA Thread 数が一定の範囲であれば性能に大きな差はな
く,また行列積では OMPCUDA のデフォルト設定であるできる限り多くの CUDA
Block・CUDA Thread を利用する割り当てが高い性能を得ていたのに対して,今回
の性能評価では CUDA Block 数を増やした場合に性能低下が見られている.この原
因として,CUDA が効率よくタスクスイッチ可能な CUDA Block 数を超えているこ
とが考えられる.
図 53 は,OMPCUDA の実行時間を 1 とした場合の CUDA-CPUreduction の実行
時間比である.CUDA Block 数が少ない場合は実行時間にほとんど差がないものの,
CUDA Block 数が多い場合には大きな実行時間の差が生じている.CUDA Block 数
が多く CUDA Thread 数が少ない場合に実行時間の差が生じていないように見える
のは,計算時間が非常に長くリダクション演算の実行時間が表面化していないため
である.なお,1CUDA Block あたりの CUDA Thread 数と CUDA Block 数の両方
が大きな場合の点がいくつか足りていないのは,CUDA Block 数*CUDA Thread 数
が問題サイズを超えており評価が意味をなさないためである.
以上から,対象問題の計算量やリダクション対象のデータ量によってはリダクショ
ン演算を全て GPU 上で行うか一部を CPU で行うかによって性能に差が生じると考
えられる.ただし今回の問題設定では,OMPCUDA・CUDA-CPUreduction ともに
CUDA Thread 数 256,CUDA Block 数 16384 の時に最も実行時間が短くなり,所要
時間はともに 285.5msec であった.
4.3 OMPCUDA の評価
図 52: 円周率の求解の実行時間 2 (問題サイズ 0x10000000)
120
4.3 OMPCUDA の評価
図 53: 円周率の求解の実行時間 3 (問題サイズ 0x10000000)
121
4.3 OMPCUDA の評価
122
今回の問題設定では,OMPCUDA デフォルトの CUDA Block 数・CUDA Thread
数設定よりも高い性能を得ることができる CUDA Block 数・CUDA Thread 数の設
定が存在した.常に最も高い性能を得られるようにするためには,デフォルトでよ
り適した CUDA Block 数・CUDA Thread 数が選ばれるような仕組みが必要である.
しかしながら評価 1 と同様に,OMPCUDA を用いることで GPU の持つ高い並列演
算性能を活用できることが確認できたと言える.
4.3.3
実装の手間や記述の容易性に関する評価
本項では行列積と円周率の求解の各プログラムについて,実装の手間や記述の容
易性についての定量的な評価を行う.
行列積を用いた性能評価で実装した各プログラムについて,プログラムの行数と
GPU に関する知識の必要性および実行時間を表 4 に示す.
表 4: 行列積のプログラム行数と GPU に関する知識の必要性
実装
CPU 向け
GPU 向け
GPU に関する
プログラム
プログラム
知識の
実行時間
の行数
の行数
必要性
(msec)
OMPCUDA-loop3
13
不要
800
OMPCUDA-loop2
11
不要
110
SimpleCUDA
80 行程度
5
要
90
UseSharedCUDA
80 行程度
20
要
24
OmniCPU-loop3 4
13
-
-
7000
OmniCPU-loop2 4
11
-
-
6900
AtlasCPU-nothread 1
-
-
190
AtlasCPU-pthread
-
-
60
1
今回の実験において CUDA 向けの実装で最も高い性能が得られたのは Shared-
Memory を用いた実装 UseSharedCUDA である.この実装はスレッド並列版の ATLAS (AtlasCPU-pthread) と比較しても実行時間が半分であり高い性能を得られてい
4.3 OMPCUDA の評価
123
る.一方で UseSharedCUDA プログラムの記述量を見てみると,GPU の制御に 80 行
程度および GPU 上で行う計算の記述に 20 行程度必要であり,さらに SharedMemory
を用いた複数 CUDA Block・複数 CUDA Thread を用いる CUDA プログラミング手
法の習得が必要であるため,単純な 3 重ループ・2 重ループによる実装と比べると
明らかに実装の手間が大きいことがわかる.
また同じく CUDA 向けだが SharedMemory を用いていない実装である Simple-
CUDA と比較した場合,実行時間の面では OMPCUDA-loop2 が SimpleCUDA に
近い性能を得られている.OMPCUDA-loop2 と SimpleCUDA の実行時間の差は,
OMPCUDA-loop2 が並列実行部で利用するデータを全て送受信しているのに対して
SimpleCUDA では必要なデータのみを送受信していることと,OMPCUDA-loop2 で
は並列実行部にループの書き換えのための計算が追加されていることによるもので
ある.SimpleCUDA におけるプログラムの記述量については,GPU 上で行う計算
の記述は短い 1 重ループで記述できるものの,GPU の制御には UseSharedCUDA と
同様に 80 行程度必要であり,さらに複数 CUDA Block・複数 CUDA Thread を用い
る CUDA プログラミング手法の習得が必要である.
ATLAS を用いた実装は対象演算が関数として提供されているため,アプリケー
ションプログラマが記述するソースコードの行数を比較する意味がない.ATLAS
自体は高度な職人芸によって作られており,一般のアプリケーションプログラマが
ATLAS レベルの性能を持つプログラムを記述することは非常に困難である.
既存の CPU 向け OpenMP における適切な並列度はプログラムを実行する計算機
システムに搭載されている CPU の数 (コア数) によって決まる.一方 CUDA は CPU
と比べて適切な並列度が大きいため,OMPCUDA では 3 重ループの OMPCUDA-
loop3 と比べて 2 重ループの OMPCUDA-loop2 の方が明らかに性能が高かった.こ
れは OMPCUDA を用いて GPU の性能を活用し高い性能を得るには,既存の CPU
向け OpenMP を用いる場合と比べてさらに並列性を得やすいようなプログラム記
述を行う必要があること,例えばこの実験で 3 重ループを 2 重ループに変更したよ
うに,より高い並列度が得られるようなプログラム記述を行う必要があることを意
味する.この性能最適化指標は “並列度が高い記述を行った方が性能が出やすい” と
いった単純な情報に変換できるため,大きな手間とはならないと考えられる.
行列積と同様に,円周率の求解を用いた性能評価で実装した各プログラムについ
4.3 OMPCUDA の評価
124
ても,プログラムの行数と GPU に関する知識の必要性および実行時間を表 5 に示す.
表 5: 円周率求解のプログラム行数と GPU に関する知識の必要性
実装
CPU 向け
GPU 向け
GPU に関する
プログラム
プログラム
知識の
実行時間
の行数
の行数
必要性
(msec)
不要
624
OMPCUDA
6
SimpleCUDA
80 行程度
5 + 60 †
要
620
OmniCPU 4
6
-
-
2100
6
不要
375
GLOBALreduction 6
不要
130000
CUDACPUreduction
CUDA-
† 計算コアは 5 行だが,リダクション演算に 60 行程度必要.
今回用いた円周率の求解プログラムは極めて単純かつ高い並列性を持つな問題で
あるため,リダクション演算以外に共有メモリを用いた並列高速化を行うべき場所
がない.そのため CUDA を直接用いた場合でも GPU の行う処理の記述は短いもの
の,GPU を制御するための記述量は評価 1 と同様に 80 行程度必要であり,さらに
複数 CUDA Block・複数 CUDA Thread を用いる CUDA プログラミング手法の習得
も必要である.
以上から,行列積と円周率の求解のいずれの問題においても OMPCUDA を用い
ることで,アーキテクチャを理解しなくてはならないうえに記述量が多く手間がか
かる CUDA プログラミングを行うことなく,容易に高い性能が得られていることが
わかる.そのため,OMPCUDA はアプリケーションプログラマに対する習得や実装
の手間と難しさを削減しつつ GPU の持つ高い演算性能を利用可能にしたと言える.
125
結論
5
5.1
研究成果の概要
本研究では,GPU の性能向上と普及が進むにともない GPU の性能を画像処理以
外の処理を含めた様々な用途に活用する GPGPU の普及が進み始めている一方で,
さらに GPGPU が普及し広く活用されるには,アプリケーションプログラマにとっ
ての習得や利用の手間と難しさが問題となっていることを指摘した.問題の原因と
しては,GPU のアーキテクチャが既存の CPU とは大きく異なること,さらに既存
の GPGPU プログラミング環境は GPU のアーキテクチャと強く結びついているた
め,GPGPU プログラミングのためには GPU のアーキテクチャや GPGPU 用のプ
ログラミング環境について学習しまた手間のかかる GPGPU プログラムの実装を行
う必要があることを挙げた.
指摘した問題に対して本研究では,GPU が並列処理による高い演算性能を持つ
ハードウェアであることから,現在 CPU 向けの並列化プログラミングに利用され
ている汎用プログラミング環境が GPGPU プログラミングにも利用できればアプリ
ケーションプログラマが GPGPU を容易に利用できると考えた.そこで,“並列計
算ライブラリ” と “並列化プログラミング環境” の 2 つのアプローチにより,アプリ
ケーションプログラマに対して GPGPU を容易に利用可能とする機構の提案と実装
を行った.
アプローチ 1 : 並列計算ライブラリ
第 1 のアプローチである “並列計算ライブラリ” では,計算カーネルのライブラリ
化はアプリケーションプログラマに対して詳細な実装方法や実行環境の差異を隠蔽
するのに効果があるものの,GPGPU においては GPU 上での実行に適さない問題
設定に関する課題や CPU-GPU 間での負荷分散に関する課題があるため,GPU を
用いた計算カーネルの実装を単純にライブラリとしてまとめただけでは高い性能が
得られない可能性があるという問題を指摘した.
この問題に対して本アプローチでは,“CPU 向けのライブラリが持つ API と同様
の API を持ち,対象問題のデータ規模が小さい場合には CPU のみで演算を行い,
5.1 研究成果の概要
126
データ規模が大きい場合には CPU と GPU の性能バランスにあわせて CPU と GPU
で問題分割・並列実行する機構を持つライブラリ” を提案した.また,提案に基づく
ライブラリについてグラフィックス API とシェーダ言語を用いた実装を検討し,検
討に基づくライブラリの実装を行った.
実装の検討においては,CPU と GPU を用いて並列処理を行うための基本的な実
装方法を示した.OpenGL とマルチスレッドプログラミングを用いた実装における
性能低下の問題とその対策についても述べた.また CPU と GPU による適切な問題
分割を行うには実行環境に依存する性能チューニングが必要だが性能チューニング
はアプリケーションプログラマにとって大きな手間となること,チューニングスク
リプトと問題分割機構を実装・提供しチューニングを行う必要をなくすことでアプ
リケーションプログラマの手間が削減できることを指摘した.さらに発展的な計算
機システム向けの検討として,複数の CPU や複数の GPU を搭載した計算機システ
ム向けの実装についても検討を行った.
アプローチに基づき,行列積和計算を対象としたライブラリ “GPUPC GEMM
Library” を実装した.GPUPC GEMM Library は,実行環境に搭載されている CPU
と GPU 両方の演算性能を活用して行列積和計算を行うライブラリである.対象問題
のデータ規模が小さい場合には CPU のみで演算を行い,問題サイズが大きく GPU
による性能向上が望める場合にのみ CPU と GPU による問題分割・並列実行を行う
ことで,CPU 向けのライブラリと同様の API を持ちながら GPU による性能向上を
得ることができる.さらに実行環境に依存する性能パラメタについては,自動的に
適切な値を求めることが可能なチューニングスクリプトと,スクリプトによって求
められた値を用いて問題分割・並列実行を行う問題分割機構を実装し,手間をかけ
ずに常に高い性能が得られるようにした.
また,テストプログラムやベンチマークプログラムを用いてプログラム作成の手
間と性能に関する評価を行った.性能については,HPL ベンチマークに対して CPU
のみで HPL を実行したときに比べて最大 45.0% の性能向上を達成したことで本提
案が演算性能の面で有効性を持つことを確認した.また本ライブラリを利用するア
プリケーションプログラマにとって,プログラムの変更を行うことなく GPU の持
つ高い並列演算性能を利用できることと,チューニングスクリプトと問題分割機構
によって実行対象である計算機システムに搭載されている CPU と GPU の性能バラ
5.1 研究成果の概要
127
ンスを気にすることなく GPU の持つ高い並列演算性能を利用できることから,本
提案がプログラム作成の手間の面で有効性を持つことを確認した.
以上から,“CPU 向けのライブラリと同様の API を持ち,対象問題のデータ規模
が小さい場合には CPU のみで演算を行い,データ規模が大きい場合には CPU と
GPU の性能バランスにあわせて CPU と GPU で問題分割・並列実行する機構を持
つライブラリ” を提供することで,アプリケーションプログラマに対して GPU が持
つ演算性能の活用と利用の手間の削減の両方を達成できたことを示した.
本アプローチの発展的な課題としては以下の 2 点が挙げられる.
1. 様々なアプリケーションへの適用実験
本アプローチでは対象問題として行列積和計算のみを扱った.ライブラリの設
計においては行列積和計算やデータ並列アプリケーションに限定されない基礎
的な実装方法を示したものの,行列積和計算は CPU と GPU の性能バランス
にあわせて容易に問題分割が行え性能が得やすい問題である.構造がより複雑
な対象問題では,CPU と GPU の性能バランスにあわせて容易に問題分割を
行えないなど,適切な問題分割を行うことが難しい可能性がある.そのため,
行列積和計算とは異なる種類のアプリケーション,例えばデータ並列性ではな
く機能並列性を行う問題への適用や,反復計算が必要な問題への適用実験を行
う意義がある.
なおこの課題に対しては,本アプローチに関する論文発表の後に東京工業大学
において FFT に対して問題分割・並列実行が行われ成果が得られている [106].
この研究では対象問題である FFT を機能分割し並列実行することで高い性能
を得ている.そのため,本アプローチが行列積和計算だけではなく様々な種
類のアプリケーションにも適用できる可能性の一端は既に示されていると言
える.
2. 複数の CPU・複数の GPU を搭載した計算機システムを対象とした性能チュー
ニング
本アプローチにおける複数の CPU や複数の GPU に対応した実装では,CPU
の処理をマルチスレッド並列化に対応したライブラリに任せており,また CPU
と GPU の問題分割割合の最適化についても 1CPU+1GPU での性能に基づい
5.1 研究成果の概要
128
た単純な分割のみを行っている.本アプローチにおける評価では性能が同じコ
アを 2 個搭載した CPU と性能が同じ 2 枚の GPU という環境を用いたために
単純なチューニングで容易に高い性能を得ることができたが,CPU や GPU を
より多く搭載した計算機システムや,性能の異なるコアからなる CPU を搭載
した計算機システム,性能の異なる複数の GPU を搭載した計算機システムを
利用する場合には,並列処理のオーバヘッドを減らすために実装を工夫するこ
とや,より適切な問題分割割合を求めるために性能のモデル化およびモデル化
に基づくチューニングアルゴリズムの考案などが必要になると考えられる.
アプローチ 2 : 並列化プログラミング環境
第 2 のアプローチである “並列化プログラミング環境” では,GPU が並列処理に
よる高い演算性能を持つハードウェアであることおよび CPU 向けの並列化プログ
ラミングにおいてはいくつかの並列化プログラミング環境が普及し広く利用されて
いることから,“既存の CPU 向け並列化プログラミング環境を用いた GPGPU プロ
グラミング” を提案した.
本アプローチでは,既存の CPU 向け並列化プログラミング環境のいくつかを挙げ
て,典型的な GPU のハードウェア構成,特に演算器やメモリの構成との対応付けを
検討した.ここでは,GPU 内部の演算器を用いて SIMD 演算を行うことや,GPU
上の共有メモリと演算器を OpenMP に関連づけて利用すること,GPU 上の演算器
間での通信や CPU-GPU 間の通信を通信ライブラリを用いて記述することなどを検
討した.さらに,GPGPU 環境の 1 つである CUDA を対象として既存の CPU 向け
並列化プログラミング環境との対応付けを検討した.ここでは演算器やメモリの対
応付けのみならず,実行モデルの対応付けや,対応付けの結果としてある程度高い
性能が得られそうであるかなど,より具体的な検討を行った.
対応付けを検討した結果,CUDA と OpenMP との対応付けを行うことでプログ
ラミングの容易さと性能の両立が期待できると判断し,検討に基づいて CUDA 向け
の OpenMP 処理系 “OMPCUDA” を実装した.OMPCUDA は,既存の CPU 向け
OpenMP コンパイラである Omni OpenMP compiler を拡張して実装した “既存の
CPU 向け OpenMP を用いて記述されたプログラムの並列実行部を GPU (CUDA)
上で実行可能とする処理系” である.
5.1 研究成果の概要
129
OMPCUDA は “プログラム変換機構” と “実行時ライブラリ” によって構成され
る.プログラム変換機構は,Omni により OpenMP プラグマの解析および実行時ラ
イブラリ関数呼び出しへの置き換えが行われた後の中間コードを対象としてプログ
ラムの解析を行い,OpenMP プログラムの並列実行部を GPU 上で実行可能とする
ための機構である.実行時ライブラリは GPU 上でのプログラム実行やスケジュー
リングを行うための機構である.
OMPCUDA の実装においては,OpenMP と CUDA がともに並列実行部を明示的
に指定する構造であることから,OpenMP 指示子で指定された並列実行部のみを
GPU (CUDA) 上で実行可能にするという方針で実装した.プログラム変換機構は
並列実行部を GPU 上で実行できるようにプログラムを変換する際に,並列実行部
で参照するデータを確認し,自動的に送受信できるようにする機構を持つ.そのた
めアプリケーションプログラマは既存の OpenMP プログラムと同様の記述のみを用
いて CUDA プログラムを作成することができる.
さらに,テストプログラムを用いて OMPCUDA の性能と記述の容易性を評価し
た.その結果 OMPCUDA は,アプリケーションプログラマに対して GPU (CUDA)
に関する知識を必要としない GPGPU プログラミング環境を提供することが可能で
あること,さらに OpenMP による性能向上が期待される典型的な問題であるループ
の並列化に対して GPU の持つ高い並列性を活用した並列演算性能を得られること
を確認した.
以上から,“既存の CPU 向け並列化プログラミング環境と同様の記述を用いて記
述されたプログラム (の並列実行部) を GPU 上で実行可能とする処理系” を提供す
ることで,アプリケーションプログラマは GPU のアーキテクチャや GPU 用のプロ
グラミング環境を習得するという大きな手間をかけることなく容易に GPGPU プロ
グラミングを行えることおよび GPU の性能を容易に活用可能となることを示した.
本アプローチの発展的な課題としては以下の 2 点が挙げられる.
1. GPU 上のメモリの効率的な利用とループ並列化以外への対応
OMPCUDA を用いてより多くの OpenMP プログラムを GPU 上で容易にかつ
高速に実行可能とするためには,メモリ特性の利用やループ並列化以外への対
応などについてさらに検討・実装する必要がある.
5.1 研究成果の概要
130
CUDA の備えるメモリの特性を活用すればより高い性能を得られる可能性があ
る.現在の OMPCUDA の実装では CUDA の共有メモリとして GlobalMemory
のみを利用しているが,ShraedMemory や ConstantMemory などを利用可能
とすることでさらなる性能向上が行える可能性がある.例えば局所的に再利
用されるデータは SharedMemory に配置することや,書き込みが行われない
データはキャッシュ効果が得られる ConstantMemory や TextureMemory に配
置することにより,さらなる性能向上が期待できる.そのためにはプログラム
変換機構を改良し,プログラムをより詳しく解析し GPU 上の各メモリとの適
切な対応付けを行えるようにする必要がある.
また適切な対応付けを行うには CUDA プログラムの最適化に関する研究の成
果を取り入れることが重要であるが,CUDA は新しい GPGPU プログラミン
グ環境でありプログラムの最適化に関する知見が十分に蓄積されているとは言
い難い.そのため,今後も CUDA プログラムの最適化に関する研究の動向を
注視し,その成果を OMPCUDA に取り入れていくことが必要であると言える.
現在の OMPCUDA はループの並列化のみを対象として実装されている.ルー
プの並列化は OpenMP の典型的な対象問題であるため,ループの並列化のみ
が対象であっても利用可能なアプリケーションは多いと考えられるが,他の指
示子を用いた並列化への対応を行うことでさらに多くのアプリケーションを容
易にかつ高速に実行可能となると考えられる.例えば sections 指示子に対して
CUDA Block レベルでの並列性を割り当てることや,sections 指示子と for 指
示子による階層的な並列化に対しては sections 指示子を CUDA Block レベル
での並列性に割り当てた上で for 指示子を CUDA Thread レベルでの並列性に
割り当てるといった割り当てを行うことが考えられる.
2. 様々なアプリケーションへの適用実験
本アプローチの評価では単純なテストプログラムを対象とした評価のみを行っ
た.OMPCUDA が広く利用されるには,より様々なアプリケーションへの適
用実験を行い,性能評価や追加実装等を行う必要がある.
OpenMP はアプリケーションプログラマが適切な並列化指示子を挿入するこ
とを期待している.そのため実行タイミングによって正しい実行結果が得られ
5.1 研究成果の概要
131
るか否かが左右されるようなプログラムが入力された場合などは,アプリケー
ションプログラマは正しくない実行結果が得られるまで記述ミスに気がつか
ない.OMPCUDA を利用したプログラム実行においても,実行タイミングに
よって正しい実行結果が得られるか否かが左右されるプログラムを作成した場
合には同様の状況が発生することが考えられる.
しかし,GPU 上での実行と CPU 上での実行では異なるタイミングで実行さ
れる可能性が高いため,同じ OpenMP プログラムを入力した場合でも,既存
の OpenMP 処理系と OMPCUDA では異なる傾向の正しくない実行結果が得
られることや,CPU のみまたは GPU のみでは常に正しい実行結果が得られる
ことも考えられる.様々なアプリケーションに対して適用実験を行うことは,
こうした問題が起きやすいプログラム記述のパターンを把握したり防止した
りする上でも意味があると言える.
まとめ
第 1 のアプローチは,並列化された計算カーネルを提供することでアプリケーショ
ンプログラマに対して並列化プログラミング自体を隠蔽した.そのため,並列化に
関する知識を持たないアプリケーションプログラマでも,GPU の演算性能を有効に
利用することができる.
また第 2 のアプローチは,既存の CPU 向け並列化プログラミング環境を用いて
GPU 向けのプログラムを記述可能な並列化プログラミング環境の提供を行った.そ
のため,GPU に関する知識を持たないアプリケーションプログラマでも,GPU の
演算性能を有効に利用することができる.
以上の 2 つのアプローチにより汎用プログラミング環境を用いて GPGPU を利用
可能とすることで,GPU のアーキテクチャや GPGPU 用の新たなプログラミング環
境を習得する手間や,GPU を制御するための記述の手間といった,アプリケーショ
ンプログラマにとっての手間を削減し,GPGPU を容易に利用可能とした.
本研究の貢献は,GPGPU を多くのアプリケーションプログラマが容易に活用で
きるようにするアプローチを提案し,提案に基づいてライブラリや処理系の実装を
行い有効性を実証した点にある.この成果は,今後さらに普及が広がると考えられ
5.2 今後の課題
132
る GPU を搭載した計算機システムにおけるアプリケーションプログラマにとって
使いやすい利用環境のあり方を示すものとして意義がある.
5.2
今後の課題
本研究によって明らかとなった今後の課題は以下の 2 点である.
第 1 の課題は,OMPCUDA の実装によって明らかになった,汎用プログラミング
環境を用いた GPGPU の限界に関するものである.
アプローチ 2 では既存の CPU 向け並列化プログラミング環境を用いた GPGPU
プログラミングについて検討を行い,GPGPU に適した既存の並列化プログラミン
グ環境として OpenMP を選択し,CUDA と対応づけて高い演算性能を達成した.本
研究はアプリケーションプログラマにとっての習得や実装の手間を削減することを
重視した研究であるため,OpenMP に対する新たな指示子の追加等は行わないとい
う方針で対応付けや実装を行った.
一方で,利用の手間や難しさが削減されることよりも高い性能が得られることを
重視するユーザ,高い性能が得られるのであれば習得や利用の手間と難しさが増加
してもかまわないというアプリケーションプログラマもいるものと考えられる.
例えば OMPCUDA の性能を向上させるための方法として以下のような 2 つの手
法が考えられる.
1. OpenMP と CUDA の対応付けについては GlobalMemory を共有メモリと見
なして GPU 上の全 SP (CUDA Thread) が並列処理を行うものとしたため,
高速な CUDA プログラムを作成する上で効果の大きな SharedMemory の活用
が行えていない.GlobalMemory と SharedMemory に (さらに可能であれば
ConstantMemory や TextureMemory にも) 適切にデータを割り当てることが
できれば,より高い性能を得ることができる可能性がある.
2. 現在の OMPCUDA は,OpenMP の並列実行部を GPU で実行するという OpenMP
と CUDA との対応付けを行っている.しかし,アプローチ 1 において CPU と
GPU による並列処理を行うことで CPU と GPU の性能を活用しさらに高い演
算性能を得られることを示したように,GPU による並列処理は問題のデータ
5.2 今後の課題
133
規模等によっては CPU よりも良い性能が得られないことがあり,また CPU
と GPU による問題分割を行うことでさらに高い演算性能を得られることが期
待できる.そのためマルチコア CPU と GPU を搭載したような計算機システ
ムにおいては,並列実行部ごとに CPU で実行するか GPU で実行するかを切
り替えることでより高い性能が得られる可能性があり,さらに 1 つの並列実行
部を CPU と GPU で分割して実行すればさらに高い性能が得られると考えら
れる.
これらの手法を実現するには,プログラム変換機構を改良し,OMPCUDA が GPU
上の複数種類のメモリをさらに有効に活用したり,CPU と GPU による問題分割・
並列実行などを行えるようにする必要がある.一方で,OpenMP は単一の共有メモ
リを持つ計算機システムにおいて利用されることを想定して仕様が決められており,
また CUDA では CPU と GPU のメモリ空間が独立しているうえに任意のタイミン
グで CPU-GPU 間のデータ送受信を行うことができない.そのため既存の OpenMP
の指示子では,アプリケーションプログラマがプログラム変換機構が上記のような
メモリの活用や問題分割・並列実行を含むプログラム変換を行うのに十分な情報を
記述できない可能性がある.
このように,既存の汎用プログラミング環境は CPU を対象として提案・実装さ
れてきたものであるため GPGPU に利用する場合にはどうしても適用できない・非
常に適用しにくいという問題が生じる可能性がある.これらの問題を解決して GPU
を搭載した計算機システムの性能をさらに活用するためには,既存の汎用プログラ
ミング環境に対してある程度の仕様変更や仕様追加を行わなくてはならない可能性
が考えられる.
そのため,今後さらに高い性能への要求が高まった場合には,“既存の指示文の
みでも正しく (GPU 上で並列に) 動作し,新たな指示文を用いるとさらに (CPU と
GPU による問題分割を行い) 性能が向上する” など,既存の CPU 向け並列化プログ
ラミング環境に対してアプリケーションプログラマにとっての習得の手間を大きく
増加させることなく GPU の性能を活用しやすいようにするにはどのような変更を
加えていくべきかが課題となると考えられる.
第 2 の課題は,GPU 以外の SIMD 型アクセラレータや OpenCL との比較である.
Cell 向けの OpenMP 環境が開発されていることを 2 章で述べたが,CPU・Cell・
5.2 今後の課題
134
GPU はそれぞれ異なる特徴を持つハードウェアであるため,同じ OpenMP を用い
たプログラミングでも性能最適化のためのチューニング方法等が異なる可能性があ
る.これらを比較することで,アプリケーションプログラマにとってさらに利用し
やすく高い性能が得られる GPGPU 環境を提供できるようになることや,GPU だ
けではなく他の SIMD 型アクセラレータも含めてアプリケーションプログラマに利
用しやすく高い性能が得られるプログラミング環境の提供につながるものと考えら
れる.
また OpenCL が普及し様々なハードウェア上で同じプログラムが利用できるよう
になった際には,OpenCL さえ習得すれば汎用性の高いプログラムが記述できるよ
うになりアプリケーションプログラマにとっての習得や利用の手間が削減されること
が考えられる.一方で OpenCL そのものの習得や利用の手間が生じるため,OpenCL
を用いてアプリケーションプログラマが 1 からプログラムを記述した場合と本研究
の各アプローチを用いた場合とで手間や性能にどのような差が生じるかを比較する
ことや,OpenCL 上に既存の CPU 向け並列化プログラミング環境を実装すること
で,さらにアプリケーションプログラマにとって利用しやすく高い性能が得られる
プログラミング環境の提供につながるものと考えられる.
謝辞
135
謝辞
本研究を進めるにあたり,あたたかいご指導ご鞭撻を頂きました並列処理学講座
(現在高性能コンピューティング学講座) 本多弘樹教授に心から感謝の意を表します.
電気通信大学 弓場敏嗣名誉教授,電気通信大学 近藤正章准教授,東京大学 片桐
孝洋准教授,東京工業大学 吉瀬謙二講師,電気通信大学 平澤将一助教には,研究
内容についてのご助言のみならず,研究の進め方や研究者としての物事の見方・考
え方についても多くのご助言を頂きました.心からお礼申し上げます.
本研究の一部は独立行政法人 科学技術振興機構 (JST) 戦略的創造研究推進事業
(CREST) の支援を受けて行いました.日頃からご助言を頂いた本事業グループの
方々に感謝いたします.
本研究の一部は独立行政法人 情報処理推進機構 (IPA) 主催の未踏ソフトウェア創
造事業 (未踏ユース) の支援を受けて行いました.また,未踏ユースの関係者および
開発者の皆様には研究に対するご助言を頂いたのみならず,ソフトウェア開発者と
しての情熱や心構えを学ばせていただきました.心から感謝いたします.
GPGPU の研究を行うきっかけの一部となった,そして学生生活を支えてくれた
電気通信大学 X680x0 同好会の皆様に感謝いたします.
最後に,研究に関する議論や学生生活を支えて頂いた石原誠氏,田邊浩志氏,渡
邊啓正氏,ほか並列処理学講座・高性能コンピューティング学講座の皆様に感謝い
たします.
参考文献
136
参考文献
[1] 佐久間弘文. 地球シミュレータ:2. 地球シミュレータの応用 2.1 大気・海洋の
シミュレーション. 情報処理学会会誌, Vol. 45, No. 2, pp. 130–133, 2004.
[2] 斎藤稔. 地球シミュレータによる蛋白質の大規模シミュレーション:ベクトル
化と並列化による加速性能. 情報処理学会論文誌 コンピューティングシステ
ム, Vol. 46, No. SIG7(ACS10), pp. 9–17, 2005.
[3] 朴泰祐, 佐藤三久, 宇川彰. 計算科学のための超並列クラスタ PACS-CS の概要
. 情報処理学会 研究報告 (HPC-103), pp. 133–138, 2005.
[4] 谷啓二, 横川三津夫. 地球シミュレータ計画:<前編>地球(ガイア)との共
生の指針を求めて. 情報処理学会会誌, Vol. 41, No. 3, pp. 249–254, 2000.
[5] 松岡聡. TSUBAME の飛翔: ペタスケールへ向けた「みんなのスパコン」の構
築. 情報処理学会 研究報告 (HPC-107), pp. 37–42, 2006.
[6] Hiroshi Nakashima. T2K Open Supercomputer: Inter-university and Interdisciplinary Collaboration on the New Generation Supercomputer. Informatics
Research for Development of Knowledge Society Infrastructure, International
Conference on, Vol. 0, pp. 137–142, 2008.
[7] 独 立 行 政 法 人 理 化 学 研 究 所.
立 地 地 点 を 神 戸 に 決 定.
次 世 代 ス ー パ ー コ ン ピュー タ 施 設 の
プ レ ス リ リ ー ス,
http://www.riken.go.jp/r-
world/info/release/press/2007/070328/index.html, March 2007.
[8] A. Gara, M. A. Blumrich, D. Chen, G. L.-T. Chiu, P. Coteus, M. E. Giampapa, R. A. Haring, P. Heidelberger, D. Hoenicke, G. V. Kopcsay, T. A.
Liebsch, M. Ohmacht, B. D. Steinmacher-Burow, T. Takken, and P. Vranas.
Overview of the Blue Gene/L system architecture. IBM Journal of Research
and Development, pp. 195–212, 2005.
[9] Intel. Intel(R) Pentium(R) 4 Processor 6xx Sequence and Intel(R) Pentium(R)
4 Processor Extreme Edition Datasheet, 2005.
参考文献
137
[10] IBM. IBM Unleashes World’s Fastest UNIX System, Offers Twice the Performance of HP Itanium System at Comparable Price. Press release, http://www03.ibm.com/press/us/en/pressrelease/23843.wss, April 2008.
[11] Stephen L. Smith. Intel Roadmap Overview. Intel Developer Forum’s presentation, 2008.
[12] Randy Allen. AMD Financial Analyst Day. AMD Financial Analyst Day’s
presentation, 2008.
[13] NVIDIA.
the
NVIDIA
world’s
first
Tesla
teraflop
Computing
parallel
Solutions
processor.
now
Press
with
release,
http://www.nvidia.com/object/io 1213744368983.html, June 2008.
[14] AMD.
aflop
AMD
Barrier.
Stream
Processor
Press
release,
First
to
Break
1
Ter-
http://www.amd.com/us-
en/Corporate/VirtualPressRoom/0,,51 104 543 15104˜126593,00.html,
June 2008.
[15] John D. Owens, David Luebke, Naga Govindaraju, Mark Harris, Jens Krüger,
Aaron E. Lefohn, and Timothy J. Purcell. A Survey of General-Purpose Computation on Graphics Hardware. In Eurographics 2005, State of the Art Reports, pp. 21–51, August 2005.
[16] gpgpu.org.
General-Purpose computation on GPUs(GPGPU) website,
http://gpgpu.org/.
[17] Dinesh Manocha. General-Purpose Computations using Graphics Processors.
In Computer, Vol.38, Num.8, pp. 85–88. IEEE Computer Society, 2005.
[18] David Geer. Taking the Graphics Processor beyond Graphics. In Computer,
Vol.38, Num.9, pp. 14–16. IEEE Computer Society, 2005.
[19] T.Amada, M.Imura, Y.Yasumuro, Y.Manabe, and K.Chihara. Particle-Based
Fluid Simulation on GPU. In ACM Workshop on General-Purpose Computing
on Graphics Processors(Poster session), 2004.
参考文献
138
[20] E.Scott Larsen and David McAllister. Fast matrix multiplies using graphics
hardware. In Proceedings of the 2001 ACM/IEEE conference on Supercomputing, p. CDROM, 2001.
[21] 松井学, 伊野文彦, 萩原兼一. プログラマブル GPU における LU 分解の設計と
実装. 先進的計算基盤システムシンポジウム SACSIS2005, pp. 359–367, 2005.
[22] Nico Galoppo, Naga K. Govindaraju, Michael Henson, and Dinesh Manocha.
LU-GPU: Efficient Algorithms for Solving Dense Linear Systems on Graphics
Hardware. In Proceedings of the ACM/IEEE SC—05 Conference, p. 3, 2005.
[23] 小松原誠, 森眞一郎, 中島康彦, 富田眞治. 汎用グラフィクスカードを用いた格子
ボルツマン法による流体シミュレーション. 情報処理学会 研究報告 (ARC-163),
pp. 37–42, 2005.
[24] 森眞一郎, 五島正裕, 中島康彦, 富田眞治. 並列ベクトルプロセッサとしてのグ
ラフィクスプロセッサ. 情報処理学会関西支部大会, pp. 179–182, 2004.
[25] 丸山悠樹, 中田智史, 高山征大, 篠本雄樹, 五島正裕, 森眞一郎, 中島康彦, 富田
眞治. 汎用グラフィクスカードを用いた並列ボリュームレンダリングシステム
. 情報処理学会論文誌, Vol.45, No.SIG11, ACS7, pp. 415–424, 2004.
[26] 篠本雄基, 三輪忍, 嶋田創, 森眞一郎, 中島康彦, 富田眞治. 並列ボリュームレ
ンダリングにおける投機的描画に関する考察. 情報処理学会 研究報告, 2005-
ARC-164, pp. 145–150, 2005.
[27] Mark Joselli, Esteban Clua, Anselmo Montenegro, Aura Conci, and Paulo
Pagliosa. A new physics engine with automatic process distribution between
cpu-gpu. In Sandbox ’08: Proceedings of the 2008 ACM SIGGRAPH symposium on Video games, pp. 149–156, 2008.
[28] Mark Harris. Gpu physics. In SIGGRAPH ’07: ACM SIGGRAPH 2007
courses, p. 15, 2007.
参考文献
139
[29] K. Moreland and E. Angel. The FFT on a GPU. In Proc. SIGGRAPH/EUROGRAPHICS Workshop Graphics Hardware, pp. 112–119, 2003.
[30] 額田彰, 尾形泰彦, 遠藤敏夫, 松岡聡. CUDA 環境における高性能 3 次元 FFT.
情報処理学会論文誌 コンピューティングシステム, Vol. 1, No. 2, pp. 231–239,
2008.
[31] Chris J. Thompson, Sahngyun Hahn, and Mark Oskin. Using Modern Graphics Architectures for General-Purpose Computing: A Framework and Analysis. In Proceedings of the 35th annual ACM/IEEE International Symposium
on Microarchitecture, pp. 306–317, 2002.
[32] Jens Krüger and Rüdiger Westermann. Linear Algebra Operators for GPU
Implementation of Numerical Algorithms. In Proceedings of ACM SIGGRAPH
2003, pp. 908–916, 2003.
[33] Nolan Goodnight and Cliff Woolley and Gregory Lewin and David Luebke andGreg Humphreys. A multigrid solver for boundary value problems using programmable graphics hardware. In Proceedings of the ACM SIGGRAPH/EUROGRAPHICS conference on Graphics hardware, pp. 102–111, 2003.
[34] Ádám Moravánszky. Dense Matrix Algebra on the GPU. In Wolfgang F.
Engel, editor, ShaderX2: Shader Programiing Tips & Tricks With DirectX 9,
pp. 352–380. Wordware, 2003.
[35] Jeff Bolz, Ian Farmer, Eitan Grinspun, and Peter Scheróder. Sparse Matrix
Solvers on the GPU: Conjugate Gradients and Multigrid. In Proceedings of
ACM SIGGRAPH 2003, pp. 917–924, 2003.
[36] Wesley De Neve, Dieter Van Rijsselbergen, Charles Hollemeersch, Jan De
Cock, Stijn Notebaert, and Rik Van de Walle. GPU-assisted decoding of
video samples represented in the YCoCg-R color space. In MULTIMEDIA ’05:
Proceedings of the 13th annual ACM international conference on Multimedia,
pp. 447–450, 2005.
参考文献
140
[37] 今給黎 隆. DirectX 9 シェーダプログラミングブック. 毎日コミュニケーショ
ンズ, 2004.
[38] OpenGL Architecture Review Board, Dave Shreiner, Mason Woo, Jackie Neider, and Tom Davis. OpenGL Programming Guide: The Official Guide to
Learning OpenGL, Version 2.1 (OpenGL). Addison-Wesley, 2007.
[39] Randima Fernando and Mark J. Kilgard. The Cg Tutorial: The Definitive
Guide to Programmable Real-Time Graphics. Addison-Wesley, 2003.
[40] NVIDIA. NVIDIA CUDA Compute Unified Device Archtecture Programming
Guide version 2.0, 2008.
[41] AMD. ATI CTM Guide Version 1.01, 2006.
[42] AMD. Stream Computing User Guide rev1.3.0, 2008.
[43] Dr James Irwin and Mr Simon McIntosh-Smith. Delivering aggregated performance for high performance math libraries in accelerated systems. In Inernational Supercomputing Conference ISC’07, 2007.
[44] IBM.
Cell Broadband Engine resource center website, http://www-
128.ibm.com/developerworks/power/cell/.
[45] Intel. Intel(R) Xeon(R) Processor 5400 Series, Boost Performance and Energy
Efficiency with New 45nm Multi-core Intel(R) Xeon(R) Processors, 2008.
[46] NVIDIA. Technical Brief, NVIDIA GeForce(R) GTX 200 GPU Architectural
Overview, Second-Generation Unified GPU Architecture for Visual Computing, 2008.
[47] ClearSpeed.inc.
CLEARSPEED ADVANCE(TM) e720 ACCELERATOR.
PRODUCT BRIEF, 2008.
[48] Fixstars. Gigaaccel 180 製品カタログ, 2008.
参考文献
141
[49] ClearSpeed.inc. CLEARSPEED WHITEPAPER: CSX PROCESSOR ARCHITECTURE. White Papers, 2007.
[50] ClearSpeed.inc. CLEARSPEED CSX700 PROCESSOR. PRODUCT BRIEF,
2008.
[51] ClearSpeed.inc. Cn Standard Library Reference Files for 3.1, 2008.
[52] IBM.
tional
IBM-Built
Lab
No.1
Supercomputer
in
TOP500.
at
NNSA’s
Press
Los
release,
Alamos
Na-
http://www-
03.ibm.com/press/us/en/pressrelease/24480.wss, June 2008.
[53] TOSHIBA.
SE1000
Toshiba
starts
high-performance
sample
stream
shipping
processor.
of
SpursEngine(TM)
Press
release,
http://www.toshiba.co.jp/about/press/2008 04/pr0801.htm, April 2008.
[54] Alexandre E. Eichenberger, KathrynO ’Brien, KevinO ’Brien, Peng Wu, Tong
Chen, Peter H. Oden, Daniel A. Prener, Janice C. Shepherd, Byoungro So,
Zehra Sura, Amy Wang, Tao Zhang, Peng Zhao, Michael Gschwind. Optimizing Compiler for the CELL Processor. In Parallel Architectures and Compilation Techniques, 2005. PACT 2005. 14th International Conference on, pp.
17–21, 2005.
[55] Rosa M. Badia Josep M. Perez, Pieter Bellens and Jesus Labarta. CellSs:
Programming the Cell/B.E. made easier. IBM Journal of R&D, Vol. 51, No. 5,
2007.
[56] 町田智志, 中西悠, 平澤将一, 本多弘樹. POSIX スレッドを用いた Cell プロ
セッサ向け API の提案. 情報処理学会 研究報告 (ARC-175), pp. 71–76, 2007.
[57] Ian Buck, Tim Foley, Daniel Horn, Jeremy Sugerman, Kayvon Fatahalian,
Mike Houston, and Pat Hanrahan. Brook for GPUs: Stream Computing on
Graphics Hardware. SIGGRAPH 2004, 2004.
[58] AMD. Brook+. SC07 BOF Session presentation, November 2007.
参考文献
142
[59] Michael D. McCool. Data-Parallel Programming on the Cell BE and the GPU
using the RapidMind Development Platform. In GSPx Multicore Applications
Conference, 2006.
[60] Michael McCool and Stefanus Du Toit. Metaprogramming GPUs with Sh. A
K Peters Ltd, 2004.
[61] 滝沢寛之, 白取寛貴, 佐藤功人, 小林広明. SPRAT:実行時自動チューニング機
能を備えるストリーム処理記述用言語. 情報処理学会論文誌 コンピューティ
ングシステム, Vol. 1, No. 2, pp. 207–220, 2008.
[62] Khronos OpenCL Working Group. the OpenCL Specification Version: 1.0,
2009.
[63] 宮田一乗, 高橋誠史, 黒田篤. GPU コンピューティングの動向と将来像. 芸術
科学会論文誌, pp. 13–19, 2005.
[64] 高橋誠史, 宮田一乗, 白井暁彦. EasyGPU : GPU を用いたコンピュータビジョ
ン実験環境の開発 (メディア表現の創出を支えるハードウェア・プラットフォー
ム技術). 情報処理学会 研究報告 (CG-120), pp. 19–24, 2005.
[65] James Fung and Steve Mann. Openvidia: parallel gpu computer vision. In
MULTIMEDIA ’05: Proceedings of the 13th annual ACM international conference on Multimedia, pp. 849–852, 2005.
[66] J.P. Farrugia, P. Horain, E. Guehenneux, and Y. Allusse. GPUCV: A framework for image processing acceleration with graphics processors. CDROM
proc.of the IEEE International Conference on Multimedia & Expo (ICME
2006), p. CDROM, 2006.
[67] Philippe Charles, Christian Grothoff, Vijay Saraswat, Christopher Donawa,
Allan Kielstra, Kemal Ebcioglu, Christoph von Praun, and Vivek Sarkar. X10:
an object-oriented approach to non-uniform cluster computing. In OOPSLA
’05: Proceedings of the 20th annual ACM SIGPLAN conference on Object oriented programming, systems, languages, and applications, pp. 519–538, 2005.
参考文献
143
[68] David Callahan, Bradford L. Chamberlain, and Hans P. Zima. The cascade
high productivity language. In In 9th International Workshop on High-Level
Parallel Programming Models and Supportive Environments (HIPS 2004), pp.
52–60, April 2004.
[69] Eric Allen, David Chase, Christine Flood, Victor Luchangco, Jan-Willem
Maessen, Sukyoung Ryu, and Guy L. Steele Jr. Project fortress: A multicore language for multicore processors. Linux Magazine, September 2007,
2007.
[70] W Carlson, J.M Draper, D.E Culler, K Yelick, E Brooks, and K Warren.
Introduction to UPC and Language Specification, 1999.
[71] 妹尾義樹. HPF 言語の動向:HPF 言語の現状と将来. 情報処理学会会誌, Vol. 38,
No. 2, pp. 90–99, 1997.
[72] Robert W. Numrich and John Reid. Co-array Fortran for parallel programming. SIGPLAN Fortran Forum, Vol. 17, No. 2, pp. 1–31, 1998.
[73] 李珍泌, 佐藤三久, 朴泰祐. 分散メモリ向けデータ並列言語 OpenMPD の設計
と実装. 情報処理学会 研究報告 (ARC-172/HPC-109), pp. 49–54, 2007.
[74] 岩崎英哉, 胡振江. マルチコアを活かすお手軽並列プログラミング:4. 並列計算
パターン (スケルトン) による並列プログラミング. 情報処理学会会誌, Vol. 49,
No. 12, pp. 1385–1394, 2008.
[75] Kiminori Matsuzaki and Hideya Iwasaki and Kento Emoto and Zhenjiang Hu.
A library of constructive skeletons for sequential style of parallel programming.
In InfoScale ’06: Proceedings of the 1st international conference on Scalable
information systems, p. 13, 2006.
[76] 金井達徳, 瀬川淳一, 武田奈穂美. 組み込みプロセッサのメモリアーキテクチャ
に依存しない画像処理プログラムの記述と実行方式. 情報処理学会論文誌 コ
ンピューティングシステム, Vol. 48, No. SIG13(ACS 19), pp. 287–301, 2007.
参考文献
144
[77] R. Clint Whaley, Antoine Petitet, and Jack J. Dongarra. Automated Empirical Optimization of Software and the ATLAS Project. Parallel Computing,
Vol. 27, No. 1–2, pp. 3–35, 2001.
[78] 片桐孝洋. ソフトウエア自動チューニング―数値計算ソフトウエアへの適用と
その可能性. 慧文社, 2004.
[79] NVIDIA. Performance Tools & SLI Programming. Iron Developer 2005 Presentations, 2005.
[80] Jon Story. Harnessing the Performance of CrossFireX(TM) (August 2008).
Radeon SDK Samples & Documents, 2008.
[81] Nicholas J. Higham. Exploiting Fast Matrix Multiplication Within the Level
3 BLAS. ACM Transactions on Mathematical Software, Vol. 16, No. 4, pp.
352–368, 1990.
[82] C. L. Lawson, R. J. Hanson, D. Kincaid, and F. T. Krogh. Basic Linear
Algebra Subprograms for FORTRAN usage. ACM Trans. Math. Soft., Vol. 5,
No. 3, pp. 308–323, 1979.
[83] TOP500. TOP500 website, http://www.top500.org/.
[84] HPL.
pack
A Portable Implementation of the High-Performance LinBenchmark
for
Distributed-Memory
Computers
website,
http://www.netlib.org/benchmark/hpl/.
[85] Kazushige
Goto.
Goto
BLAS
website,
http://www.tacc.utexas.edu/resources/software/.
[86] K.Fatahalian, J.Sugerman, and P.Hanrahan. Understanding the Efficiency
of GPU Algorithms for Matrix-Matrix Multiplication. In Graphics Hardware
2004, pp. 133–137, 2004.
参考文献
145
[87] Jesse D. Hall, Nathan A. Carr, and John C. Hart. Cache and Bandwidth
Aware Matrix Multiplication on the GPU. Technical report, University of
Illinois Dept. of Computer Science, 2003.
[88] Changhao Jiang and Marc Snir. Automatic Tuning Matrix Multiplication
Performance on Graphics Hardware. In Proceedings of the 14th International
Conference on Parallel Architectures and Compilation Techniques (PACT’05),
pp. 185–196, 2005.
[89] 笹生健, 松岡聡. HPL のパラメータチューニングの解析. 情報処理学会 研究報
告 (HPC-091), pp. 125–130, 2002.
[90] Erik Lindholm, John Nickolls, Stuart Oberman, and John Montrym. NVIDIA
Tesla: A Unified Graphics and Computing Architecture. IEEE MICRO 2008,
Vol.28, Issue.2, 2008.
[91] AMD. AMD Tech Day UK: ATI Radeon(TM) HD 2000 SeriesTechnology
Overview, 2007.
[92] Aart J. C. Bik and Milind Girkar and Paul M. Grey and Xinmin Tian. Automatic intra-register vectorization for the Intel architecture. In International
Journal of Parallel Programming, Vol. 30, pp. 65–98, 2002.
[93] 中西悠, 渡邊啓正, 平澤将一, 本多弘樹. コードの性能可搬性を提供する SIMD
向け共通記述方式. 情報処理学会論文誌 コンピューティングシステム, Vol. 48,
No. SIG13(ACS 19), pp. 95–105, 2007.
[94] Intel. Intel C++ Compiler website, http://www.intel.com/cd/software/
products/asmo-na/eng/compilers/index.htm.
[95] Apple. Velocity Engine website,
http://developer.apple.com/hardwaredrivers/ve/.
[96] C. Amza, A.L. Cox, S. Dwarkadas, P. Keleher, H. Lu, R. Rajamony, W. Yu,
and W. Zwaenepoel. TreadMarks: Shared Memory Computing on Networks
of Workstations. IEEE Computer, Vol. 29, No. 2, pp. 18–28, 1996.
参考文献
146
[97] 吉瀬謙二, 田邊浩志, 多忠行, 片桐孝洋, 本多弘樹, 弓場敏嗣. S-DSM システム
におけるページ要求時の受信通知を削減する方式. 情報処理学会論文誌 コン
ピューティングシステム, Vol. 46, No. SIG12(ACS 11), pp. 170–180, 2005.
[98] OpenMP.org. OpenMP : Simple, Portable, Scalable SMP Programming website, http://www.openmp.org/.
[99] Greg Burns, Raja Daoud, and James Vaigl. LAM: An Open Cluster Environment for MPI. In Proceedings of Supercomputing Symposium, pp. 379–386,
1994.
[100] Jeffrey M. Squyres and Andrew Lumsdaine. A Component Architecture for
LAM/MPI. In Proceedings, 10th European PVM/MPI Users’ Group Meeting,
No. 2840 in Lecture Notes in Computer Science, pp. 379–387, Venice, Italy,
September / October 2003. Springer-Verlag.
[101] Vishal Aslot, Max Domeika, Rudolf Eigenmann, Greg Gaertner, Wesley B.
Jones, and Bodo Parady. SPEComp: A New Benchmark Suite for Measuring
Parallel Computer Performance. In WOMPAT 2001 Workshop on OpenMP
Applications and Tools, pp. 1–10, 2001.
[102] M.Sato, S.Satoh, K.Kusano, and Y.Tanaka. Design of OpenMP Compiler for
an SMP Cluster. In EWOMP ’99, pp. 32–39, 1999.
[103] Daniel Horn. Stream Reduction Operations for GPGPU Applications. In GPU
Gems2, chapter 36. Addison-Wesley, 2005.
[104] David Roger, Ulf Assarsson, and Nicolas Holzschuch. Efficient Stream Reduction on the GPU. In Workshop on General Purpose Processing on Graphics
Processing Units, oct 2007.
[105] John Owens and UC Davis. Data-parallel algorithms and data structures.
In SUPERCOMPUTING 2007 Tutorial: Hight Performance Computing with
CUDA, 2007.
参考文献
147
[106] 尾形泰彦, 遠藤敏夫, 丸山直也, 松岡聡. 性能モデルに基づく CPU 及び GPU を
併用する効率的な FFT ライブラリ. 情報処理学会論文誌 コンピューティング
システム, Vol. 1, No. 1, pp. 40–50, 2008.
A 付録 1: CUDA を用いた実装のソースコード
148
A 付録 1: CUDA を用いた実装のソースコード
アプローチ 2 での評価 (4.3 節) に用いた SimpleCUDA プログラム (行列積) のソー
スコードのうち,CUDA の初期化などを除外した主な部分を以下に示す.
// GPU 向けプログラム (関数宣言を除いて 5 行)
extern "C" __global__ void mm_reference
(float data_c[N*N], float data_a[N*N], float data_b[N*N]){
int i; float tmp = 0.0f;
for(i=0; i<N; i++){
tmp += data_a[N*blockIdx.x + i] * data_b[N*i + threadIdx.x];
}
data_c[blockDim.x*blockIdx.x+threadIdx.x] = tmp;
}
// CPU 向けプログラム
ここに示した主な部分は
// コメントを除いて 16 行,初期化等を含めると合計 80 行程度
CU_SAFE_CALL(cuFuncSetBlockShape( func1, _THREADSx, _THREADSy, 1 ));
CU_SAFE_CALL(cuFuncSetSharedSize( func1, sizeof(float)*_THREADSxy ));
CUdeviceptr d_data_c;
CU_SAFE_CALL(cuMemAlloc(&d_data_c, sizeof(float)*N*N));
CU_SAFE_CALL(cuParamSeti(func1, 0, d_data_c));
CUdeviceptr d_data_a;
CU_SAFE_CALL(cuMemAlloc(&d_data_a, sizeof(float)*N*N));
// 次の行が CPU から GPU に対する行列 A の送信
CU_SAFE_CALL(cuMemcpyHtoD(d_data_a, data_a, sizeof(float)*N*N));
CU_SAFE_CALL(cuParamSeti(func1, 4, d_data_a));
CUdeviceptr d_data_b;
CU_SAFE_CALL(cuMemAlloc(&d_data_b, sizeof(float)*N*N));
// 次の行が CPU から GPU に対する行列 B の送信
CU_SAFE_CALL(cuMemcpyHtoD(d_data_b, data_b, sizeof(float)*N*N));
CU_SAFE_CALL(cuParamSeti(func1, 8, d_data_b));
CU_SAFE_CALL(cuParamSetSize(func1, 12));
// 次の行が GPU に対する実行開始指示
CU_SAFE_CALL(cuLaunchGrid(func1, _BLOCKSx, _BLOCKSy));
// 次の行が GPU から CPU に対する行列 C の書き戻し
CU_SAFE_CALL(cuMemcpyDtoH(data_c, d_data_c, sizeof(float)*N*N));
149
関連論文の印刷公表の方法および時期
1. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 弓場 敏嗣
論文題目: GPU による高速な行列積の実装
印刷公表の方法および時期: 情報処理学会第 67 回全国大会, No. 3ZB-3, pp.159–
160, 2005 年 3 月 2 日
(本文との関連: 第 3 章に関連)
2. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 弓場 敏嗣
論文題目: GPU による BLAS 演算の性能評価
印刷公表の方法および時期: 先進的計算基盤システムシンポジウム SACSIS2005
論文集, pp. 247–248, 2005 年 5 月 18 日
(本文との関連: 第 3 章に関連)
3. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 弓場 敏嗣
論文題目: CPU と GPU の並列処理による行列積和演算方式の提案
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-164), pp.139–144,
2005 年 8 月 4 日
(本文との関連: 第 3 章に関連)
4. 全著者名: 大島 聡史
論文題目: CPU と GPU を用いた効率的な並列数値計算方式の提案と実装
印刷公表の方法および時期: 修士論文, 電気通信大学大学院情報システム学研
究科, 2006 年 3 月
5. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 弓場 敏嗣
論文題目: CPU と GPU を用いた並列 GEMM 演算の提案と実装
印刷公表の方法および時期: SACSIS2006 -先進的計算基盤システムシンポジ
ウム, pp. 41–50, 2006 年 5 月 22 日
(本文との関連: 第 3 章に関連)
6. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 本多 弘樹, 弓場 敏嗣
論文題目: CPU と GPU を複数用いた並列数値計算環境の検討
印刷公表の方法および時期: SACSIS2006 -先進的計算基盤システムシンポジ
150
ウム, pp. 252–253, 2006 年 5 月 22 日
(本文との関連: 第 3 章に関連)
7. 全著者名: Satoshi Ohshima, Kenji Kise, Takahiro Katagiri, Toshitsugu Yuba
論文題目: Parallel Processing of Matrix Multiplication in a CPU and GPU
Heterogeneous Environment
印刷公表の方法および時期: Proceedings of VECPAR’2006, pp.34 (14 pages,
CD-ROM), 2006 年 7 月 10 日
(本文との関連: 第 3 章に関連)
8. 全著者名: 大島 聡史, 片桐 孝洋, 本多 弘樹
論文題目: CPU と GPU を用いた数値計算環境の提案
印刷公表の方法および時期: 日本応用数理学会 2006 年度年会, pp.328–329, 2006
年 9 月 16 日
(本文との関連: 第 3 章に関連)
9. 全著者名: 大島 聡史, 吉瀬 謙二, 片桐 孝洋, 弓場 敏嗣
論文題目: CPU と GPU を用いた並列 GEMM 演算の提案と実装
印刷公表の方法および時期: 情報処理学会論文誌 コンピューティングシステ
ム, SIG12(ARC-15), pp.317–328, 2006 年 9 月 15 日
(本文との関連: 第 3 章に関連)
10. 全著者名: 大島 聡史, 片桐 孝洋, 弓場 敏嗣, 平澤 将一, 本多 弘樹
論文題目: CPU と GPU を用いた基本行列計算ライブラリ
印刷公表の方法および時期: HPCS2007 2007 年ハイパフォーマンスコンピュー
ティングと計算科学シンポジウム, pp.66, 2007 年 1 月 17 日
(本文との関連: 第 3 章に関連)
11. 全著者名: Satoshi Ohshima, Kenji Kise, Takahiro Katagiri, Toshitugu Yuba
論文題目: Parallel Processing of Matrix Multiplication in a CPU and GPU
Heterogeneous Environment
印刷公表の方法および時期: Selected Paper of VECPAR’2006, Springer LNCS
4395, pp.305–318, 2007 年 5 月 30 日
(本文との関連: 第 3 章に関連)
151
12. 全著者名: 大島 聡史, 平澤 将一, 本多 弘樹
論文題目: 既存の並列化手法を用いた GPGPU プログラミングの提案
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-175), pp.7–10, 2007
年 11 月 20 日
(本文との関連: 第 4 章に関連)
13. 全著者名: 大島 聡史, 平澤 将一, 本多 弘樹
論文題目: 既存の並列化手法を用いた GPGPU プログラミング
印刷公表の方法および時期: 第 49 回プログラミング・シンポジウム 予稿集,
pp.81–88, 2008 年 1 月 8 日
(本文との関連: 第 4 章に関連)
14. 全著者名: 大島 聡史, 平澤 将一, 本多 弘樹
論文題目: メッセージ通信型 GPGPU プログラミング
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-177/HPC-114),
pp.109–114, 2008 年 3 月 5 日
(本文との関連: 第 4 章に関連)
15. 全著者名: 大島 聡史, 平澤 将一, 本多 弘樹
論文題目: OMPCUDA : GPU 向け OpenMP の実装
印刷公表の方法および時期: 情報処理学会 研究報告 (HPC-118), pp.121-126,
2008 年 12 月 17 日
(本文との関連: 第 4 章に関連)
16. 全著者名: 大島 聡史, 平澤 将一, 本多 弘樹
論文題目: OMPCUDA : GPU 向け OpenMP の実装
印刷公表の方法および時期: HPCS2009 2009 年ハイパフォーマンスコンピュー
ティングと計算科学シンポジウム, pp.131–138, 2009 年 1 月 22 日
(本文との関連: 第 4 章に関連)
152
参考論文の印刷公表の方法および時期
1. 全著者名: 大島 聡史, 檜田 敏克, 吉瀬 謙二, 片桐 孝洋, 本多 弘樹, 弓場 敏嗣
論文題目: 命令レベル並列性を利用した OpenMP によるプロセッサシミュレー
タの並列実行
印刷公表の方法および時期: 情報処理学会第 66 回全国大会, No. 5T-8, pp.121–
123, 2004 年 3 月 9 日
2. 全著者名: 坂口 朋也, 鈴木 祥, 今村 昌之, 大島 聡史, 片桐 孝洋, 吉瀬 謙二, 弓
場 敏嗣
論文題目: 相乗り通信を利用したソフトウェアDSMの通信回数削減手法
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-169), pp.151–156,
2006 年 7 月 31 日
3. 全著者名: 今村 昌之, 鈴木 祥, 坂口 朋也, 大島 聡史, 片桐 孝洋, 吉瀬 謙二, 弓
場 敏嗣
論文題目: ソフトウェア DSM Mocha と MPI の並列ベンチマークを用いた性
能評価
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-172/HPC-109),
pp.103–108, 2007 年 3 月 1 日
4. 全著者名: 今村 昌之, 鈴木 祥, 坂口 朋也, 大島 聡史, 片桐 孝洋, 吉瀬 謙二, 弓
場 敏嗣
論文題目: MPIとの比較によるソフトウェアDSMの性能評価
印刷公表の方法および時期: 情報処理学会 研究報告 (ARC-169), pp.157–162,
2007 年 7 月 31 日
153
著者略歴
大島 聡史 (おおしま さとし)
1982 年 2 月 16 日 栃木県に生まれる
2004 年 3 月 電気通信大学 電気通信学部 情報工学科 卒業
2004 年 4 月 電気通信大学 大学院情報システム学研究科 情報ネットワーク学専攻
博士前期課程 入学
2006 年 3 月 同上 修了
2006 年 4 月 電気通信大学 大学院情報システム学研究科 情報ネットワーク学専攻
博士後期課程 入学
2009 年 3 月 同上 修了予定
GPGPU に関する研究に従事.情報処理学会学生会員.