Каково различие между LD_LIBRARY_PATH и-L во время ссылки?

У меня есть проблемы с LD_LIBRARY_PATH во время ссылки (этот вопрос не имеет никакого отношения ко времени выполнения).

Строка ссылки похожа на это, когда я работаю, делают (это - система Linux с помощью g ++ версия 4.1.x):

g++ a.o b.o c.o -o myapp \
 -L/long/path/to/libs/ \
 -L/another/long/path/ \
 -labc -ldef -lghi

-l ссылка опций совместно использовала библиотеки (например, libabc.so), которые существуют в каталогах, определенных -L опции. Те каталоги также появляются в LD_LIBRARY_PATH. С той конфигурацией ссылка успешна, и я могу запустить приложение.

Если я удаляю каталоги из LD_LIBRARY_PATH, тогда я получаю единственную ошибочную строку, такую как:

/usr/bin/ld: cannot find -labc

С другой стороны, если я удаляю каталоги из списка -L опции, тогда я получаю много предупреждений, таких как:

/usr/bin/ld: warning: libabc.so, needed by /long/path/to/libs/libxyz.so,
    not found (try using -rpath or -rpath-link)

и затем намного больше ошибок, таких как:

/long/path/to/libs/libdef.so: undefined reference to `Foo::Bar<Baz>::junk(Fred*)'

Может кто-то объяснять различие между LD_LIBRARY_PATH и -L? Я хотел бы понять этот материал подробно, таким образом, ссылки значительно ценятся!

Кроме того, что я должен добавить к строке ссылки для избегания использования LD_LIBRARY_PATH?

Править: Когда каталоги отсутствовали в -L, компилятор, предложенный "пытаться использовать-rpath или - rpath-ссылка". Я не думаю, что когда-либо видел те опции в make-файле прежде. Вы имеете? Не уверенный, если это помогло бы LD_LIBRARY_PATH проблема все же.

23
задан Dan 15 December 2009 в 16:37
поделиться

4 ответа

Настройки LD_LIBRARY_PATH имеют наивысший приоритет, поэтому, когда он установлен, набор каталогов, упомянутых LD_LIBRARY_PATH , ищется первым даже до стандартный набор
каталогов. Итак, в вашем случае настройка LD_LIBRARY_PATH влияет на поиск
библиотеки, указанные в параметре -l . Без LD_LIBRARY_PATH некоторых зависимостей
могло быть разрешено из стандартного набора каталогов.

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

Также см. этот HOWTO из документации Linux для получения более подробной информации об общих библиотеках

20
ответ дан 29 November 2019 в 01:05
поделиться

На этот вопрос есть два ответа, часть ответа заключается в компоновке во время компиляции (т.е. gcc -lfoo -L / usr / lib ... в свою очередь вызывает ld ) и поиск компоновщика во время выполнения.

Когда вы компилируете свою программу, компилятор проверяет синтаксис, а затем компоновщик, помимо прочего, гарантирует, что символы, необходимые для выполнения (т. Е. Переменные / методы / и т.д.), существуют. LD_LIBRARY_PATH , как уже отмечалось, имеет побочный эффект, заключающийся в изменении способа поведения gcc / ld , а также поведения компоновщика времени выполнения. путем изменения пути поиска.

Когда вы запускаете свою программу, компоновщик времени выполнения фактически выбирает разделяемые библиотеки (на диск или из памяти, если это возможно) и загружает совместно используемые символы / код / ​​и т.д. LD_LIBRARY_PATH влияет на этот путь поиска неявно (иногда не очень хорошо, как уже упоминалось.)

Правильное исправление для этого без использования LD_LIBRARY_PATH в большинстве систем Linux - добавить путь, содержащий ваши общие библиотеки, к /etc/ld.so.conf (или в некоторых дистрибутивах создайте файл в /etc/ld.so.conf.d/ с путь в нем) и запустите ldconfig ( / sbin / ldconfig как root), чтобы обновить кэш привязок компоновщика времени выполнения.

Пример в Debian:

jewart@dorfl:~$ cat /etc/ld.so.conf.d/usrlocal.conf 
/usr/local/lib

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

Если вы хотите знать, с какими библиотеками запускается - время, о котором знает компоновщик, вы можете использовать:

jewart@dorfl:~$ ldconfig -v 

/usr/lib:
libbfd-2.18.0.20080103.so -> libbfd-2.18.0.20080103.so
libkdb5.so.4 -> libkdb5.so.4.0
libXext.so.6 -> libXext.so.6.4.0

И, если вы хотите знать, с какими библиотеками связан двоичный файл, вы можете использовать ldd как такой, который сообщит вам, какую библиотеку выберет ваш компоновщик времени выполнения:

jewart@dorfl:~$ ldd /bin/ls
linux-vdso.so.1 =>  (0x00007fffda1ff000)
librt.so.1 => /lib/librt.so.1 (0x00007f5d2149b000)
libselinux.so.1 => /lib/libselinux.so.1 (0x00007f5d2127f000)
libacl.so.1 => /lib/libacl.so.1 (0x00007f5d21077000)
libc.so.6 => /lib/libc.so.6 (0x00007f5d20d23000)
32
ответ дан 29 November 2019 в 01:05
поделиться

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

Как часто нежелательный побочный эффект, LD_LIBRARY_PATH также будет искать на этапе ссылки (ld) после каталогов указывается с помощью -L (также, если нет флага -L дано).

Почему LD_LIBRARY_PATH - это плохо

8
ответ дан 29 November 2019 в 01:05
поделиться

Если бы я угадал, я бы сказал, что компоновщик возвращается к использованию LD_LIBRARY_PATH для разрешения библиотеки, с которыми динамически связаны ваши прямые ссылки (например, libabc.so , libdef.so и libghi.so ). Глядя на страницу руководства для ld , похоже, что ссылка на .so , созданная с использованием -rpath , повлияет на работу поиска динамически связанных символов. .

3
ответ дан 29 November 2019 в 01:05
поделиться
Другие вопросы по тегам:

Похожие вопросы: