A Dynamic Aspect-oriented System for Data

A Dynamic Aspect-oriented
System for Data-driven Profiling
of OS Kernels
柳澤 佳里
指導教員 千葉 滋
1
OSの性能向上は今でも重要な
課題

性能向上のため、2000年以降でも

スケジューラーの実装を変更


e.g. ULEおよびSMP (FreeBSD), O(1)およびCFS (Linux)
システムコールの実装を変更

e.g. NetBSD、FreeBSDでシステムコールの性能が向上


See Also: http://bulk.fefe.de/scalability/ (syscall ベンチマーク)
スレッド実装を変更

e.g. KSE (FreeBSD)、NPTL (Linux)
・・・などなど
2
カーネルプロファイラの必要性

OSの性能向上にはボトルネックの特定が不可欠


ボトルネックを発見して除去
再コンパイル、再起動なしの調査が必要

ソースコードを書き換える単純な方法では、



現象の再現まで長時間待つ必要がある
開発者がミスしがち
仮想化により、問題点の発見がさらに困難に

関連する部分が増加
3
カーネルプロファイラの要件

自由度


任意の調査点で任意の調査コードが実行できる
調査に応じて調査対象が変化



最初はおおざっぱに調査し、徐々に絞り込む
調査データに基づきログ出力の内容を変更する
抽象度


調査点、調査コードの選択をソースコードレベルの視点で可能
調査の効率を向上


調査点を選びやすいと調査がしやすい
抽象度の高い言語で調査コードがかけると調査がしやすい
4
理想のプロファイリング
Linux カーネルソースコード (fs/attr.c)
int inode_change_ok(…)
{
…
if ((ia_valid & ATTR_UID) && …
attr->ia_uid != inode->i_uid) …
goto error;
挿入
if ((ia_valid & ATTR_GID) &&
…
}
ソースコード中の関連箇所を
自動的に選び出し、変数の値
とタイムスタンプを記録
再コンパイル、再起動
無しでプロファイリングしたい
プロファイリングコード
struct timeval tv;
do_gettimeofday(&tv) ;
print_tv(tv);
printk(“%ld”, inode->i_uid);
5
従来のカーネルプロファイラ (1)

イベントドリブン方式

指定したイベントの発生時にログ取得コードを実行





任意のログ取得コードを記述できるものが存在
調査点の指定は適度に抽象化
作者により決められた調査点でのみ調査
調査しない場合でもオーバーヘッドが発生
例) SystemTAP [Vara ’05]、DTrace [Bryan ’04]


独自言語を用意し、高い抽象度でのプロファイリングコードの
記述が可能
プロファイリング箇所は関数などに決め打ち
6
従来のカーネルプロファイラ (2)

動的コード挿入方式




指定されたコードを指定された箇所に動的に挿入
アドレス指定で任意の箇所にコード挿入可能
コード挿入箇所の指定方法の抽象度が低い
例) Kerninst [Ariel ’99], GILK [David ’02]


Linuxカーネルの任意の箇所に動的にコード挿入可能
アセンブリレベルの抽象度

任意の箇所を指定する際は抽象度が非常に低い
7
Kerninstでの記述例

開発者は次のアドレスの調査が必要:


コードを挿入する機械語のアドレス
記録する変数が格納された場所のアドレス
面倒くさい
サンプルコード: Kerninst を用いてログを取得
kmgr.createInstPointAtAddr(inst_ptr, &insert_point);
kmgr.findModule(“profiler”, &kmod);
kmod.findFunction(“print_log”, &pf);
void print_log() {
hook = kapi_call_expr(pf.getEntryAddr(), args);
…
Kmgr.insertSnippet(hook,insert_point);
__asm__ (“movl %%ebp, %0” : “=r”(ebp));
uid = ((struct inode*)ebp[11])->i_uid;
/* ebp[11] is inode */
…
8
従来手法のまとめ

従来のカーネルプロファイラは要件を満たさない


自由度と抽象度を両立しない
ソースコードレベルの抽象度で任意のコードを書けるシ
ステムが必要
自由度
抽象度
イベントドリブン
×
○
動的コード挿入
○
×
9
動的アスペクト指向を用いた
プロファイリングの提案

プログラム中の主要な実行点を調査点として選択可能


ソースコードレベルの抽象度を提供



選択可能な点: 関数呼び出し、実行、変数の参照など
高級言語で調査コードを記述可能
調査点の選択がソースコードレベルの視点で可能
調査範囲、対象の変更が実行時に可能



必要なときに調査が可能
広いところから絞り込める
無停止なので情報が消失しない

コード挿入後に再現するまで待つ必要がない
10
アスペクト指向 (AOP) とは?

ポイントカット

調査点(ジョインポイント)を
指定
 関数呼び出し


変数アクセスの指定


call/execution
set/get
アドバイス

ポイントカットで指定した実
行点で実行するコード

ジョインポイントの例
n_time
Iptime()
関数実行箇所
{
…
関数呼び出し
getmicrotime(&atv);
t=…
return (htonl(t));
}
変数への参照、代入
11
動的アスペクト指向 (DAOP)

動作中のカーネルに動的にアスペクトを織り込み



無停止に調査コード (アスペクト) を挿入
AOPを使うことで抽象度を確保
実装方法

動的コード書き換え or フックの挿入


e.g. PROSE [Andrei ’02]、Wool [Yoshiki ’03]
仮想マシンの改造

e.g. Steamloom [Christoph ’04]
12
本研究の貢献


カーネルプロファイリング用途でDAOPを使うこと
を提案
(前述)
プロファイリングのためのC言語用DAOPシステム
を開発 (後述)

データを扱うためのポイントカットを提供

構造体メンバーアクセス、データフローへのポイントカット


構造体メンバーのポイントカット: 実装方法を提案
データフローのポイントカット: 新たなポイントカット記述子を提案
13
従来のDAOPは不十分

C言語用DAOPでJava用DAOP並のポイントカット
があればいいのに!

Java用のDAOPはカーネルに使えない



ポイントカットの種類が豊富
多くのOSはC言語で記述
従来のC言語用DAOPは不十分

データのまとまりを扱うポイントカットが不十分

OSカーネルの特性に対応できていない
14
OSカーネルの特性

高度なモジュール化

共通のデータ構造として構造体を複数モジュールで共用




ポリモルフィズム風機構を構造体で実装
データのやりとりに構造体を多用
厳しいコーディング規約で使用する構造体に規則が存在
複数スレッドでデータ処理
コールフローでのプロファイリングが不可
 きちんとしたレイヤー分け
e.g.



即応性が求められるデバイスドライバ (bottom half)
高度な処理をする上位レイヤー (top half)
15
データを扱うポイントカットの
プロファイリングにおける必要性

カーネルの特性をうまく利用

構造体メンバーアクセスは大規模Cプログラムで使用



関数間でのデータの受け渡しに利用
ポリモルフィズムの実現に利用
効率的


データを使っているモジュールを一発で選択
cf. 関数を列挙する方法では、

調査するサブシステムについての詳細な知識が必要


過不足なく関数を選択するため
関数のシンボルを残すために最適化禁止が必須

Inline関数への対応が必要
 現実のOSカーネルは最適化オプションありでコンパイル
16
従来のC言語用DAOP

データを扱うポイントカットが不足

TOSKANA [Michael ’05]、TinyC2 [Charles ’03]、
DAC++ [Sufyan ’05]


Arachne [Remi ’05]


関数実行を選択するポイントカットのみ
関数呼び出し、返値、グローバル変数を選択するポイントカットのみ
μDyner [Marc ’03]


ジョインポイントとなる関数をアノテーションで指定
同様の方法でジョインポイントが増えるが、イベントドリブン方式のプロ
ファイラーと同じ問題を内包
17
本研究で開発したDAOPの機構

データ利用箇所を選択するポイントカットを提案

(1) accessポイントカット [GPCE ’06](点を指定)



構造体メンバーへのアクセスをポイントカット
OSの特性として、構造体を関連モジュールで共用
データフローを選択するポイントカットを提案

(2) xflowポイントカット [PRO ’07](点から線に)


特定のデータを持つ構造体インスタンスをポイントカット
マルチスレッド環境で処理フローの追跡が可能
18
(1) Access pointcut and KLASY
19
KLASY:
Kernel Level Aspect-oriented SYstem

Access pointcut

構造体メンバーへのアクセスをポイントカット


OSカーネルの関連箇所をまたいで選択
Source-based binary-level dynamic weaving

コンパイル時に得られる豊富な情報を実行時に利用



コンパイラを拡張し、出力するシンボル情報を拡張
シンボル情報を用いて構造体メンバーへのアクセス、ローカ
ル変数などの情報を取得
Kerninstを用いてアドバイスコードを挿入
20
KLASYのアスペクト
アスペクト
Linux カーネルコード (fs/attr.c)
<aspect>
int inode_change_ok(…)
<import>linux/time.h</import>
{
…
pointcut
<advice><pointcut>
if ((ia_valid & ATTR_UID) && …
access(inode.i_uid) AND
attr->ia_uid != inode->i_uid) …
within_function(inode_change_ok)
goto error;
選択
AND target(inode_value)
</pointcut>
if ((ia_valid & ATTR_GID) &&
advice
<before>
…
struct inode *i = inode_value;
}
struct timeval tv;
do_gettimeofday(&amp;tv);
print(i-&gt;i_uid, tv.tv_sec, tv.tv_usec);
</before>
</advice>
</aspect>
21
KLASYの対応する
主なポイントカット、アドバイス

ポイントカット

access



execution


本研究で提案
構造体メンバーアクセスを選択
関数実行を選択
アドバイス

before


選択された点の前でプロファイリングコードを実行
after

選択された点の後でプロファイリングコードを実行
22
実行時コンテキストの取得に使う
ポイントカット

ポイントカット記述子

target


local_var


accessポイントカットで選択したメンバーを持つ構造体変数への
参照を取得
accessポイントカットで選択した箇所でローカル変数への参照を
取得
argument

executionポイントカットで選択した関数の引数への
参照を取得
23
KLASYの実装

Source-based binary-level dynamic weaving

GNU C コンパイラ(gcc)を拡張

生成した拡張シンボル情報を用い:



Kerninstをバックエンドに利用


構造体メンバーへのアクセスをポイントカット可能
実行時コンテキスト(変数のアドレス)を取得可能
動的織り込みを実現
C言語でアドバイスを記述


ソースレベルの視点で記述可能
XML風のタグで囲まれている
24
処理の流れ
OS
ソースコード
アスペクト
アスペクトコンパイラー
拡張シンボル情
報
KLASY
gcc
ポイントカット
insmod
OSカーネル
コンパイル済み
アドバイス
ウィーバー
OS カーネル
フック
本体
25
処理の流れ
OS
ソースコード
アスペクト
アスペクトコンパイラー
拡張シンボル情
報
KLASY
gcc
ポイントカット
insmod
OSカーネル
コンパイル済み
アドバイス
ウィーバー
OS カーネル
フック
本体
26
KLASY gcc

KLASY gccは次のシンボル情報を収集:

構造体メンバーアクセスのあるファイル名、行番号



コンパイラーのパーザーを拡張
従来のgccではこの情報は消失
各行の先頭命令のあるアドレス


コンパイル時にデバッグオプション(-g)を利用
構造体メンバーアクセスのポイントカットにこれも必要
27
処理の流れ
OS
ソースコード
アスペクト
アスペクトコンパイラー
拡張シンボル情
報
KLASY
gcc
ポイントカット
insmod
OSカーネル
コンパイル済み
アドバイス
ウィーバー
OS カーネル
フック
本体
28
ウィーバー

Kerninstを用いポイントカットで選択した点に
フック挿入

フック


アドバイスボディを呼び出すためのコード
フック挿入アドレスの取得方法

構造体メンバーアクセス

ファイル名、行番号
 行の先頭アドレス
拡張シンボル情
報を利用
29
アンウィーブ

KLASYでは実行時にOSカーネルから織り込んだ
アスペクトを削除可能

プロファイリングには重要な機能




一般に利用者は様々なアスペクトを試用
観察効果を避けるため不要なアスペクトの削除は必要
利用者はわかりやすい名前でアスペクトを指定可能
Kerninstを用いてウィーバーの入れたフックを消去
30
アスペクト例における
実行時コンテキストの取得
アスペクト
Linux カーネルソースコード (fs/attr.c)
<aspect>
int inode_change_ok(…)
<import>linux/time.h</import>
{
<advice><pointcut> ポイントカット …
if ((ia_valid & ATTR_UID) && …
access(inode.i_uid) AND
attr->ia_uid != inode->i_uid) …
within_function(inode_change_ok)
goto error;
AND target(inode_value)
selected
</pointcut>
if ((ia_valid
& ATTR_GID) &&
ローカル変数を取得し、
アドバイス
<before>
…
アドバイス内で利用
struct inode *i = inode_value;
}
struct timeval tv;
do_gettimeofday(&amp;tv);
print(i-&gt;i_uid, tv.tv_sec, tv.tv_usec);
</before>
</advice>
</aspect>
31
実行時コンテキストの取得の実装

ウィーバーとKLASY gccの連携により実現

KLASY gccにて構造体への参照方法を保存



ローカル変数から目的の構造体への参照に至る方法を保存
例)
inode.length
→
&inode
inode_ptr->length →
inode_ptr
ウィーバーにて参照を得るトランポリンコードを作成

ローカル変数の格納場所をデバッグ情報をから取得


Gccの作成したデバッグ情報を利用
保存された方法で構造体への参照を得、アドバイスに渡す
32
実験

UnixBenchによるベンチマーク

Linux: 通常gccでコンパイルしたカーネル


-fomit-frame-pointerオプションあり
KLASY: KLASY gccでコンパイルしたカーネル

実行時コンテキスト取得のため、-fomit-frame-pointerオプション
使用不可



デバッグ情報の示す変数位置と実位置がずれるため
ほぼ-fomit-frame-pointer禁止によるオーバーヘッドを測定
実験環境
CPU: AthlonXP™ 1800+, Mem: 1GB, Linux 2.6.10
Kerninst 2.1.1, gcc 3.3.3, Intel Ethernet PRO/1000
33
実験結果
現実的なオーバーヘッドであることを確認
1000
800
600
400
200
Linux
ex
ec
co l
nt
ex
t
pi
pe
sy
sc
all
0
y2
re
g
dhry2reg: drystone
syscall: システムコール
pipe: pipeシステムコール
execl: execlシステムコール
context: コンテキストスイッチ
dh
r

KLASY
34
ケーススタディ:
ネットワークI/Oサブシステムの調査

目的


過負荷におけるLinuxネットワークサブシステムの
性能ボトルネックを発見
Sk_buff構造体へのアクセスをトレース

Sk_buff構造体はLinuxにてネットワークサブシステムでバッ
ファとして利用


Sk_buffのトレースによりネットワークサブシステムの挙動を把握
KLASYの実行時コンテキスト取得機能を利用


個々のパケットを識別するため
無関係なパケットを無視するため
35
調査に用いたアスペクト
ワイルドカード
<aspect><advice>
<pointcut>
access(sk_buff.%) AND target(arg0)
</pointcut>
<before>
struct sk_buff *skb = arg0;
skb->protocol
unsigned long timestamp;
if (skb-&gt;protocol != ETH_P_ARP) {
STORE_DATA($pc$);
プログラムカウンタ、
STORE_DATA(skb); ARPパケットを無視
sk_buff出現位置、
DO_RDTSC(timestamp);
タイムスタンプを保存
STORE_DATA(timestamp);
}
</before>
</advice></aspect>
36
トレース結果

プロセススケジューリングがボトルネックと判明

Skb_copy_datagram_iovec関数はプロセスの発行
したシステムコールから呼び出されるので
pa
cke
pa
cke
0.1
Time scale of packet arrival
差が大きい
t2
t1
1
10
Elapsed time
ip_rcv
netif_receive_skb
tcp_v4_rcv
1000_clean_rx_irq
ip_rcv_finish
100
1000
__kfree_skb
skb_copy_datagram_iovec
tcp_rcv_established
tcp_v4_do_rcv
37
ケーススタディでの
accessポイントカットの有用性

Sk_buff構造体の全メンバーをaccessポイントカット


Linuxネットワークサブシステムの挙動を把握
もし、executionポイントカットでやるとしたら…

ネットワークサブシステムについての詳細な知識が必要



過不足なく関数を選択するため
本ケーススタディでは76箇所(関数21個)にてログ取得
最適化禁止が必須

Inline関数への対応が必要


現実と大幅に異なる
 OSカーネルは通常最適化オプションつきでコンパイルされる
 例) Linux カーネルは-Os最適化オプションでコンパイル
本ケーススタディではstatic inline関数6箇所にてログ取得
38
第1部のまとめ

accessポイントカット

Source-based binary-level dynamic weaving



構造体メンバーへのアクセスをポイントカットで選択可能
実行時コンテキストを取得可能
ネットワークI/Oサブシステムのプロファイリングに
accessポイントカットが有用であると確認

性能ボトルネックがプロセススケジューリングにあると判明
39
(2) Xflow pointcut and XenLASY
XenLASY = KLASY + xflow + VM対応
40
I/Oフローの追跡が大切

I/Oフローとは



I/Oを発行してデバイスが送出する流れ
デバイスで受信しアプリケーションが受け取る流れ
個別のデータの動き (フロー) の追跡が必要


データがドメインUやドメイン0でどう処理されるかを知りたい
複数のドメインがI/Oした場合に、区別して追跡したい


余計なフローは取りたくない
個々のフローはフロー識別子 (ID) が必要

一つ一つのデータの流れを区別するため
41
単純なフロー追跡では不十分

コールフロー


関数呼び出しの流れを追跡
実行スレッドが変わると追跡不可



ドメイン間の追跡が不可能
トップハーフ / ボトムハーフの追跡が不可能
単純なデータフロー


データのポインタを追跡
データ形式が変化すると追跡不可


ドメイン間ではデータ形式が変化し、追跡不可
データの複製、分割すると追跡不可
42
VMでは特にI/Oフローが重要

データ処理に複数のOSが関与


I/Oがドメイン0を通る
複数のVMのI/Oが競合
例) XenのI/O処理 ドメイン0
ドメインU
OS
実ドライバ
OS
仮想ドライバ
仮想ドライバ
仮想マシンモニタ (VMM)
ハードウェア
43
XenLASY


Xen上のI/O処理をプロファイリングをするための
アスペクト指向システム
xflowポイントカット

Xen上のデータフローを選択するポイントカット

指定した種類のフローに指定したデータが入っている時を選択


文法: xflow(フロー名, データへのポインタ, フローID)
なお、フローIDは省略可
追跡すべきデータの流れをきめ細かく指定可能



開始点、中継点、終了点を指定
データ形式の変化、分割などにも対処
余計なデータが含まれないようにできる
44
KLASYを拡張

KLASY


カーネル用動的アスペクト指向システム
ソースコードレベルの情報を実行時の織り込みで利用




を拡張して開発
KLASYとは、


[Yanagisawa ’06]
accessポイントカットを実現
 構造体メンバーへのアクセスをポイントカット
Source-based binary-level dynamic weaving
Xenに対応
xflowを扱えるよう言語拡張
@ドメイン名を使えるよう言語拡張
45
XenLASYのアスペクト例
accessポイントカットで選択
アスペクト
<aspect>
id1
データフロー (xflow)
<import>linux/time.h</import>
id2
<advice><pointcut>
DomainU
Domain0
access(sk_buff.%) AND target(skb) AND
xflow(netflow, skb, id)
</pointcut>
<before>
long long tsc;
sk_buff構造体インスタンスが
DO_RDTSC(tsc);
netflowのデータだった場合に
pc、時間、フローidをログ出力
STORE_DATA3($pc$, tsc, id);
</before>
netflow: ネットワークI/Oの
</advice>
フロー
</aspect>
46
xflowポイントカットの定義
<xflow name=“netflow”>

<start><pointcut>
access(sk_buff.data) AND
within_function(alloc_skb_from_cache)
</pointcut></start>

<transit><pointcut>
access(sk_buff.head) AND
within_function(skb_clone)
</pointcut>
<move from=“skb” to=“n” />
</transit>
netflow

start: 開始点


</xflow>
データフローの開始点を指定
transit: 中継点

データ形式が変わる場合


<quit><pointcut>
access(sk_buff.%) AND
within_function(__kfree_skb)
</pointcut></quit>
Xen上のネットワークI/O処理フ
ロー

skb_cloneは複製を作成
ドメイン間の場合
quit: 終了点
47
start/quit (開始点/終了点)
<start><pointcut>
access(sk_buff.data) AND
within_function(alloc_skb_from_cache)
</pointcut></start>
例
<start><pointcut>…</pointcut>
<select local_var=“data” />
</start>


構造体インスタンスからIDを
引けるよう登録、削除
構造体インスタンスの指定


<start><pointcut>…</pointcut>
<action>
int id = new_flowid();
…
</action>
</start>

省略時はaccessポイントカットで
選択した構造体のインスタンス
を選択
selectで任意の変数も指定可
DB登録/削除処理は自動で設
定

任意のコードを指定する場合は
actionを利用
48
transit (中継点)
<transit><pointcut>
access(sk_buff.head) AND
within_function(skb_clone)
</pointcut>
<move from=“skb” to=“n” />
</transit>

moveで対応付けを指示



例
<transit><pointcut>
…
</pointcut>
<copy from=“skb” to=“n” />
</transit>

skb: フローID格納元
n: フローID格納先
skbを鍵としてフローIDが
引けないようエントリを抹
消
エントリを保持するcopyも
用意
49
ドメインをまたがるtransit定義

xin_move、xout_move要素を用意

ドメインをまたがるとデータのアドレスからフローID
を引けない



ドメイン間ではアドレス空間が違う
ドメイン間ではデータベースを共有していない
フローIDを送信先ドメインに伝搬

ドメイン間で渡されるヘッダの空き領域にIDを格納
ヘッダ
ドメイン0
DomU
実データ
フローIDを格納
50
ドメイン間transitの例
<transit><pointcut>
access(netif_tx_request.flags) AND
within_file(drivers/../netfront.c@linU)
</pointcut>
<xin_move name=“netin” from=“skb” to=“tx”>
<field name=“flags” offset=“4” size=“12” />
</xin_move>
</transit>


linUからlin0にフローIDを
伝搬
xin_move

skbのフローIDをtxに格納


<transit><pointcut>
access(netif_tx_request.flags) AND
within_file(drivers/../netback.c@lin0)
</pointcut>
<xout_move name=“netin” from=”tx” to=“skb” />

</transit>
flagsメンバーの下位4ビット
目から12ビットを使用
xout_move

xin_moveの逆処理でフロー
IDを取得し、skbに割当

対象xin_moveはnameで選
択
@ドメイン名で選択するドメ
インを指定
tx->flags
12bit
4bit
51
xflowの実装: start/quitの変換
<start><pointcut>
access(sk_buff.data) AND
within_function(alloc_skb_from_cache)
</pointcut></start>
<pointcut>
access(sk_buff.data) AND target(skb)
AND within_function(alloc_skb_from_cache)
</pointcut>
<before>
id = get_new_flowid();
register_flowid(netflow, id, skb);
</before>
targetポイントカットを追加
構造体インスタンスへの参照を取得
DBに参照を鍵としてIDを
取り出せるよう登録
•alloc_skb_from_cache
でskbから新規フローID
を引けるようDBに登録
quitも同様
52
xflowの実装: transitの変換
<pointcut>
access(sk_buff.head)
AND within_function(skb_clone)
AND local_var(skb, skbp)
AND local_var(n, np)
</pointcut>
<before>
void *skb = *((void **)skbp);
void *n = *((void **)np);
int id = get_flowid(netflow, skb);
if (id != 0) {
register_flowid(netflow, id, n);
remove_flowid(netflow, skb);}
</before>
<transit><pointcut>
access(sk_buff.head) AND
within_function(skb_clone)
</pointcut>
<move from=“skb” to=“n” />
</transit>
•local_varポイントカットでロー
カル変数への参照取得
skbに割り当てら
れていたフローID •skb_cloneにてskbに割り当てら
をnに割り当てる れていたフローIDをnに割り当て
53
xflowの実装:
ドメイン間transitの変換
<transit><pointcut>
access(netif_tx_request.flags) AND
within_file(drivers/../netfront.c@linU)
</pointcut>
<xin_move name=“netin” from=“skb” to=“tx” />
<field name=“flags” offset=“4” size=“12” />
</xin_move>
</transit>
<pointcut>
access(netif_tx_request.flags) AND
within_file(drivers/.../netfront.c@linU)
AND local_var(tx, txp)
AND local_var(skb, skbp)
</pointcut>
<after>
struct netif_tx_request *tx = txp;
void *skb = *((void **)skbp);
id = get_flowid(skb);
ポインタに対応づ
if (id != 0) {
けられたフローID
tx-&gt;flags |= id &lt;&lt; 4; をヘッダに格納
id &gt;&gt; 12;
}
remove_flowid(netflow, skb);
</after>
local_varポイントカットでロー
カル変数への参照取得
•XenのネットワークI/OはドメインU
でnetif_tx_request構造体にヘッダ
を格納
送信先でフローIDを
受け取るコードは割愛
54
実装: KerninstのXen対応


アスペクトの織り込みにKerninst [Tamches ’99]を使用
割り込みテーブル読み込みを除去


ブレークポイントトラップ処理関数をエクスポートし、Kerninstか
ら直接参照
割り込みテーブル読み込みは特権命令


ドメインUやドメイン0から読み込めない
特権レベル判定を変更


Xen上ドメインでの実行に対応
Kerninstはring0でカーネルが動作していると仮定
55
マイクロベンチマーク

目的


xflowのバックエンド関数の
オーバーヘッドを調査
実験方法



各関数を2000回呼び出し、平均
を計算
実験環境


CPU: AMD Athlon™ 64 3500+
メモリー: 2GB


ドメイン0: 256MB
ドメインU: 128MB
結果
関数名
実行時間(ナノ秒)
get_new_flowid
3 ± 0.0
空要素
get_flowid
9 ± 0.0
register_flowid
33 ± 4.0
get_flowid
15 ± 1.0
remove_flowid
32 ± 2.0
ドメイン0で実施
バックエンド関数のオーバーヘッドは低い
56
ネットワークI/Oのボトルネック

目的


ドメインUからドメイン0までの処理の流れ、ボトルネックを
調査
xflowを用いて、ドメインUからドメイン0までのデータ
フローを調査

sk_buff構造体のメンバーにアクセスがあった箇所でフ
ローIDを取得し、時間とともに記録

例に出したアスペクトを使用
57
実験結果

処理の流れがわかった


skb_clone関数でできた複製も追跡可能
 TCP再送処理のためにTCP層で実行され、ドライバーは複製を利用
ボトルネックはドメイン0の内部
ボトムハーフ → トップハーフのところ

netif_receive_skbはトップハーフの処理割り当て関数
送信時のパケットの流れ
フロ
ー
0
500
1000
network_start_xmit
tcp_sendmsg
alloc_skb_from_cache
1500
2000
2500
経過時間 (μ秒)
netif_rx
netbk_fill_flags
3000
FreeTxDescriptors
3500
4000
__br_forward
netif_receive_skb SkGeXmit
58
xflowによるオーバーヘッドの削減

目的


方法



xflowを使うことでプロファイルのオーバーヘッドを削減できるか
調査
上のケーススタディのアスペクトでxflowありとなしを比較
ApacheBenchを300リクエスト、10並列で実行
メモリー使用量
結果
ドメイン0
ドメインU
性能
(req/s)
xflowあり
1.6MB
10.6MB
382
xflowなし
13.6MB
15.7MB
382
約60%のメモリーを削減
59
関連研究

Dflow pointcut [Masuhara ’03]



DJcutter [Nishizawa ’04]、DAC++ [Almajali ’05]



データの流れを選択するポイントカット
コンパイル時にdflowのためのコードを織り込み
分散環境に対応したアスペクト指向システム
ユーザーランドのアプリケーションを対象とする
Causeway [Chanda ’05]


メタデータを伝搬させ処理の流れを追跡
FreeBSDのネットワークI/Oコードを改造して実装
60
第2部のまとめ

xflowポイントカット




データフロー追跡をアスペクトとして容易に記述可能
複数ドメインに自動でアスペクトを織り込み
KLASYを拡張して実装
ケーススタディ


ネットワークI/Oのボトルネックがドメイン0の処理にあることを発見
フロー追跡機能により調査に必要なメモリー使用量の削減を確認
61
本発表のまとめ


DAOPをプロファイリングに使うことを提案
カーネルプロファイリングのための実用的な
DAOPシステムを提案

データを扱うポイントカットを提供

(1) accessポイントカット


(2) xflowポイントカット


データ利用箇所を選択するポイントカット
データフローを選択するポイントカット
従来のC言語用DAOPで不足
62
従来手法との比較
自由度
抽象度
イベントドリブン
×
○
動的コード挿入
○
×
本研究
○
○
63
今後の展開

他のアーキテクチャでの実装


フローの分割への対処


フロー分割後のフローIDの適切な割当方法の検討
VMM内部へのアスペクトの織り込み


x86以外のアーキテクチャで本方式が使えるかを検証
現在はOS内部だけなのでVMM内部にも織り込み、網羅的な調査を行いたい
統計的手法を用いたプロファイラとの連携

DAOPによるプロファイリングは正確な実行点を選択



突発的な変化に強いが外乱に弱い
統計的手法でならす
UIとの連携


行単位でのプロファイリングコードの挿入、削除
開発の効率をさらに上昇
64
既発表論文

Accessポイントカット



“OSカーネル用アスペクト指向システム KLASY”,情報処理学会
論文誌:プログラミング, vol. 48, no. SIG 10 (PRO33)
“A Dynamic Aspect-oriented System for OS Kernels”,
GPCE’06
Xflowポイントカット

“XenLASY: XenのI/O処理を追跡するためのアスペクト指向プ
ロファイラ”,情報処理学会論文誌:プログラミング, PRO35
掲載予定
65
業績リスト

査読付き論文




ワークショップ論文








滝澤裕二,光来健一,千葉滋,柳澤佳里: SAccessor: デスクトップPCのための安全なファイルアクセス制御システム,第19回コンピュータシステム・シンポ
ジウム (ComSys 2007), 東京都 東京ファッションタウン, 2007年11月27日
今吉竜之介, 柳澤佳里, 千葉滋: アスペクト指向言語のための独立性の高いパッケージシステム, 第11回 プログラミングおよび応用のシステムに関す
るワークショップ (SPA 2007), 愛知県 三谷温泉, 2007 年 9 月 3日 - 5日
滝澤裕二、光来健一、柳澤佳里、千葉滋: OSが乗っ取られた場合にも機能するファイルアクセス制御システム, 第10回 プログラミングおよび応用のシ
ステムに関するワークショップ (SPA X), 新潟県 越後湯沢温泉, 2006 年 8 月 28 - 30 日
柳澤 佳里, 光来 健一, 千葉 滋: アスペクト指向を用いたカーネルプロファイラ, 第99回 システムソフトウェアとオペレーティングシステム研究会, 沖縄県
ホテルムーンビーチ, 2005年 5月25-27日, 情報処理学会研究報告 2005-OS-99, pp.149-156
Yoshisato YANAGISAWA, Shigeru CHIBA, Kenichi KOURAI: A Source-level Kernel Profiler based on Dynamic Aspect-Orientation, Dynamic
Aspects Workshop (DAW05) Chicago, USA. March 15th, 2005 (held in conjunction with AOSD 2005)
柳澤佳里、光来健一、千葉滋: 通信処理のカーネル内競合を検出するアスペクト指向カーネルレベルロガー, 並列/分散/協調処理に関するサマー・
ワークショップ (SwoPP青森2004) 情報処理学会研究報告 2004-OS-97, pp.33-40, 2004年8月.
柳澤佳里、千葉滋: 他のプロセスに与える影響が少ない実行時ミラーリングシステム,並列/分散/協調処理に関するサマー・ワークショップ(SWoPP '03)
第94回OS研究会,松江、pp.83-89、2003年8月.
口頭発表(抜粋)



柳澤佳里, 光来健一, 千葉滋: XenLASY: XenのI/O処理を追跡するためのアスペクト指向プロファイラ, 第65回プログラミング研究会 (PRO-2007-2),
北海道 旭川市大雪クリスタルホール, 2007年8月1日 - 3日 (情報処理学会論文誌:プログラミング(PRO35)掲載予定)
柳澤佳里, 光来健一, 千葉滋, 石川零: OSカーネル用アスペクト指向システム KLASY, 情報処理学会論文誌:プログラミング、vol. 48, no. SIG 10
(PRO33)、pp.176-188、June 2007. (平成19年度コンピュータサイエンス領域奨励賞受賞)
Yoshisato Yanagisawa, Kenichi Kourai, Shigeru Chiba, and Rei Ishikawa: A Dynamic Aspect-oriented System for OS Kernels, In Proc. of the 5th
Int'l Conf. on Generative Programming and Component Engineering (GPCE'06), pp.69-78. Portland, Oregon, USA. October 22-26, 2006.
柳澤佳里, 光来健一, 千葉滋, 石川零:カーネル用アスペクト指向システム KLAS,第9回 プログラミングおよび応用のシステムに関するワークショップ
(SPA 2006), 栃木県 塩原温泉, 2006 年 3 月 5 - 7 日. (ポスター・デモセッション最優秀発表賞受賞)
Yoshisato YANAGISAWA, Shigeru CHIBA, Kenichi KOURAI: KLAS: Kernel Level Aspect-oriented System – Source-based Binary-level Dynamic
Weaving -, AOSD 2005 (poster), Chicago, Illinois, USA, March 16th, 2005. (Best Poster Award)
その他

第11回 プログラミングおよび応用のシステムに関するワークショップ(SPA 2007) 実行副委員長
66