Oracle® Developer Studio 12.5: dbx コマンドによるデバッグ

印刷ビューの終了

更新: 2016 年 6 月
 
 

OpenMP コードで利用可能な dbx の機能

マルチスレッドプログラムをデバッグするための通常の機能に加えて、dbx には、OpenMP プログラムをデバッグするための機能が用意されています。 スレッドおよび LWP 上で動作するすべての dbx コマンドは OpenMP デバッグに使用できます。dbx は、OpenMP デバッグでの非同期スレッド制御はサポートしていません。

並列領域へのシングルステップ

dbx は、並列領域にシングルステップ実行できます。並列領域は OpenMP 実行時ライブラリからアウトライン化されて呼び出されるため、実行のシングルステップでは、実際には、この目的で作成されたスレッドによって実行される何層にもわたる実行時ライブラリの呼び出しが実行されます。 並列領域にシングルステップ実行すると、最初にブレークポイントに到達したスレッドによってプログラムが停止します。このスレッドは、ステップを開始したマスターステップではなく、スレーブスレッドになります。

たとえば、コンパイラによる OpenMP コードの変換の Fortran コードで、マスタースレッド t@1 が行 10 にあるとします。行 12 にシングルステップ実行すると、スレーブスレッド t@2t@3、および t@4 が作成され、実行時ライブラリの呼び出しを実行します。スレッド t@3 が最初にブレークポイントに到達し、プログラムの実行が停止します。そのため、スレッド t@1 によって開始されたシングルステップは、スレッド t@3 で終了します。この動作は、一般にシングルステップのあとも前と同じスレッド上にある通常のステップ実行とは異なります。

変数と式の出力

dbx は、すべての共有変数、非公開変数、およびスレッド非公開変数を出力できます。並列領域外で thread private 変数を出力しようとすると、マスタースレッドのコピーが出力されます。whatis コマンドは、並列構文内の shared 変数と private 変数のデータ共有属性を出力します。スレッド非公開変数については、並列構造内にあるかどうかには関係なく、そのデータ共有属性を出力します。例:

(dbx) whatis p_a
# OpenMP first and last private variable
int p_a;

print –s コマンドは、式 expression に非公開変数またはスレッド非公開変数が含まれている場合、現在の OpenMP 並列領域内のスレッドごとにその式の値を出力します。例:

(dbx) print -s p_a
thread t@3: p_a = 3
thread t@4: p_a = 3

式に private 変数または thread private 変数が含まれない場合は、1 つの値だけが出力されます。

領域およびスレッド情報の出力

現在の並列領域または指定された並列領域の説明を出力するには、omp_pr コマンドを使用します。これには、親領域、並列領域 ID、チームのサイズ (スレッドの数)、およびプログラムの場所 (プログラムカウンタアドレス) が含まれます。例:

(dbx) omp_pr
parallel region 127283434369843201
    team size = 4
    source location = test.c:103
    parent = 127283430568755201

また、現在の並列領域または指定された並列領域からそのルートまでのパスに沿ったすべての並列領域の説明を出力することもできます。例:

(dbx) omp_pr -ancestors
parallel region 127283434369843201
    team size = 4
    source location = test.c:103
    parent = 127283430568755201

    parallel region 127283430568755201
        team size = 4
        source location = test.c:95
        parent = <no parent>

また、並列領域ツリー全体も出力できます。例:

(dbx) omp_pr -tree
parallel region 127283430568755201
    team size = 4
    source location = test.c:95
    parent = <no parent>

    parallel region 127283434369843201
        team size = 4
        source location = test.c:103
        parent = 127283430568755201

詳細については、omp_pr コマンドを参照してください。

現在のタスク領域または指定されたタスク領域の説明を出力するには、omp_tr コマンドを使用します。これには、タスク領域 ID、状態 (spawnedexecutingwaiting)、実行中のスレッド、プログラムの場所 (プログラムカウンタアドレス)、未完了の子、および親が含まれます。例:

(dbx) omp_tr
task region 65540
    type = implicit
    state = executing
    executing thread = t@4
    source location == test.c:46
    unfinished children = 0
    parent = <no parent>

また、現在のタスク領域または指定されたタスク領域からそのルートまでのパスに沿ったすべてのタスク領域の説明を出力することもできます。

(dbx) omp_tr -ancestors
task region 196611
    type = implicit
    state = executing
    executing thread = t@3
    source location - test.c:103
    unfinished children = 0
    parent = 131075

    task region 131075
        type = implicit
        state = executing
        executing thread = t@3
        unfinished children = 0
        parent = <no parent>

また、タスク領域ツリー全体も出力できます。例:

(dbx) omp_tr -tree
task region 10
    type = implicit
    state = executing
    executing thread = t@10
    source location = test.c:103
    unfinished children = 0
    parent = <no parent>
task region 7
    type = implicit
    state = executing
    executing thread = t@7
    source location = test.c:103
    unfinished children = 0
    parent = <no parent>
task region 6
    type implicit
    state = executing
    executing thread = t@6
    source location = test.c:103
    unfinished children = 0
    parent = <o parent>
task region 196609
    type = implicit
    state = executing
    executing thread = t@1
    source location = test.c:95
    unfinished children = 0
    parent = <no parent>

    task region 262145
        type = implicit
        state = executing
        executing thread = t@1
        source location = test.c:103
        unfinished children - 0
        parent = 196609
 

詳細については、omp_tr コマンドを参照してください。

現在のループの説明を出力するには、omp_loop コマンドを使用します。これには、スケジューリング型 (静的、動的、ガイド付き、自動、または実行時)、順序付きかどうか、範囲、ステップ数または刻み幅、および繰り返し回数が含まれます。例:

(dbx) omp_loop
    ordered loop: no
    lower bound: 0
    upper bound: 3
    step: 1
    chunk: 1
    schedule type: static
    source location: test.c:49

詳細については、omp_loop コマンドを参照してください。

現在のチームまたは指定された並列領域のチーム上のすべてのスレッドを出力するには、omp_team コマンドを使用します。例:

(dbx) omp_team
team members:
    0: t@1 state = in implicit barrier, task region = 262145
    1: t@6 state = in implicit barrier, task region = 6
    2: t@7 state = working, task region = 7
    3: t@10 state = in implicit barrier, task region = 10

詳細については、omp_team コマンドを参照してください。

OpenMP コードをデバッグしている場合、thread –info は、現在のスレッドまたは指定されたスレッドに関する通常の情報に加えて、OpenMP スレッド ID、並列領域 ID、タスク領域 ID、および OpenMP スレッドの状態を出力します。詳細については、thread コマンドを参照してください。

並列領域の実行の直列化

現在のスレッド、または現在のチーム内のすべてのスレッドについて、次に検出された並列領域の実行を直列化するには、omp_serialize コマンドを使用します。詳細については、omp_serialize コマンドを参照してください。

スタックトレースの使用

並列領域内で実行が停止されると、where コマンドは、アウトラインサブルーチンを含むスタックトレースを表示します。

(dbx) where
current thread: t@4
=>[1] _$d1E48.main(), line 52 in "test.c"
  [2] _$p1I46.main(), line 48 in "test.c"

--- frames from parent thread ---
current thread: t@1
  [7] main(argc = 1, argv = 0xffffffff7fffec98), line 46 in "test.c"

スタックの上位フレームはアウトライン関数のフレームです。コードが略述されているにもかかわらず、ソース行番号は依然として 15 にマップされます。

並列領域で実行が停止されたときに、関連フレームがアクティブ状態である場合、スレーブスレッドの where コマンドはマスタースレッドのスタックトレースを出力します。マスタースレッドの where コマンドは完全トレースバックを行います。

また、まず omp_team コマンドを使用して現在のチーム内のすべてのスレッドを一覧表示し、次にマスタースレッド (OpenMP スレッド ID が 0 のスレッド) に切り替え、そのスレッドからスタックトレースを取得することによって、実行がスレーブスレッド内のブレークポイントにどのように到達したかを判定することもできます。

dump コマンドの使用

並列領域内で実行が停止されると、dump コマンドは、非公開変数の複数のコピーを出力する可能性があります。 次の例では、dump c コマンドが変数 i の 2 つのコピーを出力します。

[t@1 l@1]: dump
i = 1
sum = 0.0
a = ARRAY
i = 1000001

変数 i の 2 つのコピーが出力されるのは、アウトラインルーチンがホストルーチンのネストされた関数として実装され、private 変数がアウトラインルーチンの局所変数として実装されます。dump コマンドはスコープ内のすべての変数を出力するため、ホストしているルーチン内の i とアウトラインルーチン内の i の両方が表示されます。

イベントの使用

dbx では、OpenMP コード上で stopwhen、および trace コマンドで使用できるイベントが提供されます。これらのコマンドとともにイベントを使用する方法については、イベント指定の設定を参照してください。

同期イベント

omp_barrier [type] [state]

バリアーに入っているスレッドのイベントを追跡します。

type の有効な値は次のとおりです。

  • explicit – 明示的なバリアーを追跡する

  • implicit – 暗黙的なバリアーを追跡する

type を指定しなければ、明示的なバリアーだけが追跡されます。

state の有効な値は次のとおりです。

  • enter – いずれかのスレッドがバリアーに入ったときにイベントを報告する

  • exit – いずれかのスレッドがバリアーを出たときにイベントを報告する

  • all_entered – すべてのスレッドがバリアーに入ったときにイベントを報告する

state を指定しない場合のデフォルトは all_entered です。

enter または exit を指定する場合は、そのスレッドのみの追跡を指定するためにスレッド ID を含めることができます。

omp_taskwait [state]

taskwait に入っているスレッドのイベントを追跡します。

state の有効な値は次のとおりです。

  • enter – スレッドが taskwait に入ったときにイベントを報告する

  • exit – すべての子タスクが完了したときにイベントを報告する

state を指定しない場合のデフォルトは exit です。

omp_ordered [state]

順序付き領域に入っているスレッドのイベントを追跡します。

state の有効な値は次のとおりです。

  • begin – 順序付き領域が開始したときにイベントを報告する

  • enter – スレッドが順序付き領域に入ったときにイベントを報告する

  • exit – スレッドが順序付き領域を出たときにイベントを報告する

state を指定しない場合のデフォルトは enter です。

omp_critical

クリティカル領域に入っているスレッドのイベントを追跡します。

omp_atomic [state]

不可分領域に入っているスレッドのイベントを追跡します。

state の有効な値は次のとおりです。

  • begin – 微細領域が開始したときにイベントを報告する

  • exit – スレッドが微細領域を出たときにイベントを報告する

state を指定しない場合のデフォルトは begin です。

omp_flush

フラッシュを実行しているスレッドのイベントを追跡します。

その他のイベント

omp_task [state]

タスクの作成と終了を追跡します。

state の有効な値は次のとおりです。

  • create – タスクが作成されてすぐ、その実行が開始される前にイベントを報告する

  • start – タスクがその実行を開始したときにイベントを報告する

  • finish – タスクがその実行を完了し、終了されようとしているときにイベントを報告する

state を指定しない場合のデフォルトは start です。

omp_master

マスター領域に入るマスタースレッドのイベントを追跡します。

omp_single

単一領域に入っているスレッドのイベントを追跡します。