Upload
takeshi-yamamuro
View
387
Download
2
Embed Size (px)
Citation preview
ご注文はランタイム最適化ですか -‐ Program Genera,on and Embedded Compilers -‐
2014/10/11 maropu@dsirnlp#6
ランタイム最適化とは?
• 広義ではprogram実行時にcompileを行うことで実行速度の向上を図る技法(e.g., JavaのHotspot)
• 本日話す内容は「program作成時には不明な入力データの情報を活用してdomain-‐specificな最適化を実行時に行う技法」について紹介
compile
domain-‐specificな 最適化の追加
program genera,on & compile
入力データを活用した programの再構成
開発における一般的な課題
• 生産性と性能は開発言語の抽象度の度合いで反比例するケースが多い
Performance
Prod
uc,vity
Scalaなどの 抽象度の高い言語
Cやアセンブラなどの 抽象度の低い言語
抽象的にデータ構造を扱いつつ最適化したい
• 抽象的にprogramを記述しつつ、ランタイム最適化を活用することで実行時性能を改善
Performance
Prod
uc,vity
Scalaなどの 抽象度の高い言語
Cやアセンブラなどの 抽象度の低い言語
実行時性能改善
具体例:
• 行列-‐ベクトル積
• 行列の粗密や並びで最適なデータ構造は様々 • 行列は入力時に固定され、ベクトルが入力のたびに変動するケースを考える – e.g., PageRankやHMMの計算
具体例: Scalaで行列-‐ベクトル積
def matrix_vector_prod(a: Array[Array[Int]], v: Array[Int]) = { val n = a.length val v1 = new Array[Int](n) for (i <-‐ (0 un,l n)) { for (j <-‐ (0 un,l n)) { v1(i) = v1(i) + a(i)(j) * v(j) } } v1 }
入力のたびに変化しない 静的な行列
入力のたびに変化する 動的なベクトル
LMS: Light-‐weight Modular Staging
• 式の評価をランタイムまで遅延させることを型で表現することで実行時最適化を行うScalaライブラリ
• LLVM*1のようなlow-‐level IRを用いた(Produc,vityを下げる要因になる)煩雑な実装は不要
*1 イリノイ大が開発したコンパイラ基盤、clangのバックエンド hap://llvm.org/
hap://scala-‐lms.github.io/
具体例: Scala w/LMSで行列-‐ベクトル積 def matrix_vector_prod(a0: Array[Array[Int]], v: Rep[Array[Int]]) = { val n = a0.length val a = sta,cData(a0) val v1 = NewArray[Int](n) for (i <-‐ (0 un,l n):Range) { val sparse = a0(i).count(_ != 0) < 3 if (sparse) { for (j <-‐ (0 un,l n):Range) { v1(i) = v1(i) + a(i).apply(j) * v(j) } } else { for (j <-‐ (0 un,l n):Rep[Range]) { v1(i) = v1(i) + a(i).apply(j) * v(j) } } } v1 }
具体例: Scala w/LMSで行列-‐ベクトル積 def matrix_vector_prod(a0: Array[Array[Int]], v: Rep[Array[Int]]) = { val n = a0.length val a = sta,cData(a0) val v1 = NewArray[Int](n) for (i <-‐ (0 un,l n):Range) { val sparse = a0(i).count(_ != 0) < 3 if (sparse) { for (j <-‐ (0 un,l n):Range) { v1(i) = v1(i) + a(i).apply(j) * v(j) } } else { for (j <-‐ (0 un,l n):Rep[Range]) { v1(i) = v1(i) + a(i).apply(j) * v(j) } } } v1 }
行列の粗密で条件分岐
行が素ならunroll処理して 非ゼロ要素のみを計算
行が密ならloop処理
LMSによる拡張構文
具体例: Scala w/LMSで行列-‐ベクトル積
• ランタイム時に生成されるcode snippet def apply(x0:Array[Int]): Array[Int] = { val x2 = new Array[Int](5) val x6 = px6 // sta,c data: Array(1,1,1,1,1) var x4 : Int = 0 val x13 = while (x4 < 5) { val x5 = x2(0) ... val x11 = x2(0) = x10 x4 = x4 + 1 } val x14 = x2(1) ... val x35 = x33 + x21 val x36 = x2(4) = x35 x2 } ※完全なcodeは hap://scala-‐lms.github.io/tutorials/shonan.html参照
行が素ならunroll処理して 非ゼロ要素のみを計算
行が密ならloop処理
具体例: C++ w/LLVMで行列-‐ベクトル積
haps://github.com/maropu/matrix_vector_mul,ply/blob/master/matrix_vector_mul,ply.cc
具体例: C++ w/LLVMで行列-‐ベクトル積
• ランタイム時に生成されるcode snippet
実際どのくらい速くなるのか?
• 評価まで辿り着かなかったので論文[3]から引用 • 行列が素なほど高速(当たり前)
素 密
beaer
その他の応用
• SQLのクエリ処理の実行時最適化 – hap://scala-‐lms.github.io/tutorials/query.html – 処理に必要なスキーマ情報や、式/定数を用いて最適化 – 今年のVLDB’14のBest Paper [2]
• 圧縮データの復元処理の実行時最適化 – 圧縮に対して復元は繰り返し行われることが多い – ある圧縮系列のみを復元するデコーダを実行時に生成
• ...
本日参考にした資料
• [1] LMS: hap://scala-‐lms.github.io/ • [2] Yannis Klonatos et al: Building Efficient Query Engines in a
High-‐Level Language, Proc. of VLDB, 2014 • [3] Tiark Rompf et al.: Op,mizing Data Structures in High-‐
Level Program, Proc. of POPL, 2013 • [4] Tiark Rompf et al.: Lightweight Modular Staging-‐ A
Pragma,c Approach to Run,me Code Genera,on and Compiled DSLs, Proc. of GPCE, 2010