Каковы различия между .so и .dylib на osx?

.dylib - расширение динамической библиотеки на OSX, но мне никогда не было ясно, когда я не могу/не должен использовать традиционный unix.so общий объект.

Некоторые из вопросов, которые у меня есть:

  • На концептуальном уровне, каковы основные различия между .so и .dylib?
  • Когда можно/нужно использовать один над другим?
  • Компиляционные трюки и подсказки (например, замена gcc -shared -fPIC, поскольку это не работает на osx)

Ответ 1

Формат файла объекта Mach-O, используемый Mac OS X для исполняемых файлов и библиотек, различает разделяемые библиотеки и динамически загружаемые модули. Используйте otool -hv some_file, чтобы просмотреть тип файла some_file.

Совместно используемые библиотеки Mach-O имеют тип файла MH_DYLIB и несут расширение .dylib. Они могут быть связаны с обычными статическими флагами компоновщика, например. -lfoo для libfoo.dylib. Их можно создать, передав флаг -dynamiclib компилятору. (-fPIC является значением по умолчанию и его не нужно указывать.)

Загружаемые модули называются "расслоениями" в речи Mach-O. Они имеют тип файла MH_BUNDLE. Они могут нести любое расширение; расширение .bundle рекомендуется Apple, но большинство портированных программ использует .so для обеспечения совместимости. Как правило, вы используете пакеты для плагинов, которые расширяют приложение; в таких ситуациях пакет связывается с двоичным кодом приложения, чтобы получить доступ к API-интерфейсам, экспортированным приложениями. Их можно создать, передав флаг -bundle компилятору.

Оба dylibs и bundles могут динамически загружаться с использованием API dl (например, dlopen, dlclose). Невозможно связать их с пакетами, как если бы они были разделяемыми библиотеками. Однако возможно, что связка связана с реальными разделяемыми библиотеками; они будут загружаться автоматически при загрузке пакета.

Исторически различия были более значительными. В Mac OS X 10.0 не было возможности динамически загружать библиотеки. Набор dyld API (например, NSCreateObjectFileImageFromFile, NSLinkModule) был введен с 10.1 для загрузки и выгрузки пакетов, но они не работали для dylib. Библиотека соответствия dlopen, которая работала с пакетами, была добавлена ​​в 10.3; в 10.4, dlopen была переписана как нативная часть dyld и добавлена ​​поддержка загрузки (но не разгрузки) dylib. Наконец, 10.5 добавили поддержку использования dlclose с dylib и отказались от dyld API.

В ELF-системах, таких как Linux, используют один и тот же формат файла; любая часть общего кода может использоваться как библиотека и для динамической загрузки.

Наконец, имейте в виду, что в Mac OS X "bundle" может также ссылаться на каталоги со стандартизованной структурой, которая содержит исполняемый код и ресурсы, используемые этим кодом. Существует некоторое концептуальное перекрытие (в частности, с "загружаемыми пучками", такими как плагины, которые обычно содержат исполняемый код в виде пакета Mach-O), но их не следует путать с пакетами Mach-O, рассмотренными выше.

Дополнительные ссылки:

Ответ 2

Файл .so не является расширением UNIX для общей библиотеки.

Это просто бывает обычным.

Проверить строку 3b на ArnaudRecipes sharedlib page

В основном .dylib - это расширение файла Mac, используемое для указания общей библиотеки.

Ответ 3

Разница между .dylib и .so на mac os x заключается в том, как они скомпилированы. Для .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, - это обратная совместимость с другими программами ОС UNIX, которые скомпилируются с типом файла .so.

Замечания о компиляции: компилируете ли файл .so или .dylib файл, вам нужно вставить правильный путь в динамическую библиотеку во время этапа компоновки. Вы делаете это, добавляя -install_name и путь к ссылке на команду связывания. Если вы этого не сделаете, вы столкнетесь с проблемой, замеченной в этом сообщении: Mac Dynamic Library Craziness (может быть только Fortran).

Ответ 4

Просто замечание, которое я только что сделал при создании простого кода для OSX с помощью cmake:

cmake ... -DBUILD_SHARED_LIBS=OFF ...

создает .so файлы

в то время как

cmake ... -DBUILD_SHARED_LIBS=ON ...

создает файлы .dynlib.

Возможно, это кому-нибудь поможет.