System.mapファイルの概要と機能
Linuxオペレーティングシステムでは、System.mapファイルが
カーネルに関連する重要な役割を果たします。このファイルは、
カーネルが使用するシンボルテーブルとして機能し、シンボル名とそのアドレスの対応関係を示しています。シンボル名は、主にデータや関数の名前であり、これを使って
カーネルが内部でどのように働いているかを理解することができます。
System.mapファイルの必要性
特に
カーネルパニックや
Linux kernel oopsが発生した際、System.mapファイルはデバッグに非常に役立ちます。これにより、問題のあるシンボル名やそのアドレスを特定しやすくなります。
カーネルは、CONFIG_KALLSYMSの設定が有効である場合、自動的にアドレスと名前の変換を行います。この機能により、特別なツールであるksymoopsを使用せずとも、シンボル情報を取得できるようになります。
シンボルテーブルの構造
System.mapファイルの一部には、以下のようなアドレスとシンボルのリストが存在します:
```
c041bc90 b packet_sklist
c041bc94 b packet_sklist_lock
c041bc94 b packet_socks_nr
c041bc98 A __bss_stop
c041bc98 A _end
c041c000 A pg0
ffffe400 A __kernel_vsyscall
ffffe410 A SYSENTER_RETURN
ffffe420 A __kernel_sigreturn
ffffe440 A __kernel_rt_sigreturn
```
このリストは、`nm`コマンドの出力結果と一致しており、スペースで区切られたアドレスとシンボル名の間にある文字列は、それぞれのシンボルの「型」を示しています。
UNIXシステムにおける`nm`ユーティリティは、
オブジェクトファイルに含まれるシンボルをリストアップしますが、System.mapはその結果を一箇所に集めたものです。つまり、
カーネル全体を対象に`nm`を実行し、その結果をファイルに書き出したものだと考えられます。
カーネルビルドとSystem.mapの生成
Linuxカーネルのビルドプロセスでは、最終的に実行可能なファイル「vmlinux」が生成され、その後に`nm`コマンドを実行してSystem.mapが作成されます。このファイルが作成された後、vmlinuxからはシンボルがストリップされ、特殊なコードがリンクされて圧縮され、最終的に「zImage」や「bzImage」と呼ばれるファイルが生成されるのです。これが通常目にする
カーネルそのものであり、アドレスはコンパイル時に決定しますので、
カーネルのビルドが行われるたびにSystem.mapファイルも新しく生成されることになります。
シンボルの型についての説明
System.mapにおいて、シンボルにはさまざまな型が定義されています。以下はその一部です:
- - A: 絶対アドレス
- - B または b: 初期化されていないデータセクション (BSSと呼称)
- - D または d: 初期化済みデータセクション
- - G または g: 小さいオブジェクト用の初期化済みデータセクション (global)
- - N: デバッギングシンボル
- - R または r: 読み取り専用データセクション
- - T または t: テキスト(コード)セクション
- - U: 未定義シンボル
これらの型は、シンボルの性質を理解する上で非常に重要です。
System.mapファイルの配置場所
System.mapファイルは、
カーネルのビルドが正常に終了すると、
カーネルソースコードのトップ
ディレクトリに配置されますが、その後のソフトウェアのインストールプロセスにより、他の
ディレクトリにもコピーされることがあります。例えば、次のような場所に存在することがあります:
- - `/boot/System.map-$(uname -r)`
- - `/lib/modules/$(uname -r)/build/System.map`(SVGALibのビルド時)
また、
Linuxカーネルのバージョン2.5.71以降のシステムでは、`/proc/kallsyms`を用いて現在読み込まれているシンボル名とそのアドレスを表示することも可能で、これはSystem.mapファイルの情報の一部に相当します。
まとめ
このように、System.mapファイルは
カーネルの構造を理解し、デバッグする上で欠かせない情報源となっています。
カーネルの挙動を把握するためにも、このファイルの内容を正確に理解することが重要です。