JavaScript is required to for searching.
ナビゲーションリンクをスキップ
印刷ビューの終了
Oracle Solaris Studio 12.3: パフォーマンスアナライザ     Oracle Solaris Studio 12.3 Information Library (日本語)
search filter icon
search icon

ドキュメントの情報

はじめに

1.  パフォーマンスアナライザの概要

2.  パフォーマンスデータ

3.  パフォーマンスデータの収集

4.  パフォーマンスアナライザツール

5.   er_print コマンド行パフォーマンス解析ツール

6.  パフォーマンスアナライザとそのデータについて

7.  注釈付きソースと逆アセンブリデータについて

ツールがソースコードを見つけるしくみ

注釈付きソースコード

パフォーマンスアナライザの「ソース」タブのレイアウト

元のソース行の識別

「ソース」タブのインデックス行

コンパイラのコメント

共通部分式の除去

ループの最適化

関数のインライン化

並列化

注釈付きソースの特別な行

ソース行メトリック

ソース行メトリックの解釈

メトリックの形式

注釈付き逆アセンブリコード

注釈付き逆アセンブリの解釈

命令発行時のグループ化

命令発行遅延

ハードウェアカウンタオーバーフローの関連付け

「ソース」タブ、「逆アセンブリ」タブ、「PC」タブの特別な行

アウトライン関数

コンパイラ生成の本体関数

動的にコンパイルされる関数

Java ネイティブ関数

クローン生成関数

静的関数

包括的メトリック

分岐先

ストア命令とロード命令の注釈

実験なしのソース/逆アセンブリの表示

-func

-{source,src} item tag

-{disasm,dis} item tag

-{cc,scc,dcc} com-spec

-outfile filename

-V

8.  実験の操作

9.  カーネルプロファイリング

索引

注釈付き逆アセンブリコード

注釈付き逆アセンブリは、関数またはオブジェクトモジュールの命令のアセンブリコードのリストを提供します。このリストには、各命令に関連付けられているパフォーマンスメトリックスが含まれています。注釈付き逆アセンブリは複数の方法で表示することができ、どの方法で表示されるかは、行番号のマッピング情報およびソースファイルが存在するかどうか、また注釈付き逆アセンブリが要求されている関数のオブジェクトモジュールが既知かどうかによって決まります。

逆アセンブリコードの各命令には、注釈として次の情報が付けられます。

呼び出しアドレスの解決が可能な場合、それらのアドレスは関数名などのシンボルに変換されます。メトリックは、命令行について表示されます。対応する表示方式が設定されていれば、インタリーブされるソースコードについても表示することができます。表示可能なメトリック値は、表 7-1 に示されているソースコードの注釈で説明しているとおりです。

複数の場所に #include されるコードの逆アセンブリリストには、コードが #include されるたびに逆アセンブリ命令が 1 回現れます。ソースコードは初回のみインタリーブされ、逆アセンブリコードの繰り返されるブロックはファイルに表示されます。たとえば、inc_body.h というヘッダーに定義されているコードブロックが、inc_bodyinc_entryinc_middle、および inc_exit という 4 つの関数によって #include されている場合、逆アセンブリ命令のブロックは inc_body.h の逆アセンブリリストに 4 回現れますが、ソースコードは逆アセンブリ命令の 4 つのブロックの最初のもののみインタリーブされます。「ソース」タブに切り替えると、逆アセンブリコードの繰り返しにそれぞれ対応するインデックス行が表示されます。

インデックス行は「逆アセンブリ」タブ内に表示される場合があります。「ソース」タブの場合とは異なり、これらのインデックス行を直接ナビゲーションの目的に使用することはできません。ただし、インデックス行の直下の命令の 1 つにカーソルを置いて「ソース」タブを選択すると、インデックス行で参照されているファイルに移動できます。

ほかのファイルのコードを #include するファイルでは、ソースコードのインタリーブなしで、インクルードされたコードが逆アセンブリ命令として表示されます。ただし、これらの命令の 1 つにカーソルを置いて「ソース」タブを選択すると、#include されているコードを含むファイルが開かれます。このファイルを表示した状態で「逆アセンブリ」タブを選択すると、インタリーブされたソースコードとともに逆アセンブリコードが表示されます。

インライン関数の場合はソースコードと逆アセンブリコードをインタリーブできますが、マクロの場合はできません。

コードが最適化されていない場合、各命令の行番号は逐次順であり、ソース行と逆アセンブリされた命令は予想どおりにインタリーブされます。最適化されている場合は、あとの行の命令が前の行の命令よりも前に表示されることがあります。アナライザのインタリーブアルゴリズムでは、命令が行 N にあると表示される場合は、常に、行 N とその行までのすべてのソース行がその命令の前に挿入されます。最適化を行なった結果、制御転送命令とその遅延スロット命令の間にソースコードが現れます。ソース行の N に関連するコンパイラのコメントは、その行の直前に挿入されます。

注釈付き逆アセンブリの解釈

注釈付き逆アセンブリを解釈するのは簡単ではありません。 リーフ PC とは、次に実行する命令のアドレスです。このため、命令の属性メトリックは、命令の実行待ちに費やされた時間とみなされます。ただし、命令の実行は必ずしも順に行われるわけではなく、呼び出しスタックの記録に遅延があることもあります。注釈付き逆アセンブリコードを利用するには、実験の記録先であるハードウェアと、そのハードウェアが命令を読み込み、実行する方法を理解しておいてください。

次では、注釈付き逆アセンブリコードを解釈する上での問題点をいくつか説明します。

命令発行時のグループ化

命令は、命令発行グループと呼ばれるグループ単位で読み込まれ、発行されます。グループに含まれる命令は、ハードウェア、命令の種類、すでに実行された命令、およびほかの命令またはレジスタの依存関係によって異なります。その結果、ある命令が常に前の命令と同じクロックで実行され、次に実行される命令として現れない場合、その命令の出現回数は実際よりも少なくなることを意味します。また、呼び出しスタックが記録されるときに、「次」に実行する命令が複数存在する可能性もあります。

命令発行規則はプロセッサの種類ごとに異なり、キャッシュ行内の命令位置合わせに依存します。リンカーはキャッシュ行よりも高い精度による命令位置合わせを強制的に行うので、関連性がないと思える関数を変更すると、異なる命令の位置合わせが生じる可能性があります。位置合わせが異なると、パフォーマンスの向上や劣化が発生することがあります。

次の例では、同じ関数をわずかに異なる状況でコンパイルしてリンクしています。2 つの出力例は、er_print ユーティリティーからの注釈付き逆アセンブリリストを示しています。2 つの例の命令は同じですが、位置合わせが異なっています。

次の出力例の命令位置合わせでは、cmpbl,a の 2 つの命令を別々のキャッシュ行にマップし、この 2 つの命令の実行待ちに多大な時間が消費されます。

   Excl.     Incl.
User CPU  User CPU
    sec.      sec.
                             1. static int
                             2. ifunc()
                             3. {
                             4.     int i;
                             5.
                             6.     for (i=0; i<10000; i++)
                                <function: ifunc>
   0.010     0.010              [ 6]    1066c:  clr         %o0
   0.        0.                 [ 6]    10670:  sethi       %hi(0x2400), %o5
   0.        0.                 [ 6]    10674:  inc         784, %o5
                             7.         i++;
   0.        0.                 [ 7]    10678:  inc         2, %o0
## 1.360     1.360              [ 7]    1067c:  cmp         %o0, %o5
## 1.510     1.510              [ 7]    10680:  bl,a        0x1067c
   0.        0.                 [ 7]    10684:  inc         2, %o0
   0.        0.                 [ 7]    10688:  retl
   0.        0.                 [ 7]    1068c:  nop
                             8.     return i;
                             9. }

次の出力例の命令位置合わせでは、cmpbl,a の 2 つの命令を 1 つのキャッシュ行にマップし、この 2 つの命令の内 1 つの命令のみの実行待ちに多大な時間が消費されます。

   Excl.     Incl.
User CPU  User CPU
    sec.      sec.
                             1. static int
                             2. ifunc()
                             3. {
                             4.     int i;
                             5.
                             6.     for (i=0; i<10000; i++)
                                <function: ifunc>
   0.        0.                 [ 6]    10684:  clr         %o0
   0.        0.                 [ 6]    10688:  sethi       %hi(0x2400), %o5
   0.        0.                 [ 6]    1068c:  inc         784, %o5
                             7.         i++;
   0.        0.                 [ 7]    10690:  inc         2, %o0
## 1.440     1.440              [ 7]    10694:  cmp         %o0, %o5
   0.        0.                 [ 7]    10698:  bl,a        0x10694
   0.        0.                 [ 7]    1069c:  inc         2, %o0
   0.        0.                 [ 7]    106a0:  retl
   0.        0.                 [ 7]    106a4:  nop
                             8.     return i;
                             9. }

命令発行遅延

特定のリーフ PC の示す命令の発行前に遅延があると、そのリーフ PC の出現回数が多くなることがあります。これは、次のケースを初めとして、さまざまな多くの理由で発生する可能性があります。

ハードウェアカウンタオーバーフローの関連付け

一部のプラットフォームでの TLB ミスを除き、オーバーフローにより生成される割り込みの処理に要する時間などのいくつかの理由から、ハードウェアカウンタのオーバーフローイベントの呼び出しスタックは、オーバーフローが発生した時点ではなく命令シーケンスの後ろの方で記録されます。 サイクルおよび発行された命令などの一部のカウンタの場合、この遅延は問題になりません。しかし、キャッシュミスや浮動小数点演算をカウントするようなカウンタの場合は、そのオーバーフローの原因となっているものとは別の命令がメトリックの原因とされます。多くの場合、イベントを発生させた PC は、記録されている PC の数命令前のもので、逆アセンブリリストでその命令を正確に特定できます。ただし、この命令範囲内に分岐先がある場合、イベントを引き起こした PC に対 応する命令を見分けることは難しいか、または不可能です。メモリーアクセスイベントをカウントするハードウェアカウンタについて、コレクタはカウンタ名の前に「+」が付いている場合、イベントを引き起こした PC を検索します。この方法で記録されたデータは、データ空間プロファイリングをサポートします。詳細は、「データ領域プロファイリングとメモリー領域プロファイリング」および -h counter_definition_1...[, counter_definition_n]を参照してください。

precise キーワードでラベル付けされたカウンタを持つプロセッサを備えたシステムでは、バイナリの特殊コンパイルなしでメモリー領域プロファイリングを行うことができます。たとえば、SPARC T2、SPARC T3、および SPARC T4 プロセッサには、いくつかの高精度カウンタがあります。システムでメモリー領域プロファイリングが可能かどうかを調べるには、collect —h コマンドを実行し、precise キーワードを探します。

たとえば、SPARC T4 プロセッサを備えたシステムで次のコマンドを実行すると、使用可能な高精度 raw カウンタが表示されます。

% collect -h | & grep -i precise | grep -v alias
    Instr_ld[/{0|1|2|3}],1000003 (precise load-store events)
    Instr_st[/{0|1|2|3}],1000003 (precise load-store events)
    SW_prefetch[/{0|1|2|3}],1000003 (precise load-store events)
    Block_ld_st[/{0|1|2|3}],1000003 (precise load-store events)
    DC_miss_L2_L3_hit_nospec[/{0|1|2|3}],1000003 (precise load-store events)
    DC_miss_local_hit_nospec[/{0|1|2|3}],1000003 (precise load-store events)
    DC_miss_remote_L3_hit_nospec[/{0|1|2|3}],1000003 (precise load-store events)
    DC_miss_nospec[/{0|1|2|3}],1000003 (precise load-store events)