18

カーネル モジュールがクラッシュしたときに運が良ければ、レジスタ内の値など、多くの情報を含むログを含む oops を取得できます。そのような情報の 1 つがスタック トレースです (コア ダンプについても同じことが言えますが、もともとはカーネルモジュール用にこれを求めていました)。次の例を見てください。

[<f97ade02>] ? skink_free_devices+0x32/0xb0 [skin_kernel]
[<f97aba45>] ? cleanup_module+0x1e5/0x550 [skin_kernel]
[<c017d0e7>] ? __stop_machine+0x57/0x70
[<c016dec0>] ? __try_stop_module+0x0/0x30
[<c016f069>] ? sys_delete_module+0x149/0x210
[<c0102f24>] ? sysenter_do_call+0x12/0x16

私の推測では+<number1>/<number2>、エラーが発生した関数からのオフセットと関係があると思います。つまり、この番号を調べることで、おそらくアセンブリの出力を見て、このエラーが発生した行 (できれば命令) を見つけることができるはずです。あれは正しいですか?

私の質問は、これらの 2 つの数字は正確には何ですか? それらをどのように活用しますか?

4

3 に答える 3

19
skink_free_devices+0x32/0xb0

これは、問題のある命令が0x32関数の開始からのバイトであり、合計でバイト長でskink_free_devices()あることを意味します。0xB0

カーネルを有効にしてコンパイルすると、ツールまたは古き良きもの-gを使用してコントロールがジャンプした関数内の行番号を取得できますaddr2linegdb

このようなもの

$ addr2line -e ./vmlinux 0xc01cf0d1
/mnt/linux-2.5.26/include/asm/bitops.h:244
or
$ gdb ./vmlinux
...
(gdb) l *0xc01cf0d1
0xc01cf0d1 is in read_chan (include/asm/bitops.h:244).
(...)
244     return ((1UL << (nr & 31)) & (((const volatile unsigned int *) addr)[nr >> 5])) != 0;
(...)

したがって、検査したいアドレスを指定するaddr2linegdb、問題のある関数が存在するソースファイルの行番号を教えてくれます詳細については、この記事を参照してください

EDIT: は、デバッグに使用されるカーネルの圧縮されていないバージョンであり、ソースからカーネルをビルドした場合vmlinuxに一般的に見つかります。あなたが見つけたのは圧縮されたカーネルであり、デバッグにはそれほど役に立たないかもしれません/lib/modules/$(uname -r)/build/vmlinuxvmlinuz/boot

于 2012-04-16T10:10:08.543 に答える
1

For Emacs users, here's is a major mode to easily jump around within the stack trace (uses addr2line internally).

Disclaimer: I wrote it :)

于 2012-11-01T00:35:07.243 に答える