🌕

よく使うgdbコマンド覚書

2022/08/21に公開

いままでデバッガーはlldbをつかっていたのだが、

GDBでステップ実行をしていて、実行ステップ行を戻すことができずに、「しまった!行きすぎた!」という経験はよくある。

そんなとき、プログラムの実行を最初からやり直してあげる必要があったが、gdbのreverse debuggingをつかうと、next に対応する reverse-next や、stepに対応する reverse-step で前のステップや、前の行に戻って実行を繰り返すことができる。

1. 起動

デバッグのためのコンパイルオプション

-gオプションを付ける。
ここはlldbと同じ。

$ gcc -g hoge.c

ファイル名を指定してlldbを起動

$ gdb hoge

TUIモード

Ctrl + x + 1でソースコードの表示

Ctrl + x + 2を繰り返し入力することで、2画面でレジスタ、ソースコード、アセンブラ
の組み合わせを表示

実行

$ r

2. 基本操作

変数を出力

$ p 変数

処理を次に進める

n(next)

$ n

ステップインのs でもOK。

ステップイン

関数がある場合はステップ・イン
なければ現在の位置から 1 行分だけ処理を進める

$ s	

スタックトレースを出力

スタックトレースとは、エラーが発生するまでに、どんな処理をどの順番で呼び出したの履歴
btとはthread backtraceの略

$ bt

デフォルトの引数を確認

$ show args

ローカル変数の一覧を出力

$ i lo

iはinformationの略
loはlocalの略

ソースコードを表示

l

構造体を出力

pコマンドを使うと構造体名が出力されます。
また、p val[0]と、[0]を指定することで構造体の中身を見ることができます。

$ p val[0]

現在の関数を最後まで実行

$ fin

ループを抜ける

$ u

uはuntilの略

一つ前の行にもどる

これはlldbにはない機能なので重宝する。

まずは、プログラム実行中に、事前に

$ record

を入力し、一つ前に戻りたいときに

$ reverse-next

を入力する。

sでステップイン直後に、ステップイン前に戻りたい場合は、

$ reverse-step

1つ前のブレークポイントへ戻りたい場合は、

$ reverse-continue 

今実行している関数が呼び出される直前へ戻りたい場合は、

$ reverse-finish

recordを止める場合は

$ record stop

3. ブレークポイント

関数にブレークポイントを張る

$  b main

ファイルと行数を指定してブレークポイントを張る

以下は、test.cファイルの12行目にブレークポイントを貼った例

 $ break test.c:12

ブレークポイントを張った後の移動

rコマンドで実行して最初のプレークポイントへ移動

その後、次のブレークポイントへの移動はc(continue)コマンドを使う。

ブレークポイント一覧を出力

$ i b

ブレークポイントの削除

$ d 1

で1番目のブレークポイントの削除できる

グローバル変数の値が変更された時

$ watch global_var

設定したグローバル変数の値が変更される時に停止。

4. その他

実行中の関数から即return

$ return <RETURN EXPRESSION>

オプションで RETURN EXPRESSIONを入力すると、return値を設定できる。

値の代入

$ p var1=-1

変数var1の値を-1に変更

現在のスレッド上で式を評価

$ call	

スタックフレームを選択

番号を指定して、現在のスレッドのスタックフレームを選択
番号はbt(thread backtrace)で参照

$ f 番号

先のスタックフレームへ移動

$ down

過去のスタックフレームへ移動

$ up		

現在のターゲットプロセスを終了

$ kill

デバッガを終了

$ q

5. シチュエーション別

セグフォ

rで実行
listあるいはlとタイプし、少し広く処理が中断した箇所を表示
btで、その場所がmain関数からどのように呼び出されているかを確認

子プロセスのデバック

子プロセスを生むプログラムの場合、forkの前に以下のコマンドで子プロセスのデバッグが可能に

set follow-fork-mode child

Discussion