web-dev-qa-db-ja.com

osxの.soと.dylibの違いは何ですか?

.dylibはOSXの動的ライブラリ拡張機能ですが、従来のUNIX .so共有オブジェクトを使用できない/使用すべきでない場合は、はっきりしませんでした。

私が持っている質問のいくつか:

  • 概念レベルでは、.soと.dylibの主な違いは何ですか?
  • いつ使用することができますか?
  • コンパイルのコツとヒント(たとえば、osxでは機能しないため、gcc -shared -fPICの置き換え)
190
Trent Davies

Mac OS Xが実行可能ファイルおよびライブラリに使用するMach-Oオブジェクトファイル形式は、共有ライブラリ動的にロードされるファイルを区別しますモジュールotool -hv some_fileを使用して、some_fileのファイルタイプを確認します。

Mach-O共有ライブラリのファイルタイプはMH_DYLIBで、拡張子は.dylibです。これらは、通常の静的リンカーフラグとリンクすることができます。 libfoo.dylibの-lfoo-dynamiclibフラグをコンパイラに渡すことで作成できます。 (-fPICがデフォルトであり、指定する必要はありません。)

ロード可能なモジュールは、Mach-O speakでは「バンドル」と呼ばれます。ファイルタイプはMH_BUNDLEです。彼らは、任意の拡張子を運ぶことができます。 Appleは拡張子.bundleを推奨していますが、移植されたソフトウェアのほとんどは、互換性のために.soを使用しています。通常、アプリケーションを拡張するplug-insにはバンドルを使用します。このような状況では、バンドルはアプリケーションバイナリにリンクして、アプリケーションのエクスポートされたAPIにアクセスします。 -bundleフラグをコンパイラに渡すことで作成できます。

Dylibとバンドルは、dl AP​​Iを使用して動的にロードできます(例:dlopendlclose)。バンドルを共有ライブラリであるかのようにリンクすることはできません。ただし、バンドルが実際の共有ライブラリに対してリンクされている可能性があります。これらは、バンドルがロードされるときに自動的にロードされます。

歴史的に、違いはより重要でした。 Mac OS X 10.0では、ライブラリを動的にロードする方法はありませんでした。 dyld APIのセット(例:NSCreateObjectFileImageFromFileNSLinkModule)は、バンドルをロードおよびアンロードするために10.1で導入されましたが、dylibでは機能しませんでした。バンドルで機能するdlopen互換性ライブラリは10.3で追加されました。 10.4では、dlopenはdyldのネイティブ部分に書き換えられ、dylibのロード(アンロードではない)のサポートが追加されました。最後に、10.5はdylibでdlcloseを使用するためのサポートを追加し、dyld APIを廃止しました。

LinuxなどのELFシステムでは、- 両方とも同じファイル形式を使用 ;共有コードの任意の部分をライブラリとして使用したり、動的ロードに使用したりできます。

最後に、Mac OS Xでは、 "bundle"alsoが、実行可能コードと使用されるリソースを保持する標準化された構造を持つディレクトリを参照できることに注意してください。そのコード。いくつかの概念的な重複があります(特にプラグインのような「ロード可能なバンドル」には、通常Mach-Oバンドルの形式で実行可能コードが含まれます)が、上記のMach-Oバンドルと混同しないでください。

追加の参照:

174
Miles

ファイル.soは、共有ライブラリのUNIXファイル拡張子ではありません。

よくあることです。

ArnaudRecipes sharedlibページ の行3bを確認します

基本的に、.dylibは、共有ライブラリを示すために使用されるmacファイル拡張子です。

19
Martin York

Mac os xでの.dylibと.soの違いは、コンパイル方法です。 .soファイルには-sharedを使用し、.dylibには-dynamiclibを使用します。 .soと.dylibは両方とも動的ライブラリファイルとして互換性があり、DYLIBまたはBUNDLEのいずれかのタイプを持っています。これを示すさまざまなファイルの読み出しを示します。

libtriangle.dylib:
Mach header
      magic cputype cpusubtype  caps    filetype ncmds sizeofcmds      flags
MH_MAGIC_64  X86_64        ALL  0x00       DYLIB    17       1368   NOUNDEFS DYLDLINK TWOLEVEL NO_REEXPORTED_DYLIBS



libtriangle.so:
Mach header
      magic cputype cpusubtype  caps    filetype ncmds sizeofcmds      flags
MH_MAGIC_64  X86_64        ALL  0x00       DYLIB    17       1256   NOUNDEFS DYLDLINK TWOLEVEL NO_REEXPORTED_DYLIBS

triangle.so:
Mach header
      magic cputype cpusubtype  caps    filetype ncmds sizeofcmds      flags
MH_MAGIC_64  X86_64        ALL  0x00      BUNDLE    16       1696   NOUNDEFS DYLDLINK TWOLEVEL

Mac OS Xでこの2つが同等である理由は、.soファイルタイプにコンパイルされる他のUNIX OSプログラムとの後方互換性のためです。

コンパイルに関する注意:.soファイルまたは.dylibファイルのどちらをコンパイルする場合でも、リンク手順中にダイナミックライブラリに正しいパスを挿入する必要があります。これを行うには、リンクコマンドに-install_nameとファイルパスを追加します。これを行わない場合、この投稿で見られる問題に遭遇します: Mac Dynamic Library Craziness(Fortranのみかもしれません)

11
Zachary Kraus

OSXでcmakeを使用して素朴なコードを構築しているときに行った観察です。

cmake ... -DBUILD_SHARED_LIBS=OFF ...

。soファイルを作成します

ながら

cmake ... -DBUILD_SHARED_LIBS=ON ...

。dynlibファイルを作成します。

おそらくこれは誰にも役立つでしょう。

3
user2996950