オペレーティング システムを開発していますが、ページングをセットアップする前にいくつかのモジュールをロードする必要があります。したがって、この時点ではページングが設定されていないため、プログラム内のすべてのシンボルを物理アドレスに再配置する必要があります。私の問題は、すべてのシンボルがシンボル テーブルにあるわけではなく、すべての再配置情報が rel.text にあるわけではないことです。GCCにすべてのシンボルデータをエクスポートさせるにはどうすればよいですか???
2 に答える
確かに、再配置が必要なものはすべて再配置テーブルにあります。他にどのようにロードできますか?ページングが有効になっているかどうかに関係なく、再配置はまったく同じように機能します。バイナリ内の絶対位置であるエントリは、オフセットとともにリストされ、ロード ソフトウェアによって処理されます。他のすべては、移転しなくても問題ないはずです。
シンボルテーブルは、シンボルの場所を提供するだけなので、それ自体で再配置を解決するのに意味がないことに注意してください。
OS自体のシンボルについて考えていますか?もしそうなら、それは本当にあなたのOSから適切な方法でシンボルをエクスポートするケースです. Linux には EXPORT_SYMBOL(name) があり、カーネル自体内にシンボル テーブルを構築します。[これはgcc
またはによって生成されld
たシンボルではなく、マクロによって構築され、カーネルで処理されたシンボルであることに注意してください。
「コメント」のスペースが足りなくなったので、明確にするために編集してください: 「再配置」には 2 つのタイプがあります: switch ステートメントなど - これらは、現在の値と、バイナリが実際に配置されている場所 (もちろん仮想アドレス) のオフセットを加算するだけの問題です。もう1つは、モジュールが呼び出すときなどの「外部参照」です。spinlock()
- これはモジュール内に実装されていないため、「外部参照」があります。この場合、「spinlock」という名前の再配置エントリと、モジュール内でのスピンロックの呼び出し先のオフセットがあります。ここで明らかに、カーネルの「スピンロック」がどこにあるかを調べるためにシンボルテーブルが必要です [そして、本当に複雑にしたい場合は、モジュールが他のモジュールを参照できるようにしますが、1 つのモジュールのロードが OK になるまでそのままにしておきます最初!]。
本当にあなたの質問はリンカーに関するものです。答えは、使用しているリンカーによって異なります。
gccの標準リンカーld
である場合は、"-Wl,-r" オプションを試してください。