cmake 如何设置dylib搜索路径OSX

7gyucuyw  于 2023-10-20  发布在  其他
关注(0)|答案(1)|浏览(144)

我在Xcode中有一个项目,我在环境变量窗格中设置DYLD_BELLBACK_LIBRARY_PATH来设置我的应用程序应该在哪里寻找要链接的库(这对我的目的很有效)

我写一个CMakeLists.txt文件生成这个项目现在,我想从脚本设置这个属性。
我知道我可以做到这一点:

SET(ENV{DYLD_FALLBACK_LIBRARY_PATH} ${DYLD_FALLBACK_LIBRARY_PATH} /path/to/lib)

但是当我运行时,我得到这个错误:

'dyld: Library not loaded ... Reason: image not found'

启动应用程序时。我想声明是不一样的。
有人知道我怎样才能从CMakeLists.txt中实现与Xcode中相同的功能吗?
我隐约知道CMake RPATH的东西,但我宁愿避免,如果可能的话。
感谢您的宝贵时间!
干杯!干杯!
汤姆

lmvvr0a8

lmvvr0a81#

我终于用一种稍微不同的方法完成了这个工作。这可能不是完美的解决方案,并在所有情况下工作,但希望这将有助于有人谁是有类似的问题,我。
我尝试链接的dylib是libSDL2-2.0.0
如果我导航到该文件所在的位置并运行:

otool -L libSDL2-2.0.0.dylib

我在输出中得到的最上面一行是这样的:

/usr/local/lib/libSDL2-2.0.0.dylib

然后,如果我导航到我构建的可执行文件并运行相同的命令,我会看到同样的事情:

/usr/local/lib/libSDL2-2.0.0.dylib

(my可执行文件链接到SDL)
我的问题是libSDL2-2.0.0.dylib实际上并不在那里,它在我的项目结构中的一个libs文件夹中。为了让链接器在运行时找到库,我必须在dylib上运行以下命令

install_name_tool -id "@executable_path/../path/to/lib/<lib_name>" <lib_name>

其中@executable_path是要运行的应用程序的位置-在我的示例中,这是在-build/debug
项目结构:

root/
    CMakeLists.txt
    project/
        lib/
            libSDL2-2.0.0.dylib
    build/
        debug/
            my_app

为了清晰起见,这是一个精确的Map:

install_name_tool -id "@executable_path/../../project/lib/libSDL2-2.0.0.dylib" libSDL2-2.0.0.dylib

如果我运行otool -L libSDL2-2.0.0.dylib,我现在看到:

@executable_path/../../sdl-test/lib/libSDL2-2.0.0.dylib

在输出的第一行。
如果我现在再次构建我的项目(我只是在Xcode中构建),这会用dylib的新相对路径更新我的应用程序。你只需要在库上运行install_name_tool,你不需要在你的可执行文件上运行它,当你构建它的时候,它会被更新。
如果我运行otool -L myapp,我现在会看到到libSDL2-2.0.0.dylib的相同相对路径
有了这个,当启动应用程序时,它能够成功地找到dylib!
我的理解是,这是在OSX上实现这一点的方法,没有一个很好的替代方案(除了我在问题中提到的DYLD_FALLBACK_LIBRARY_PATH
我希望这对那些有类似困难的人有所帮助!
我发现有用的资源:
http://osiris.laya.com/coding/dylib_linking.html
https://www.fmod.org/questions/question/forum-23398/
https://blogs.oracle.com/dipol/entry/dynamic_libraries_rpath_and_mac

更新:

实际上,我发现了一种更好的方法,使用rpaths来实现这一点,并认为我应该写下来以供将来参考:
在我的CMakeLists.txt文件中,我在末尾添加了以下行(在add_executabletarget_link_libraries之后):

# set @rpaths for libraries to link against
set(CMAKE_SKIP_BUILD_RPATH  FALSE)
set(CMAKE_BUILD_WITH_INSTALL_RPATH TRUE) 
set(CMAKE_INSTALL_RPATH "${PROJ_LIB_DIR}")
set(CMAKE_INSTALL_RPATH_USE_LINK_PATH TRUE)

(see https://cmake.org/Wiki/CMake_RPATH_handling了解更多信息)
其中${PROJ_LIB_DIR}是我的dylib所在的位置:

set(PROJ_LIB_DIR ${CMAKE_CURRENT_LIST_DIR}/lib)

然后我跑了:
举例说明:

install_name_tool -id "@rpath/<my-dylib>.dylib" <my-dylib>.dylib

实际:

install_name_tool -id "@rpath/libSDL2-2.0.0.dylib" libSDL2-2.0.0.dylib

在我的dylib所在的目录中(在我的例子中是libSDL 2 -2.0.0.dylib)
现在,当我运行cmake并构建我的项目时,我的新可执行文件将在运行时在CMakeLists.txt文件中设置的位置搜索库。@rpath将替换为CMakeLists.txt文件中指定的路径,所有内容都可以正常工作,而无需显式设置@executable_path@loader_path

相关问题