LD_LIBRARY_PATH против LIBRARY_PATH

159

Я создаю простую программу на C ++ и хочу временно заменить поставляемую системой разделяемую библиотеку более свежей версией для разработки и тестирования.

Я попытался установить переменную LD_LIBRARY_PATH, но компоновщик (ld) потерпел неудачу с:

/ usr / bin / ld: не удается найти -lyaml-cpp

Я ожидал, что это сработает, потому что согласно man-странице ld:

Компоновщик использует следующие пути поиска для поиска необходимых общих библиотек: ... Для встроенного компоновщика содержимое переменной среды "LD_LIBRARY_PATH" ...

Затем я попытался установить LIBRARY_PATH, и это сработало.

Согласно руководству GCC:

Значение LIBRARY_PATH - это список каталогов, разделенный двоеточиями, очень похожий на PATH. При настройке в качестве собственного компилятора GCC пробует каталоги, указанные таким образом, при поиске специальных файлов компоновщика, если он не может найти их с помощью GCC_EXEC_PREFIX. Связывание с использованием GCC также использует эти каталоги при поиске обычных библиотек для опции -l (но каталоги, указанные с -L, идут первыми).

Как предполагает руководство (GCC), LIBRARY_PATH работает, потому что я связываюсь с GCC.

Но..

  • Поскольку я связываюсь с gcc, почему вызывается ld, как следует из сообщения об ошибке?
  • Какой смысл иметь две переменные, служащие одной цели? Есть ли другие отличия?
Георгиос Политис
источник

Ответы:

213

LIBRARY_PATH используется gcc перед компиляцией для поиска в каталогах, содержащих статические и общие библиотеки, которые необходимо связать с вашей программой.

LD_LIBRARY_PATHиспользуется вашей программой для поиска каталогов, содержащих общие библиотеки, после того, как она была успешно скомпилирована и скомпонована.

РЕДАКТИРОВАТЬ: Как указано ниже, ваши библиотеки могут быть статическими или общими. Если он статический, то код копируется в вашу программу, и вам не нужно искать библиотеку после того, как ваша программа скомпилирована и скомпонована. Если ваша библиотека является общей, то она должна быть динамически связана с вашей программой, и именно тогда она LD_LIBRARY_PATHвступает в игру.

Нэвин
источник
14
И, конечно, LD_LIBRARY_PATH имеет смысл только с динамическими библиотеками
Алекс Жасмин
2
Я хочу сказать, что если бы я использовал ld для линковки (напрямую), то, согласно руководству ld, LD_LIBRARY_PATH использовался бы для поиска каталогов, содержащих библиотеки, которые должны быть связаны с моей программой. Я, должно быть, что-то здесь
упускаю
2
если вы сами не вызовете ld и не объедините объектные файлы с библиотеками, он «унаследует» путь, который ему передает gcc. Вы можете переопределить стандартный gcc с опциями -Xlinker.
Навин
5
На самом деле, LIBRARY_PATH используется для поиска каталогов, содержащих статические и динамические библиотеки, а не только статические библиотеки.
particle128
3
Да , это неправильно - разница в том , что LIBRARY_PATHищется для библиотек (статические или динамические) при компиляции и LD_LIBRARY_PATHищется динамических библиотек во время выполнения. Конечно, во время выполнения вам не нужно искать статические библиотеки.
Тимммм
47

LD_LIBRARY_PATHищется при запуске программы, LIBRARY_PATHищется во время ссылки.

будьте осторожны из комментариев :

F'x
источник
38
Примечание: при компоновке библиотек, ldсами по себе не ищет библиотеки либо LIBRARY_PATHили LD_LIBRARY_PATH. Это только когда gccвызывает, ldчто LIBRARY_PATHиспользуется. (Изучил это трудным путем.)
Rufflewind
1
@Rufflewind Интересно, но было бы еще больше, если бы вы дали какую-либо ссылку.
hmijail скорбит по отставке
Это представление делает различие в момент поиска библиотек (время соединения и время выполнения), в то время как @Naveen различает тип библиотек, которые ищут (статический v динамический). Существуют ли фактически два идентичных представления (динамическое: время выполнения = статическое: время соединения) или существуют важные ситуации, когда это соответствие не выполняется? Я предполагаю, что некоторые знания о динамических библиотеках необходимы также во время компиляции.
XavierStuvw
13

Поскольку я связываюсь с gcc, почему вызывается ld, как следует из сообщения об ошибке?

gcc вызывает ld внутри, когда он находится в режиме связывания.

heroxbd
источник