回答:
ranlib
追加または更新されたオブジェクトファイルをに静的ライブラリ。リンカは、コードが動作するために必要なシンボルを提供するために、リンク時に静的ライブラリを使用できます(ローダーが実行可能ファイルの実行時に動的ライブラリでそれらを探すのとは対照的です)。
ranlib
ライブラリの作成と変更に使用されます。それらを使用するかどうかは、通常、コマンドラインでライブラリの場所や名前を渡すことにより、リンカに委ねられます。詳細については、-L
および-l
gccの引数を参照してください。
ar
もしませんか?違いは何ですか?
この説明はかなり明確に見えます:http : //sourceware.org/binutils/docs/binutils/ranlib.html
したがって、オブジェクトファイルのコレクションをアーカイブする場合は、次のようにします。
$ ar r fruits.a apple.o orange.o pineapple.o
その後、実行
$ ranlib fruits.a
fruit.aのコンテンツのインデックスを作成し、fruits.aにインデックスを格納します。これは、リンクやオブジェクトが相互に呼び出す場合に役立ちます。
tar
あまり明確ではありません。
ar
Linuxではar
、GNU汎用アーカイバーです。(ar
他のUnixライクなOSには、GNU以外のバリアントがあります)。オプション付きc
ar c... archive-name file...
のコピーを含むアーカイブを作成しますfile...
。archive-name
従来は必ずしも必要ではない拡張子がある.a
(のためのアーカイブを)。それぞれfile...
がオブジェクトファイルである必要はなく、どのような種類のファイルでもかまいません。
アーカイブされたファイルがすべてオブジェクトファイルである場合、通常はアーカイブを使用して、選択したオブジェクトファイルをプログラムまたはDSO(動的共有オブジェクト)のリンケージに配信します。この場合archive-name
、従来どおりlib
、たとえば
libfoo.a
、接頭辞が付けられるため、リンカーオプションを介して候補リンカー入力ファイルとして検出できます-lfoo
。
リンカー入力ファイルとして使用され、libfoo.a
通常はスタティックライブラリと呼ばれます。この使用法は、アーカイブlibfoo.a
がDSOとほぼ同じ種類のものでありlibfoo.so
、通常はダイナミック/共有ライブラリーと呼ばれ、これに基づいて誤った期待を構築するため、熟練していないプログラマーにとっては、絶え間ない混乱の源です。実際、「静的ライブラリ」と「動的ライブラリ」はまったく同じものではなく、まったく異なる方法で連携して使用されます。
顕著な違いは、静的ライブラリはリンカーではなくによって生成されることar
です。したがって、リンケージは発生せず、シンボル解決も発生しません。アーカイブされたオブジェクトファイルは変更されていません。バッグに入れられているだけです。
アーカイブは、何かの連携で入力されるとされた未収いる未解決のシンボル参照の定義を提供し、その中に任意のオブジェクトファイルがあるかどうかを確認するために袋の中のリンカーのルックス-このようなプログラムやDSOなど-リンカによって生成しますリンケージの早い段階で。見つかった場合は、それらのオブジェクトファイルをバッグから抽出し、リンカーのコマンドラインで個別に指定した場合とまったく同じようにアーカイブに名前を付けたかのように、それらを出力ファイルにリンクします。したがって、リンケージにおけるアーカイブの全体的な役割は、リンカがリンケージを実行するために必要なファイルを選択できるオブジェクトファイルのバッグとしての役割です。
デフォルトでは、GNU ar
はその出力アーカイブをリンカー入力として使用できるようにします。偽の「ファイル」を魔法の偽のファイル名でアーカイブに追加します。この偽のファイルには、アーカイブ内のオブジェクトファイルによって定義されているグローバルシンボルからリンカがルックアップテーブルとして読み取ることができるコンテンツが書き込まれます。アーカイブ内のそれらのオブジェクトファイルの名前と位置に。このルックアップテーブルにより、リンカーはアーカイブを調べて、手元にある未解決のシンボル参照を定義するオブジェクトファイルを識別できます。
このルックアップテーブルの作成または更新を抑制するには、q
(= クイック)オプション(
実際には独自のar
例で使用しています)および(大文字)S
(= シンボルテーブルなし)オプションを使用します。またar
、何らかの理由で(最新の)シンボルテーブルを持たないアーカイブを作成または更新するために呼び出す場合は、オプションでアーカイブを指定できs
ます。
ランリブ
ranlib
ライブラリをまったく作成しません。Linuxにranlib
は、(最新の)シンボルテーブルar
がない場合にアーカイブに追加するレガシープログラムがあります。その効果はar s
、GNU の場合とまったく同じar
です。歴史的にar
は、シンボルテーブル自体を生成する機能が装備される前はranlib
、マジックフォニーファイルをアーカイブに挿入して、リンカーがオブジェクトファイルを選択できるようにするクラッジがありました。非GNU UnixライクなOSでは、ranlib
この目的のためにまだ必要になるかもしれません。あなたの例:
ar qc libgraphics.a *.o
ranlib libgraphics.a
言う:
libgraphics.a
すべての*.o
ファイルをアーカイブに追加して作成します。libgraphics.a
Linuxでは、これは次と同じ正味の効果があります。
ar cr libgraphics.a *.o
それ自体はar qc libgraphics.a *.o
、シンボルテーブルがないため、リンカが使用できないアーカイブを作成します。
ld
あなたの例:
ld -r -o libgraphics.a *.o
実際にはまったく正統ではありません。これはかなり稀使用示すリンカー、
ld
製造する、マージされたシンボル解決が実行された単一の出力オブジェクトファイルに複数の入力ファイルをリンクすることによってオブジェクトファイルをはるかに可能な限り入力ファイル所与を、。-r
(= 再配置可能)オプションは、未定義のシンボル参照は出力ファイルに残っている場合linkaqeを失敗する可能な限りとしないように入力をリンクすることによって、オブジェクトファイル(むしろプログラムより、またはDSO)ターゲットを生成するために、リンカーを指示します。この使用法は、部分リンクと呼ばれます。
の出力ファイルはアーカイブでld -r ...
はなくオブジェクトファイルであり、 ar
アーカイブのように見える出力ファイル名を指定しても、ファイル名にar
はなりません。したがって、あなたの例は欺瞞を示しています。この:
ld -r -o graphics.o *.o
正直になります。ELFオブジェクトファイルが呼び出されlibgraphics.a
、その名前またはによってリンケージに入力された場合でも-lgraphics
、リンカーがELFオブジェクトファイルとして正しく識別するため、このような詐欺の目的が何であるかは不明です。ar
アーカイブではなく、コマンドラインでオブジェクトファイルを使用するのと同じように使用します。無条件にアーカイブを出力ファイルにリンクしますが、本物のアーカイブを入力する目的は、参照されている場合にのみアーカイブメンバーをリンクすることです。たぶん、あなたはここで悪質なリンクの例を持っているだけでしょう。
まとめ...
実際には、ライブラリと呼ばれるものを生成する方法は1つしかありません。これは、いくつかのオブジェクトファイルをアーカイブし、シンボルテーブルをアーカイブに保存する、いわゆるスタティックライブラリの生成です。
また、従来ライブラリと呼ばれていた他の最も重要な種類のオブジェクト、つまり動的共有オブジェクト/共有ライブラリ/動的ライブラリを作成する方法はまったく見ていません。
プログラムと同様に、DSOはリンカーによって生成されます。プログラムとDSOは、OSローダーが理解し、実行中のプロセスをアセンブルするために使用できるELFバイナリのバリアントです。通常、我々は(GCCフロントエンドの1つを介してリンカーを起動しgcc
、g++
、gfortran
、など):
プログラムのリンク:
gcc -o prog file.o ... -Ldir ... -lfoo ...
DSOのリンク:
gcc -shared -o libbar.so file.o ... -Ldir ... -lfoo ...
-lfoo
他のプログラムまたはDSOをリンクする場合、共有ライブラリと静的ライブラリの両方を、統一されたプロトコルによってリンカーに提供できます。そのオプションのいずれかを見つけるために、その指定するか、デフォルトの検索directroriesをスキャンするためにリンカに指示し
libfoo.so
たりlibfoo.a
。デフォルトでは、どちらかが見つかると、そのファイルをリンケージに入力しますlibfoo.so
。同じ検索ディレクトリで両方が見つかった場合は、を優先します。場合はlibfoo.so
、選択された後、リンカはDSOは、どんなプログラムやDSOの実行時の依存関係リストにあなたが作っていることを追加します。場合はlibfoo.a
、選択された右が、その後、必要に応じてリンカは、出力ファイルに結合のためのオブジェクトファイルの選択などのアーカイブを使用しています。ランタイムに依存しない
libfoo.a
それ自体は可能です。プロセスにマッピングすることはできません。OSローダーには何の意味もありません。