顶级CMakeLists.txt
包含:
include(CTest)
add_subdirectory(lib)
add_subdirectory(demo)
add_subdirectory(test)
lib/CMakeLists.txt
基本上是:
add_library(MyLib <sources>)
demo/CMakeLists.txt
基本上是:
add_executable(Demo demo.c)
target_link_libraries(Demo MyLib)
test/CMakeLists.txt
是:
add_test(NAME Demo COMMAND Demo)
从一个gitlab-runner,我们执行:
cmake -G "Ninja" -DCMAKE_INSTALL_PREFIX=C:\opt\x64 -B. ..
cmake --build
ctest --output-on-failure
前两步成功;第三个失败的原因是:
Start 1: Demo
1/1 Test #1: Demo .......................Exit code 0xc0000135
***Exception: 0.03 sec
如果我重试:
cmake --install
ctest
则测试成功。所以唯一的问题是在运行ctest
时找不到build/lib/mylib.dll
。而C:\opt\x64\lib
位于PATH
中,因此DLL位于cmake --install
之后。然而,这并不是我们想要的:ctest
应始终使用当前版本的最新DLL,而不是已安装的版本。
在Linux下,一切正常。为什么不支持Windows和MinGW?这是CMake中的一个bug吗?我们如何解决这个问题,使ctest
在所有平台上都能正确执行?
2条答案
按热度按时间aydmsdu91#
您的问题似乎是Windows DLL搜索过程无法找到
mylib.dll
时,您的Demo
可执行文件是由ctest
运行。Windows DLL搜索顺序在此处指定:1.从其中加载应用程序的目录。
1.系统目录。使用
GetSystemDirectory
函数获取此目录的路径。GetWindowsDirectory
函数获取此目录的路径。1.当前目录。
1.在
PATH
环境变量中列出的目录。请注意,这不包括App Paths
注册表项指定的每个应用程序的路径。在计算DLL搜索路径时不使用App Paths
键。因此,您可以修改您的
PATH
环境变量,以 * 还 * 包括当前构建的新DLL的位置。一个更好、更少出错的解决方案可能是将DLL放在
Demo
可执行文件所在的目录中。您可以通过修改顶级CMake文件,强制CMake对DLL和可执行文件使用相同的binary目录:或者,作为一种本地化程度较低的方法,您可以通过设置
CMAKE_RUNTIME_OUTPUT_DIRECTORY
将DLL放置在与可执行文件相同的目录中:另一种选择:
jucafojl2#
使用生成器表达式并附加到测试环境PATH的更现代的方法:
这将把包含“my_library”的目录附加到测试运行器在Windows上构建时使用的PATH中,否则不会有任何更改。不需要复制库或弄乱构建产品的位置,也不需要直接更改PATH或使用特定的工作目录。