TL; DR
Objective-C app与静态库链接,动态链接Boost Filesystem。应用程序可以使用终端从输出目录运行,但尝试从Xcode调试器或Finder运行会出现错误dyld: Library not loaded: libboost_filesystem.dylib <snip> Reason: image not found
。
问题
在我的Xcode项目中,我有一个如下所示的结构:
MainProject (Objective-C)
- static_lib_that_uses_filesystem (C++)
为了获得所有链接,我将libboost_system和libboost_filesystem dylibs添加到MainProject中的“Link Binary with Libraries”构建阶段。
当我尝试从Xcode或Finder运行应用程序时,我得到:
sharedlibrary apply-load-rules all
warning: Unable to read symbols for libboost_filesystem.dylib (file not found).
warning: Unable to read symbols from "libboost_filesystem.dylib" (not yet mapped into memory).
warning: Unable to read symbols for libboost_system.dylib (file not found).
warning: Unable to read symbols from "libboost_system.dylib" (not yet mapped into memory).
[Switching to process 43957 thread 0x0]
dyld: Library not loaded: libboost_filesystem.dylib
Referenced from: /Users/ssteele/Library/Developer/Xcode/DerivedData/MainProject-dqrhyuarllykslftblocjdzxlran/Build/Products/Debug/MainProject.app/Contents/MacOS/MainProject
Reason: image not found
我添加了一个构建阶段,将dylib复制到bundle中的Frameworks目录,这没有用。我将其更改为将它们复制到Executables目录,这也没有帮助。
将它们放在可执行文件目录中允许我从终端运行应用程序。
如何从Finder / Xcode运行时让应用程序找到dylib?
背景资讯
我在Lion上使用Xcode 4.2,目前仅针对Lion。我为文件系统构建了我的共享库,如下所示:
./b2 threading=multi macosx-version=10.7 --with-filesystem stage
这会创建libboost_system.dylib,libboost_filesystem.dylib,以及stage / lib目录中的.a等效项,我直接在那里引用它们。
答案 0 :(得分:12)
OSX上的动态库(dylib)在应该从中加载的路径中进行烘焙。例如......
/usr/lib/some_awesome.dylib
。
链接到dylib时,链接器会将此路径嵌入可执行文件中,作为在运行时查找它的位置。这对于安装的库来说很简单,但是对于相对路径的链接,它更复杂。
当你构建boost库时,他们只是嵌入了他们的名字而不是完整或相对路径(即libboost_system.dylib
而不是/usr/lib/libboost_filesystem.dylib
)。您应该可以使用dll-path
option,that seems broken currently更改此内容。
要解决您的问题,您需要以某种方式将相对于嵌入式应用程序的正确路径(例如@executable_path/libwhatever.dylib
)放入dylibs中,这可能需要bjam dll-path选项才能工作,或者您可以修复您的可执行文件以查找其他位置。
要执行此操作,请使用以下内容作为构建中的脚本步骤:
install_name_tool -change libboost_filesystem.dylib @executable_path/libboost_filesystem.dylib$BUILT_PRODUCTS_DIR/$EXECUTABLE_PATH
请注意,如果您有多个dylib使用损坏的路径相互引用,您还需要修复它们之间的路径,例如。
install_name_tool -change libboost_system.dylib @executable_path/libboost_system.dylib$BUILT_PRODUCTS_DIR/$EXECUTABLE_FOLDER_PATH/libboost_filesystem.dylib
以下是一篇很好的文章:Creating working dylibs
答案 1 :(得分:1)
问题在于需要安装增强功能,例如b2 ..... install
。这会将库和标头复制到/ usr / local / lib和/ usr / local / include。
OSX动态库仅从为其构建的目录运行。
您可以使用-prefix参数更改安装目录以进行boost构建。但是,库仍然需要位于所有用户的同一目录中。
应该有一种方法可以将boost作为框架构建和/或在库中嵌入@executable_path。
另一种方法是使用boost的静态库 - 仅构建静态或删除动态库,Xcode在静态之前查找动态。如果使用static,那么库的路径在运行时无关紧要,因为所有代码现在都在可执行文件中。
答案 2 :(得分:0)
我认为您需要将路径添加到“库搜索路径”中保存libboost_filesystem.a的目录
点击您的项目个人资料 - &gt;构建设置 - &gt;展开“搜索路径” - &gt; “图书馆搜索路径”