对提升库的依赖没有完整路径
Dependencies on boost library don't have full path
我成功地构建了我的动态库,它依赖于使用自定义前缀(./b2 install --prefix=PREFIX
)构建和安装的boost库。然而,当我在库上运行otool -L
时,我得到的输出如下:
...
libboost_regex.dylib (compatibility version 0.0.0, current version 0.0.0)
libboost_system.dylib (compatibility version 0.0.0, current version 0.0.0)
...
与其他依赖项不同,它在没有通往这些提升库的完整路径的情况下呈现。当应用程序加载我的库时,这会导致运行时错误。我知道可以使用install_name_tool
手动解决这个问题。然而,我试图弄清楚,为什么它只发生在boost库中,而不发生在我的lib所依赖的其他依赖项中?
编辑
我被要求给出一个构建命令的例子,但和往常一样,"现实生活"的例子有点复杂。在我的例子中,有一个库libA.dylib
,它依赖于boost。然后是我的库libMy.dylib
,它依赖于libA.dylib
和boost。问题出现在configure
步骤中,当执行简单的库存在检查时(类似于AC_CHECK_LIB
的自定义测试程序)。该检查试图构建一个与libA.dylib
链接的小测试程序,以证明libA.dylib
的可用性,但由于找不到boost库的错误,该检查失败了。当然,它不会找到它们,因为otool -L libA.dylib
给了我没有完整路径的提升库。
回答问题:
"为什么它只发生在boost库中,而不发生在我的lib所依赖的其他依赖项中"
技术原因是Boost构建系统(bjam)显式地将库的安装名指定为仅文件名。它可以在内部使用-install_name编译器选项来执行此操作
对于其背后的理由,我不能代表Boost开发人员发言,所以我只能推测(这是一种糟糕的投资形式):对库中的本地安装路径进行硬编码只会延迟";库未找到";运行时错误到分发时间,所以他们可能只希望您在开发时尽快正确解决它。(或者这可能只是他们不想投入更多时间返工的遗留行为;)
潜在解决方案
假设您的动态库(依赖于Boost)命名为myLib
。正如您在问题中已经指出的,您可以很好地更改记录在myLib
:中的Boost库的安装名称
install_name_tool myLib -change libboost_regex.dylib /full/path/to/libboost_regex.dylib
另一种选择是更改Boost库本身的安装名称:
install_name_tool libboost_regex.dylib -id $new_name
使用这种方法,当您根据修改后的libboost_regex.dylib
构建安装名称$new_name
时,它将记录在myLib
中
您必须决定给$new_name哪个值。当然,它可以是库的完整路径,这样Boost库的行为将与其他依赖项一样。
另一种更易于分发的选择是使用RPath。(基于RPath的安装名称给依赖程序增加了查找依赖项的负担:依赖程序存储了一个路径列表,它将尝试用它来替换"@RPath"):
install_name_tool libboost_regex.dylib -id @rpath/libboost_regex.dylib #assign a rpath dependant install name to a boost library
install_name_tool myLib -add_rpath $a_rpath_prefix # adds a candidate to substitute @rpath with, stored in myLib
$a_rpath_prefix
可以是包含Boost库的文件夹的路径,它将在您的开发环境中运行良好。如果有一天你需要分发你的库,你可以将Boost依赖项嵌入到一个相对路径(或OSX捆绑包)中,并添加一个将遵循这个相对路径的RPath值。
编辑到问题
对于您描述的无法定位Boost的自动检查的特定情况,您可能可以使用上面提出的替代解决方案来解决它。它更改了存储在库中的Boost库的安装名称(因此将被复制到libA.dylib
中):
install_name_tool libboost_regex.dylib -id /full/path/to/libboost_regex.dylib
在这个特定的用例中,一个更简单的解决方案可以是用包含Boost库的目录的路径填充DYLD_FALLBACK_LIBRARY_PATH
。动态链接器将在这些目录中查找库,因此它将在那里找到boost库。在将运行构建检查的终端中:
export DYLD_FALLBACK_LIBRARY_PATH=/full/path/to/;$DYLD_FALLBACK_LIBRARY_PATH
- 如何从C++中的依赖类型中获得它所依赖的类型
- 如何将更多文件夹添加到c++include路径
- 带有特殊路径部分的"std::filesystem::weakly_canonical"失败
- C++A*算法并不总是在路径中具有目标节点
- 使用运行路径进行 C++ 辅助依赖项解析
- CMake将依赖项复制到可执行输出路径
- 如果 copts 不允许系统路径,如何引用外部依赖项使用的系统库?
- 错误 LNK1104:错误消息中显示的路径未在其他依赖项中定义
- 提供依赖于输入的程序的文件路径
- 共享库依赖于具有硬编码路径的其他库
- Maven NAR插件:在路径上找不到DLL依赖项
- 如何解决 CMake + XCode 4 路径依赖项
- qmake:如何消除对绝对路径的依赖
- Heroku / Rails:无法设置供应商化依赖项的路径
- 对提升库的依赖没有完整路径
- 为构建依赖使用绝对路径
- (make/g++)包含自动生成的依赖目标的完整路径?(或方法)
- 动态依赖库/tls搜索路径
- GCC 自动依赖完整路径
- 在DLL搜索路径中添加路径以帮助执行依赖于DLL的EXE