我想设置一个变量,该变量可在我作为子目录 ( ) 包含的第三方库中修改add_subdirectory(.../third_party/libA)
。该库允许我启用/禁用构建过程的某些部分,例如包括测试目标,例如:set(BUILD_TESTS OFF)
。
但是,如果多个库包含相同的选项,并且名称相同,我该怎么办?我知道存在我想要实现的“相反方向”PARENT_SCOPE
的选项set()
,但是有没有办法以某种方式限制范围,以便我可以执行以下操作(下面的模拟行为):
project(my_project)
set(libA_BUILD_TESTS OFF) # I DO NOT want to build tests for libA
add_subdirectory("${my_project_SOURCE_DIR}/third_party/libA")
set(libB_BUILD_TESTS ON) # I DO want to build tests for libB
add_subdirectory("${my_project_SOURCE_DIR}/third_party/libB")
由于我无法控制第三方库的变量名,因此变量libA_BUILD_TESTS
和libB_BUILD_TESTS
实际上并不存在。它们都只是有BUILD_TESTS
。
是否可以这样做并期望每个都应该正确设置?我不熟悉 CMake 如何处理变量解析的时间...
set(BUILD_TESTS OFF) add_subdirectory(.../third_party/libA) set(BUILD_TESTS ON) add_subdirectory(.../third_party/libB)
除了共享相同的变量名之外,有没有更明确/更安全的方式来声明我希望这两个变量不同?对我来说,重复使用相同的变量名似乎从根本上容易出错,而且特别“糟糕”。我不喜欢这样,因为它使变量“有状态”,这使得在构建过程中更难跟踪。
我是否正确地思考了这个基本的变量设置过程?也许我对 #2 的感受根本不是“做事的方式”。
我尝试过的一些随机的事情(没有成功):
特定于子目录的设置属性:
set(libA_dir "${my_project_SOURCE_DIR}/third_party/libA")
set(libB_dir "${my_project_SOURCE_DIR}/third_party/libB")
set_property(DIRECTORY ${libA_dir} PROPERTY BUILD_TESTS OFF)
set_property(DIRECTORY ${libB_dir} PROPERTY BUILD_TESTS ON)
设置目标属性(由于目标尚不存在,因此不起作用):
# does not work because the libA target does not yet exist
set_target_properties(libA PROPERTIES BUILD_TESTS OFF)
add_subdirectory("${my_project_SOURCE_DIR}/third_party/libA")
# this does work based on how the third party CMake was written...
find_package(libA REQUIRED)
在定义目标之后设置目标属性(不起作用,因为在看到我的 set_target_properties 之前逻辑已经被处理了):
add_subdirectory("${my_project_SOURCE_DIR}/third_party/libA")
# does not work because the subdir was already included and seems to have not respected
# the options here due to timing/ordering.
set_target_properties(libA PROPERTIES BUILD_TESTS OFF)
# this does work based on how the third party CMake was written...
find_package(libA REQUIRED)
最后:我希望了解确保这两个库之间变量分配“隔离”的方法,尤其是当同一个变量有两个不同的值时(即“我想为 libA 构建测试,但不想为 libB 构建测试”)。谢谢。