C 未在libtool包装器脚本中将生成的库目录添加到LD_library_路径

C 未在libtool包装器脚本中将生成的库目录添加到LD_library_路径,c,automake,libtool,C,Automake,Libtool,我无法在生成后轻松测试我的程序: $ ./src/rap/rap -h /home/il/workspace/rap/src/rap/.libs/lt-rap: error while loading shared libraries: libpmclient.so: cannot open shared object file: No such file or directory libpmclient.so位于/src/nsreclient/x86_64-unknown-linux-gnu

我无法在生成后轻松测试我的程序:

$ ./src/rap/rap -h
/home/il/workspace/rap/src/rap/.libs/lt-rap: error while loading shared libraries: libpmclient.so: cannot open shared object file: No such file or directory
libpmclient.so
位于
/src/nsreclient/x86_64-unknown-linux-gnu/
中,链接过程中使用了正确的
-L
标志

Automake使用libtool构建我的二进制文件。它创建一个包装器脚本
src/rap/rap

我的期望是:在生成脚本时,libtool将忽略
LD\u LIBRARY\u PATH
的当前值。运行脚本时,它会将构建树中所需的目录附加到现有值
LD\u LIBRARY\u PATH
。e、 g.执行:

LD_LIBRARY_PATH=/foo ./src/rap/rap
将导致:

LD_LIBRARY_PATH=/foo:/home/il/workspace/rap/src/nsreclient/x86_64-unknown-linux-gnu ./src/rap/.libs/lt-rap
但libtool的作用正好相反:它将
LD\u LIBRARY\u PATH
的当前值硬编码到生成的脚本中:

LD_LIBRARY_PATH=/opt/oracle/product/11.2.0/client_64/lib:/lib:/usr/lib:/usr/local/lib; export LD_LIBRARY_PATH;
这毫无意义。为什么不在那里添加构建树目录

下面是make命令的格式化输出:

/bin/sh ../../libtool  --tag=CC   --mode=link gcc  -Werror-implicit-function-declaration -O2 \
    -pthread   -o rap rap.o \
    librap.a \
    ../liclib/liblic.a \
    ../fget-1.3.3/lib/libfget.a \
    ../lib_mt/libppb.la \
    ../sgplib/libsgp.la \
    ../../variations/asn1lib/ebuf_lib_mt/libasn1cebuf.la \
    -L../../src/nsreclient/x86_64-unknown-linux-gnu -lpmclient \
    -L/opt/oracle/product/11.2.0/client_64/lib -lclntsh \
    -L/usr/lib -lexpat \
    -lssl \
    -lcrypto  \
    -lm


libtool: link: gcc -Werror-implicit-function-declaration -O2 -pthread -o .libs/rap rap.o  librap.a ../liclib/liblic.a ../fget-1.3.3/lib/libfget.a \
    ../lib_mt/.libs/libppb.so \
    ../sgplib/.libs/libsgp.so \
    ../../variations/asn1lib/ebuf_lib_mt/.libs/libasn1cebuf.so \
    -L../../src/nsreclient/x86_64-unknown-linux-gnu -lpmclient \
    -L/opt/oracle/product/11.2.0/client_64/lib -lclntsh \
    -L/usr/lib /usr/lib/libexpat.so \
    -lssl -lcrypto -lm -pthread -Wl,-rpath -Wl,/usr/local/lib

libtool
及其包装器脚本所做的工作存在误解。 特别是,它不会解析传递给链接器的库路径(
-L
)的所有标志,并将它们添加到一些
LD\u library\u PATH
变量中

libtool包装器脚本的目的是(cf)满足使用

[任何]已卸载的libtool库

现在
libtool库
是那些古怪的
.la
文件(而不是带有
.so
后缀的实际动态库)

由于您的
libpmclient.so
不是这样的怪兽,因此包装器脚本在这里对您帮助不大

解决方案
如果您无法将第三方库安装到运行时链接器可以找到它们的地方,我建议您在进行黑客攻击时向
LD\u LIBRARY\u PATH
添加所需的路径,并获取配置文件(你也可以在你的
~/.bashrc
中这样做,但是如果你以后使用你的帐户来处理不同于单个项目编码的事情,那么它可能会妨碍你)

包装器脚本根本不设置
LD\u LIBRARY\u PATH
。它假定包含所需库的子目录已添加到实际二进制文件的
RPATH

-lfoo
标志传递给
libtool
时,它首先尝试打开相应的文件
libfoo.la
。如果该文件不存在,
libtool
会退回到将标志传递给
gcc
不变

如果
.la
文件存在并指向共享库,
libtool
告诉链接器将包含库的目录添加到输出二进制文件的
RPATH

许多软件包将其
.la
文件安装到
/usr/lib/
中。这意味着较新的
libtool
将能够解析以前版本创建的文件。手动为预编译的
编写
.la
文件必须是完全安全的。因此
文件不是每次都生成它们

我创建了文件
/src/nsreclient/x86_64-unknown-linux-gnu/libpmclient.la

# libpmclient.la - a libtool library file
# Generated by ltmain.sh - GNU libtool 1.5.22 (1.1220.2.365 2005/12/18 22:14:06)
#
# Please DO NOT delete this file!
# It is necessary for linking the library.

# The name that we can dlopen(3).
dlname='libpmclient.so'

# Names of this library.
library_names='libpmclient.so'

# The name of the static archive.
old_library='libpmclient.a'

# Linker flags that cannot go in dependency_libs.
inherited_linker_flags=' -pthread'

# Libraries that this one depends upon.
dependency_libs=''

# Names of additional weak libraries provided by this library
weak_library_names=''

# Version information for libpmclient.
current=0
age=0
revision=0

# Is this an already installed library?
installed=no

# Should we warn about portability when linking against -modules?
shouldnotlink=no

# Files to dlopen/dlpreopen
dlopen=''
dlpreopen=''

# Directory that this library needs to be installed in:
libdir='/usr/local/lib'

重建后,我的包装器脚本不再抱怨。

您说过库位于
/src/nsreclient/x86_64-unknown-linux-gnu/
,但是该脚本没有将该目录添加到
$LD_library\u路径中。
。这不是问题吗?@特洛伊木马是的。(
/src/…
)因此,您需要编辑设置
$LD\u LIBRARY\u路径的脚本?或者您想做其他事情吗?我想知道为什么libtool不这么做。您是如何链接的?您可以显示
Makefile.am
部分吗?我还有另外两个库有
.la
文件:
。/lib\u mt/libppb.la
。/sgplibsgp.la
。它们没有添加到LD_LIBRARY_PATH,但我的二进制文件可以找到它们。也许最好手动为第三方编写一个
.la
文件。那么?